[
  {
    "path": ".editorconfig",
    "content": "root = true\n\n[*]\nindent_style = space\nindent_size = 4\ntab_width = 4\nend_of_line = lf\ncharset = utf-8\ntrim_trailing_whitespace = true\ninsert_final_newline = true\n\n[*.md]\ntrim_trailing_whitespace = false\n\n[*.{md,nix,yml,yaml}]\nindent_size = 2\ntab_width = 2\n"
  },
  {
    "path": ".eslintignore",
    "content": "public\nnode_modules\nresources/views\nbabel.config.js\ntailwind.config.js\nwebpack.config.js\n"
  },
  {
    "path": ".eslintrc.js",
    "content": "/** @type {import('eslint').Linter.Config} */\nmodule.exports = {\n    parser: '@typescript-eslint/parser',\n    parserOptions: {\n        ecmaVersion: 6,\n        ecmaFeatures: {\n            jsx: true,\n        },\n        project: './tsconfig.json',\n        tsconfigRootDir: './',\n    },\n    settings: {\n        react: {\n            pragma: 'React',\n            version: 'detect',\n        },\n        linkComponents: [\n            { name: 'Link', linkAttribute: 'to' },\n            { name: 'NavLink', linkAttribute: 'to' },\n        ],\n    },\n    env: {\n        browser: true,\n        es6: true,\n    },\n    plugins: ['react', 'react-hooks', 'prettier', '@typescript-eslint'],\n    extends: [\n        // 'standard',\n        'eslint:recommended',\n        'plugin:react/recommended',\n        'plugin:@typescript-eslint/recommended',\n        'plugin:jest-dom/recommended',\n    ],\n    rules: {\n        eqeqeq: 'error',\n        'prettier/prettier': ['error', {}, { usePrettierrc: true }],\n        // TypeScript can infer this significantly better than eslint ever can.\n        'react/prop-types': 0,\n        'react/display-name': 0,\n        '@typescript-eslint/no-explicit-any': 0,\n        '@typescript-eslint/no-non-null-assertion': 0,\n        // This setup is required to avoid a spam of errors when running eslint about React being\n        // used before it is defined.\n        //\n        // @see https://github.com/typescript-eslint/typescript-eslint/blob/master/packages/eslint-plugin/docs/rules/no-use-before-define.md#how-to-use\n        'no-use-before-define': 0,\n        '@typescript-eslint/no-use-before-define': 'warn',\n        '@typescript-eslint/no-unused-vars': ['warn', { argsIgnorePattern: '^_', varsIgnorePattern: '^_' }],\n        '@typescript-eslint/ban-ts-comment': ['error', { 'ts-expect-error': 'allow-with-description' }],\n        'react/no-unknown-property': ['error', { ignore: ['css'] }],\n    },\n};\n"
  },
  {
    "path": ".github/FUNDING.yml",
    "content": "github: [vlssu]\ncustom: [\"https://afdian.com/a/vlssu\"]\n"
  },
  {
    "path": ".github/ISSUE_TEMPLATE/1-bug-report.yml",
    "content": "name: Bug Reports\ndescription: For reporting known and reproducible issues with the software.\nbody:\n  - type: markdown\n    attributes:\n      value: |\n        Bug reports should only be used for reporting issues with how the software works. For assistance installing this software, as well as debugging issues with dependencies, please use our [Discord server](https://discord.gg/pterodactyl).\n\n  - type: textarea\n    attributes:\n      label: Current Behavior\n      description: Please provide a clear & concise description of the issue.\n    validations:\n      required: true\n\n  - type: textarea\n    attributes:\n      label: Expected Behavior\n      description: Please describe what you expected to happen.\n    validations:\n      required: true\n\n  - type: textarea\n    attributes:\n      label: Steps to Reproduce\n      description: Please be as detailed as possible when providing steps to reproduce, failure to provide steps will result in this issue being closed.\n    validations:\n      required: true\n\n  - type: input\n    id: panel-version\n    attributes:\n      label: Panel Version\n      description: Version number of your Panel (latest is not a version)\n      placeholder: 1.4.0\n    validations:\n      required: true\n\n  - type: input\n    id: wings-version\n    attributes:\n      label: Wings Version\n      description: Version number of your Wings (latest is not a version)\n      placeholder: 1.4.2\n    validations:\n      required: true\n\n  - type: input\n    id: egg-details\n    attributes:\n      label: Games and/or Eggs Affected\n      description: Please include the specific game(s) or egg(s) you are running into this bug with.\n      placeholder: Minecraft (Paper), Minecraft (Forge)\n\n  - type: input\n    id: docker-image\n    attributes:\n      label: Docker Image\n      description: The specific Docker image you are using for the game(s) above.\n      placeholder: ghcr.io/pterodactyl/yolks:java_17\n\n  - type: textarea\n    id: panel-logs\n    attributes:\n      label: Error Logs\n      description: |\n        Run the following command to collect logs on your system.\n\n        Wings: `sudo wings diagnostics`\n        Panel: `tail -n 150 /var/www/pterodactyl/storage/logs/laravel-$(date +%F).log | nc pteropaste.com 99`\n      placeholder: \"https://pteropaste.com/a1h6z\"\n      render: bash\n    validations:\n      required: false\n\n  - type: checkboxes\n    attributes:\n      label: Is there an existing issue for this?\n      description: Please [search here](https://github.com/pterodactyl/panel/issues) to see if an issue already exists for your problem.\n      options:\n        - label: I have searched the existing issues before opening this issue. I understand that maintainers may close this issue without communication if I have not provided sufficient information.\n          required: true\n"
  },
  {
    "path": ".github/ISSUE_TEMPLATE/2-approved.yml",
    "content": "name: Pre-Discussed and Approved Topics\ndescription: For topics already previously discussed and approved in the GitHub Discussions section.\nbody:\n  - type: markdown\n    attributes:\n      value: |\n        **DO NOT** open a new issue for feature requests _without prior maintainer approval_ and corresponding\n        thread in the discussions section. You MUST link to the corresponding discussion thread when opening\n        this feature request issue or it will be closed without further consideration.\n  - type: textarea\n    attributes:\n      label: The Feature Request\n  - type: input\n    attributes:\n      label: GitHub Discussion Link\n      description: Link to the GitHub Discussions thread where the feature was previously discussed and approved.\n    validations:\n      required: true\n"
  },
  {
    "path": ".github/ISSUE_TEMPLATE/config.yml",
    "content": "blank_issues_enabled: false\ncontact_links:\n  - name: 安装帮助\n    url: https://discord.gg/pterodactyl\n    about: 请访问翼龙的 Discord 来获取安装帮助。\n  - name: 基础问题\n    url: https://discord.gg/pterodactyl\n    about: 有关翼龙的基础问题，请访问翼龙的 Discord。\n  - name: 翼龙中国社区\n    url: https://bbs.pterodactyl.top\n    about: 有关常见问题和问题反馈\n  - name: 中文翻译问题\n    url: https://kook.top/0Grsf5\n    about: 有关中文翻译等一些问题，请访问翼龙中国的 KOOK 来获取帮助。\n"
  },
  {
    "path": ".github/docker/README.md",
    "content": "# 翼龙面板 - Docker 镜像\n这是一个将面板所需环境等全部准备好的 docker 镜像。\n\n## 要求\n此 docker 镜像需要一些额外的软件来运作。这些软件既可以在其他容器中提供（见 [docker-compose.yml](https://github.com/pterodactyl-china/panel/blob/develop/docker-compose.example.yml) 为例），也可以作为现有的实例。\n\n需要一个 mysql 数据库。如果你喜欢在 docker 容器中运行它，我们推荐使用 [MariaDB Image](https://hub.docker.com/_/mariadb/) 镜像。作为一个非容器化的选择，我们推荐 mariadb。\n\n还需要一个缓存软件。我们推荐使用 [Redis Image](https://hub.docker.com/_/redis/) 镜像。你可以选择任何一个[支持的选项](#缓存驱动程序)。\n\n你可以使用自定义的 `.env` 文件或在 docker-compose 文件中设置适当的环境变量来提供额外的设置。\n\n## 设置\n\n启动 docker 容器和所需的依赖项（可以提供现有的依赖项，也可以同时启动容器，参见 [docker-compose.yml](https://github.com/pterodactyl-china/panel/blob/develop/docker-compose.example.yml) 文件为例。\n\n启动完成后，您需要创建一个用户。\n如果您在没有 docker-compose 的情况下运行 docker 容器，请使用：\n```\ndocker exec -it <container id> php artisan p:user:make\n```\n如果您使用的是 docker compose，请使用\n```\ndocker-compose exec panel php artisan p:user:make\n```\n\n## 环境变量\n当您不提供自己的 `.env` 文件时，有多个环境变量可以配置面板，有关每个可用选项的详细信息，请参见下表。\n\n注意：如果您的 `APP_URL` 以 `https://` 开头，您还需要提供 `LE_EMAIL` 以便生成证书。\n\n| 变量               | 描述                           | 必需项 |\n|------------------|------------------------------|-----|\n| `APP_URL`        | 可以访问面板的 URL（包括协议）            | 是   |\n| `APP_TIMEZONE`   | 面板所使用的时区                     | 是   |\n| `LE_EMAIL`       | 用于生成 letsencrypt 证书的邮箱       | 是   |\n| `DB_HOST`        | MySQL 主机                     | 是   |\n| `DB_PORT`        | MySQL 端口                     | 是   |\n| `DB_DATABASE`    | MySQL 数据库名称                  | 是   |\n| `DB_USERNAME`    | MySQL 用户名                    | 是   |\n| `DB_PASSWORD`    | 指定用户的 MySQL 密码               | 是   |\n| `CACHE_DRIVER`   | 缓存驱动程序（详见[缓存驱动程序](#缓存驱动程序)）。 | 是   |\n| `SESSION_DRIVER` |                              | 是   |\n| `QUEUE_DRIVER`   |                              | 是   |\n| `REDIS_HOST`     | Redis 数据库的主机名或IP地址            | 是   |\n| `REDIS_PASSWORD` | 用于保护 redis 数据库的密码            | 可选  |\n| `REDIS_PORT`     | Redis 数据库端口                | 可选  |\n| `MAIL_DRIVER`    | 邮件驱动程序（详见 [邮件驱动程序](#邮件驱动程序)） | 是   |\n| `MAIL_FROM`      | 发件邮箱                         | 是   |\n| `MAIL_HOST`      | 邮件驱动主机                       | 可选  |\n| `MAIL_PORT`      | 邮件驱动端口                       | 可选  |\n| `MAIL_USERNAME`  | 邮件驱动用户名                     | 可选  |\n| `MAIL_PASSWORD`  | 邮件驱动密码                       | 可选  |\n\n### 缓存驱动程序\n您可以根据自己的喜好选择不同的缓存驱动程序。\n我们推荐在使用 docker 时使用 redis，因为它可以在容器中轻松启动。\n\n| 驱动程序   | 描述                                 | 所需变量                                               |\n| -------- | ------------------------------------ | ------------------------------------------------------ |\n| redis    | redis 运行的主机          | `REDIS_HOST`                                           |\n| redis    | redis 运行的端口             | `REDIS_PORT`                                           |\n| redis    | redis 数据库密码              | `REDIS_PASSWORD`                                       |\n\n### 邮件驱动程序\n你可以根据你的需要选择不同的邮件驱动。\n每个驱动程序都需要设置 `MAIL_FROM`。\n\n| 驱动程序   | 描述                                 | 所需变量                                                       |\n| -------- | ------------------------------------ | ------------------------------------------------------------- |\n| mail     | 使用已安装的php邮件                   |                                                               |\n| mandrill | [Mandrill](http://www.mandrill.com/) | `MAIL_USERNAME`                                               |\n| postmark | [Postmark](https://postmarkapp.com/) | `MAIL_USERNAME`                                               |\n| mailgun  | [Mailgun](https://www.mailgun.com/)  | `MAIL_USERNAME`, `MAIL_HOST`                                  |\n| smtp     | 任何SMTP服务器都可以配置               | `MAIL_USERNAME`, `MAIL_HOST`, `MAIL_PASSWORD`, `MAIL_PORT`    |\n"
  },
  {
    "path": ".github/docker/default.conf",
    "content": "# If using Ubuntu this file should be placed in:\n# \t\t\t/etc/nginx/sites-available/\n#\n# If using CentOS this file should be placed in:\n#\t\t\t\t /etc/nginx/conf.d/\n#\nserver {\n    listen 80;\n    server_name _;\n    \n    root /app/public;\n    index index.html index.htm index.php;\n    charset utf-8;\n\n    location / {\n        try_files $uri $uri/ /index.php?$query_string;\n    }\n\n    location = /favicon.ico { access_log off; log_not_found off; }\n    location = /robots.txt  { access_log off; log_not_found off; }\n\n    access_log off;\n    error_log  /var/log/nginx/pterodactyl.app-error.log error;\n\n    # allow larger file uploads and longer script runtimes\n    client_max_body_size 100m;\n    client_body_timeout 120s;\n  \n    sendfile off;\n\n    location ~ \\.php$ {\n        fastcgi_split_path_info ^(.+\\.php)(/.+)$;\n        # the fastcgi_pass path needs to be changed accordingly when using CentOS\n        fastcgi_pass 127.0.0.1:9000;\n        fastcgi_index index.php;\n        include fastcgi_params;\n        fastcgi_param PHP_VALUE \"upload_max_filesize = 100M \\n post_max_size=100M\";\n        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;\n        fastcgi_param HTTP_PROXY \"\";\n        fastcgi_intercept_errors off;\n        fastcgi_buffer_size 16k;\n        fastcgi_buffers 4 16k;\n        fastcgi_connect_timeout 300;\n        fastcgi_send_timeout 300;\n        fastcgi_read_timeout 300;\n    }\n\n    location ~ /\\.ht {\n        deny all;\n    }\n}\n"
  },
  {
    "path": ".github/docker/default_ssl.conf",
    "content": "# If using Ubuntu this file should be placed in: \n# \t\t\t/etc/nginx/sites-available/\n#\nserver {\n    listen 80;\n    server_name <domain>;\n    return 301 https://$server_name$request_uri;\n}\n\nserver {\n    listen 443 ssl http2;\n    server_name <domain>;\n\n    root /app/public;\n    index index.php;\n\n    access_log /var/log/nginx/pterodactyl.app-access.log;\n    error_log  /var/log/nginx/pterodactyl.app-error.log error;\n\n    # allow larger file uploads and longer script runtimes\n    client_max_body_size 100m;\n    client_body_timeout 120s;\n    \n    sendfile off;\n\n    # strengthen ssl security\n    ssl_certificate /etc/letsencrypt/live/<domain>/fullchain.pem;\n    ssl_certificate_key /etc/letsencrypt/live/<domain>/privkey.pem;\n    ssl_protocols TLSv1 TLSv1.1 TLSv1.2;\n    ssl_prefer_server_ciphers on;\n    ssl_session_cache shared:SSL:10m;\n    ssl_ciphers \"EECDH+AESGCM:EDH+AESGCM:ECDHE-RSA-AES128-GCM-SHA256:AES256+EECDH:DHE-RSA-AES128-GCM-SHA256:AES256+EDH:ECDHE-RSA-AES256-GCM-SHA384:DHE-RSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES128-SHA256:ECDHE-RSA-AES256-SHA:ECDHE-RSA-AES128-SHA:DHE-RSA-AES256-SHA256:DHE-RSA-AES128-SHA256:DHE-RSA-AES256-SHA:DHE-RSA-AES128-SHA:ECDHE-RSA-DES-CBC3-SHA:EDH-RSA-DES-CBC3-SHA:AES256-GCM-SHA384:AES128-GCM-SHA256:AES256-SHA256:AES128-SHA256:AES256-SHA:AES128-SHA:DES-CBC3-SHA:HIGH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4\";\n    \n    # See the link below for more SSL information:\n    #     https://raymii.org/s/tutorials/Strong_SSL_Security_On_nginx.html\n    #\n    # ssl_dhparam /etc/ssl/certs/dhparam.pem;\n\n    # Add headers to serve security related headers\n    add_header Strict-Transport-Security \"max-age=15768000; preload;\";\n    add_header X-Content-Type-Options nosniff;\n    add_header X-XSS-Protection \"1; mode=block\";\n    add_header X-Robots-Tag none;\n    add_header Content-Security-Policy \"frame-ancestors 'self'\";\n\n    location / {\n        try_files $uri $uri/ /index.php?$query_string;\n    }\n\n    location ~ \\.php$ {\n        fastcgi_split_path_info ^(.+\\.php)(/.+)$;\n        fastcgi_pass 127.0.0.1:9000;\n        fastcgi_index index.php;\n        include fastcgi_params;\n        fastcgi_param PHP_VALUE \"upload_max_filesize = 100M \\n post_max_size=100M\";\n        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;\n        fastcgi_param HTTP_PROXY \"\";\n        fastcgi_intercept_errors off;\n        fastcgi_buffer_size 16k;\n        fastcgi_buffers 4 16k;\n        fastcgi_connect_timeout 300;\n        fastcgi_send_timeout 300;\n        fastcgi_read_timeout 300;\n        include /etc/nginx/fastcgi_params;\n    }\n\n    location ~ /\\.ht {\n        deny all;\n    }\n}"
  },
  {
    "path": ".github/docker/entrypoint.sh",
    "content": "#!/bin/ash -e\ncd /app\n\nmkdir -p /var/log/panel/logs/ /var/log/supervisord/ /var/log/nginx/ /var/log/php7/ \\\n  && chmod 777 /var/log/panel/logs/ \\\n  && ln -s /app/storage/logs/ /var/log/panel/\n\n## 检查 .env 文件并在缺少时生成应用程序密钥\nif [ -f /app/var/.env ]; then\n  echo \"存在外部变量.\"\n  rm -rf /app/.env\n  ln -s /app/var/.env /app/\nelse\n  echo \"不存在外部变量.\"\n  rm -rf /app/.env\n  touch /app/var/.env\n\n  ## 由于 key generate --force 失败，手动生成密钥\n  if [ -z $APP_KEY ]; then\n     echo -e \"生成密钥.\"\n     APP_KEY=$(cat /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 32 | head -n 1)\n     echo -e \"生成的应用程序密钥：$APP_KEY\"\n     echo -e \"APP_KEY=$APP_KEY\" > /app/var/.env\n  else\n    echo -e \"APP_KEY 存在于环境中，已使用它.\"\n    echo -e \"APP_KEY=$APP_KEY\" > /app/var/.env\n  fi\n\n  ## 如果未提供，则为哈希 ID 生成随机盐值。\n  if [ -z $HASHIDS_SALT ]; then\n     echo -e \"生成哈希值盐。\"\n     HASHIDS_SALT=$(cat /dev/urandom | tr -dc 'a-zA-Z0-9!@#$%^&*()_+?><~' | fold -w 20 | head -n 1)\n     echo -e \"生成的哈希值盐: $HASHIDS_SALT\"\n     echo -e \"HASHIDS_SALT=$HASHIDS_SALT\" >> /app/var/.env\n  else\n    echo -e \"使用在环境中的 HASHIDS_SALT 值。\"\n    echo -e \"HASHIDS_SALT=$HASHIDS_SALT\" >> /app/var/.env\n  fi\n\n  ln -s /app/var/.env /app/\nfi\n\necho \"正在检查是否需要 https.\"\nif [ -f /etc/nginx/http.d/panel.conf ]; then\n  echo \"nginx 配置已经就位.\"\n  if [ $LE_EMAIL ]; then\n    echo \"正在检查证书更新\"\n    certbot certonly -d $(echo $APP_URL | sed 's~http[s]*://~~g')  --standalone -m $LE_EMAIL --agree-tos -n\n  else\n    echo \"未设置 Letsencrypt 电子邮箱\"\n  fi\nelse\n  echo \"正在检查是否设置了 letsencrypt 电子邮箱.\"\n  if [ -z $LE_EMAIL ]; then\n    echo \"http 配置文件中没有设置 letencrypt 电子邮箱.\"\n    cp .github/docker/default.conf /etc/nginx/http.d/panel.conf\n  else\n    echo \"编写 ssl 配置\"\n    cp .github/docker/default_ssl.conf /etc/nginx/http.d/panel.conf\n    echo \"正在更新域名的 ssl 配置\"\n    sed -i \"s|<domain>|$(echo $APP_URL | sed 's~http[s]*://~~g')|g\" /etc/nginx/http.d/panel.conf\n    echo \"生成证书\"\n    certbot certonly -d $(echo $APP_URL | sed 's~http[s]*://~~g')  --standalone -m $LE_EMAIL --agree-tos -n\n  fi\n  echo \"删除默认的 nginx 配置\"\n  rm -rf /etc/nginx/http.d/default.conf\nfi\n\nif [[ -z $DB_PORT ]]; then\n  echo -e \"未指定 DB_PORT，默认为 3306\"\n  DB_PORT=3306\nfi\n\n## 检查日志文件夹权限\necho \"修复日志文件夹权限。\"\nif [ \"$(stat -c %U:%G /app/storage/logs)\" != \"nginx\" ]; then\n  echo \"修复日志文件夹权限。\"\n  chown -R nginx: /app/storage/logs/\nfi\n\n## 在启动面板之前检查数据库\necho \"正在检查数据库状态。\"\nuntil nc -z -v -w30 $DB_HOST $DB_PORT\ndo\n  echo \"正在等待数据库连接...\"\n  # 等待 1 秒再检查\n  sleep 1\ndone\n\n## 确保数据库已设置\necho -e \"迁移或生成数据库\"\nphp artisan migrate --seed --force\n\n## 启动队列的 cronjobs\necho -e \"正在启动 cron 作业.\"\ncrond -L /var/log/crond -l 5\n\necho -e \"正在启动 supervisord.\"\nexec \"$@\"\n"
  },
  {
    "path": ".github/docker/supervisord.conf",
    "content": "[unix_http_server]\nfile=/tmp/supervisor.sock                       ; path to your socket file\n\n[supervisord]\nlogfile=/var/log/supervisord/supervisord.log    ; supervisord log file\nlogfile_maxbytes=50MB                           ; maximum size of logfile before rotation\nlogfile_backups=2                               ; number of backed up logfiles\nloglevel=error                                  ; info, debug, warn, trace\npidfile=/var/run/supervisord.pid                ; pidfile location\nnodaemon=false                                  ; run supervisord as a daemon\nminfds=1024                                     ; number of startup file descriptors\nminprocs=200                                    ; number of process descriptors\nuser=root                                       ; default user\nchildlogdir=/var/log/supervisord/               ; where child log files will live\n\n[rpcinterface:supervisor]\nsupervisor.rpcinterface_factory = supervisor.rpcinterface:make_main_rpcinterface\n\n[supervisorctl]\nserverurl=unix:///tmp/supervisor.sock         ; use a unix:// URL  for a unix socket\n\n[program:php-fpm]\ncommand=/usr/local/sbin/php-fpm -F\nautostart=true\nautorestart=true\n\n[program:queue-worker]\ncommand=/usr/local/bin/php /app/artisan queue:work --queue=high,standard,low --sleep=3 --tries=3\nuser=nginx\nautostart=true\nautorestart=true\n\n[program:nginx]\ncommand=/usr/sbin/nginx -g 'daemon off;'\nautostart=true\nautorestart=true\npriority=10\nstdout_events_enabled=true\nstderr_events_enabled=true"
  },
  {
    "path": ".github/docker/www.conf",
    "content": "[www]\n\nuser = nginx\ngroup = nginx\n\nlisten = 127.0.0.1:9000\nlisten.owner = nginx\nlisten.group = nginx\nlisten.mode = 0750\n\npm = ondemand\npm.max_children = 9\npm.process_idle_timeout = 10s\npm.max_requests = 200\n\nclear_env = no"
  },
  {
    "path": ".github/workflows/build.yaml",
    "content": "name: Build\n\non:\n  push:\n    branches:\n      - 1.0-develop\n  pull_request:\n    branches:\n      - \"1.0-develop\"\n\njobs:\n  ui:\n    name: UI\n    runs-on: ubuntu-24.04\n    permissions:\n      contents: read\n    strategy:\n      fail-fast: false\n      matrix:\n        node-version: [ 22 ]\n    steps:\n      - name: Code Checkout\n        uses: actions/checkout@v4\n\n      - name: Setup Node\n        uses: actions/setup-node@v4\n        with:\n          node-version: ${{ matrix.node-version }}\n          cache: yarn\n\n      - name: Install dependencies\n        run: yarn install --frozen-lockfile\n      - run: yarn tsc\n      - run: yarn lint\n      - run: yarn build:production\n"
  },
  {
    "path": ".github/workflows/ci.yaml",
    "content": "name: Tests\n\non:\n  push:\n    branches:\n      - 1.0-develop\n  pull_request:\n    branches:\n      - \"1.0-develop\"\n\njobs:\n  tests:\n    name: Tests\n    runs-on: ubuntu-24.04\n    permissions:\n      contents: read\n    strategy:\n      fail-fast: false\n      matrix:\n        php:\n          - 8.2\n          - 8.3\n        database:\n          - mariadb:10\n          - mariadb:11\n          - mysql:8\n          - mysql:9\n    services:\n      database:\n        image: ${{ matrix.database }}\n        env:\n          MYSQL_ALLOW_EMPTY_PASSWORD: yes\n          MYSQL_DATABASE: testing\n        ports:\n          - 3306\n    steps:\n      - uses: actions/checkout@v4\n      - id: composer-cache\n        run: |\n          echo \"dir=$(composer config cache-files-dir)\" >> $GITHUB_OUTPUT\n      - uses: actions/cache@v4\n        with:\n          path: ${{ steps.composer-cache.outputs.dir }}\n          key: ${{ runner.os }}-composer-${{ matrix.php }}-${{ hashFiles('**/composer.lock') }}\n          restore-keys: |\n            ${{ runner.os }}-composer-${{ matrix.php }}-\n      - uses: shivammathur/setup-php@v2\n        with:\n          php-version: ${{ matrix.php }}\n          extensions: bcmath, cli, curl, gd, mbstring, mysql, openssl, pdo, tokenizer, xml, zip\n          tools: composer:v2\n          coverage: none\n      - run: cp .env.ci .env\n      - run: composer install --no-interaction --no-progress --no-suggest --prefer-dist\n      - run: vendor/bin/php-cs-fixer fix --dry-run --diff\n      - run: vendor/bin/phpunit --bootstrap vendor/autoload.php tests/Unit\n        env:\n          DB_HOST: UNIT_NO_DB\n      - run: vendor/bin/phpunit tests/Integration\n        env:\n          DB_PORT: ${{ job.services.database.ports[3306] }}\n          DB_USERNAME: root\n"
  },
  {
    "path": ".github/workflows/docker.yaml",
    "content": "name: Docker\n\non:\n  push:\n    branches:\n      - 1.0-develop\n  release:\n    types:\n      - published\n\njobs:\n  push:\n    name: Push\n    runs-on: ubuntu-24.04\n    if: \"!contains(github.event.head_commit.message, 'skip docker') && !contains(github.event.head_commit.message, 'docker skip')\"\n    permissions:\n      contents: read\n      packages: write\n    steps:\n      - name: Code checkout\n        uses: actions/checkout@v4\n\n      - name: Docker metadata (multi-registry)\n        id: docker_meta\n        uses: docker/metadata-action@v5\n        with:\n          images: |\n            ghcr.io/pterodactyl-china/panel\n            pterodactylchina/panel\n            ${{ secrets.ALIYUN_ACR_REGISTRY }}/pterodactyl-china/panel\n          flavor: |\n            latest=false\n          tags: |\n            type=raw,value=latest,enable=${{ github.event_name == 'release' && github.event.action == 'published' && github.event.release.prerelease == false }}\n            type=ref,event=tag\n            type=ref,event=branch\n\n      - name: Setup QEMU\n        uses: docker/setup-qemu-action@v3\n\n      - name: Setup Docker buildx\n        uses: docker/setup-buildx-action@v3\n\n      # 登录 GHCR\n      - name: Login to GitHub Container Registry\n        if: github.event_name != 'pull_request'\n        uses: docker/login-action@v3\n        with:\n          registry: ghcr.io\n          username: ${{ github.repository_owner }}\n          password: ${{ secrets.GITHUB_TOKEN }}\n\n      # 登录 Docker Hub\n      - name: Login to Docker Hub\n        if: github.event_name != 'pull_request'\n        uses: docker/login-action@v3\n        with:\n          username: ${{ secrets.DOCKERHUB_USERNAME }}\n          password: ${{ secrets.DOCKERHUB_TOKEN }}\n\n      # 登录阿里云 ACR\n      - name: Login to Aliyun ACR\n        if: github.event_name != 'pull_request'\n        uses: docker/login-action@v3\n        with:\n          registry: ${{ secrets.ALIYUN_ACR_REGISTRY }}  # e.g., registry.cn-hangzhou.aliyuncs.com\n          username: ${{ secrets.ALIYUN_ACR_ACCESS_KEY_ID }}\n          password: ${{ secrets.ALIYUN_ACR_ACCESS_KEY_SECRET }}\n\n      - name: Update version\n        if: \"github.event_name == 'release' && github.event.action == 'published'\"\n        env:\n          REF: ${{ github.event.release.tag_name }}\n        run: |\n          sed -i \"s/    'version' => 'canary',/    'version' => '${REF:1}',/\" config/app.php\n\n      - name: Build and Push to all registries\n        uses: docker/build-push-action@v6\n        with:\n          context: .\n          file: ./Dockerfile\n          push: ${{ github.event_name != 'pull_request' }}\n          platforms: linux/amd64,linux/arm64\n          labels: ${{ steps.docker_meta.outputs.labels }}\n          tags: ${{ steps.docker_meta.outputs.tags }}\n          cache-from: type=gha\n          cache-to: type=gha,mode=max\n"
  },
  {
    "path": ".github/workflows/release.yaml",
    "content": "name: Release\non:\n  push:\n    tags:\n      - \"v*\"\njobs:\n  release:\n    name: Release\n    runs-on: ubuntu-latest\n    permissions:\n      contents: write\n    steps:\n      - uses: actions/checkout@v4\n      - uses: actions/setup-node@v4\n        with:\n          node-version: 22\n          cache: yarn\n      - run: yarn install --frozen-lockfile\n      - run: yarn tsc\n      - run: yarn build:production\n      - name: create release branch and bump version\n        env:\n          VERSION: ${{ github.ref_name }}\n        run: |\n          BRANCH=release/${{ env.VERSION }}\n          git config --local user.email 'ci@pterodactyl.io'\n          git config --local user.name 'Pterodactyl CI'\n          git checkout -b \"$BRANCH\"\n          git push -u origin \"$BRANCH\"\n          sed -i \"s/'canary'/'${VERSION:1}'/\" config/app.php\n          git add config/app.php\n          git commit -m 'ci(release): bump version'\n          git push\n      - name: create release archive\n        run: |\n          rm -rf node_modules tests CONTRIBUTING.md flake.lock flake.nix phpunit.xml shell.nix\n          tar -czf panel.tar.gz * .editorconfig .env.example .eslintignore .eslintrc.js .gitignore .prettierrc.json\n      - name: write changelog\n        run: |\n          sed -n \"/^## ${{ github.ref_name }}/,/^## /{/^## /b;p}\" CHANGELOG.md > ./RELEASE_CHANGELOG\n      - uses: softprops/action-gh-release@a06a81a03ee405af7f2048a818ed3f03bbf83c7b\n        env:\n          GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}\n        with:\n          draft: true\n          prerelease: ${{ contains(github.ref_name, 'rc') || contains(github.ref_name, 'beta') || contains(github.ref_name, 'alpha') }}\n          body_path: ./RELEASE_CHANGELOG\n          files: |\n            panel.tar.gz\n"
  },
  {
    "path": ".gitignore",
    "content": "/vendor\n*.DS_Store*\n!.env.ci\n!.env.example\n.env*\n.vagrant/*\n.vscode/*\nstorage/framework/*\n/.idea\n/nbproject\n/.direnv\n\nnode_modules\n*.log\n_ide_helper.php\n_ide_helper_models.php\n.phpstorm.meta.php\n.yarn\npublic/assets/manifest.json\n\n# For local development with docker\n# Remove if we ever put the Dockerfile in the repo\n.dockerignore\ndocker-compose.*\n!docker-compose.example.yml\n!docker-compose.example.yaml\n\n# for image related files\nmisc\n.php-cs-fixer.cache\ncoverage.xml\nresources/lang/locales.js\n.phpunit.result.cache\n\n/public/build\n/public/hot\nresult\n"
  },
  {
    "path": ".php-cs-fixer.dist.php",
    "content": "<?php\n\nuse PhpCsFixer\\Config;\nuse PhpCsFixer\\Finder;\nuse PhpCsFixer\\Runner\\Parallel\\ParallelConfigFactory;\n\n$finder = (new Finder())\n    ->name('*.php')\n    ->ignoreVCSIgnored(true)\n    ->exclude([__DIR__ . '/bootstrap/cache'])\n    ->in([\n        __DIR__ . '/app',\n        __DIR__ . '/bootstrap',\n        __DIR__ . '/config',\n        __DIR__ . '/database',\n        __DIR__ . '/routes',\n        __DIR__ . '/tests',\n    ]);\n\nreturn (new Config())\n    ->setFinder($finder)\n    ->setUsingCache(true)\n    ->setParallelConfig(ParallelConfigFactory::detect())\n    ->setRules([\n        '@Symfony' => true,\n        '@PSR1' => true,\n        '@PSR2' => true,\n        '@PSR12' => true,\n        'align_multiline_comment' => ['comment_type' => 'phpdocs_like'],\n        'combine_consecutive_unsets' => true,\n        'concat_space' => ['spacing' => 'one'],\n        'heredoc_to_nowdoc' => true,\n        // 'no_alias_functions' => true,\n        // 'no_unreachable_default_argument_value' => true,\n        'no_useless_return' => true,\n        'ordered_imports' => [\n            'sort_algorithm' => 'length',\n        ],\n        'phpdoc_align' => [\n            'align' => 'left',\n            'tags' => [\n                'param',\n                'property',\n                'return',\n                'throws',\n                'type',\n                'var',\n            ],\n        ],\n        'phpdoc_no_alias_tag' => false,\n        // 'random_api_migration' => true,\n        'ternary_to_null_coalescing' => true,\n        'yoda_style' => [\n            'equal' => false,\n            'identical' => false,\n            'less_and_greater' => false,\n        ],\n    ]);\n"
  },
  {
    "path": ".prettierrc.json",
    "content": "{\n\t\"printWidth\": 120,\n\t\"tabWidth\": 4,\n\t\"useTabs\": false,\n\t\"semi\": true,\n\t\"singleQuote\": true,\n\t\"jsxSingleQuote\": true,\n\t\"endOfLine\": \"lf\"\n}\n"
  },
  {
    "path": "BUILDING.md",
    "content": "# 本地开发\n翼龙现在由React、Typescript和Tailwindcss驱动，其核心是使用webpack来生成编译资源。\n翼龙的发布版本将包括预编译、压缩和哈希的资源，你可以随时使用。\n\n然而，如果你有兴趣运行自定义主题或对React文件进行修改，你将需要一个构建系统来生成这些编译资源。要设置好你的环境，你至少需要。\n\n* [Node.js](https://nodejs.org/en/) v14.x.x\n* [Yarn](https://classic.yarnpkg.com/lang/en/) v1.x.x\n* [Go](https://golang.org/) 1.17.x\n\n### 安装依赖项\n```bash\nyarn install\n```\n\n上面的命令将下载所有必要的依赖，以使翼龙资源构建。在这之后，它就像运行下面的命令一样简单，在你开发时生成资源。在你运行这个命令至少一次之前，你可能会在面板上看到一个500错误，即缺少`manifest.json`文件。这是由下面的命令生成的。\n\n```bash\n# 构建用于开发的编译资源集。\nyarn run build\n\n# 当资源被改变时自动构建。这使你可以刷新页面并立即看到变化。\nyarn run watch\n```\n\n### 模块热加载\n对于更高级的用户，我们还支持 '模块热重载'，让你快速查看你对 Vue 模板文件所做的修改，而不必重新加载你所在的页面。要使用它你只需要运行下面的命令。\n\n```bash\nPUBLIC_PATH=http://192.168.1.1:8080 yarn run serve --host 192.168.1.1\n```\n\n这个命令有两个非常重要的部分需要注意，并根据你的具体环境进行修改。第一个是 `--host` 参数，这是必须的，应该指向服务器将运行 `webpack-serve` 的机器。\n第二个是 `PUBLIC_PATH` 环境变量，它是指向 HMR 服务器的 URL，并被附加到翼龙中使用的所有资源 URL 上。\n\n#### 开发环境\n如果你使用 [`pterodactyl-china/development`](https://github.com/pterodactyl-china/development) 环境，强烈推荐你可以直接运行 `yarn run serve` 来运行 HMR 服务器，它不需要额外配置。\n\n### 为生产环境构建\n一旦你有了你的文件，并准备好上线服务器，你将需要生成预编译、压缩和哈希的资源来推送上线。要做到这一点，请运行下面的命令。\n\n```bash\nyarn run build:production\n```\n\n这将生成一个生产 JS 包和相关资源，都位于 `public/assets/` 中，需要上传到你的服务器或CDN供客户使用。\n\n### 运行 Wings\n要在开发中运行 `wings`，你需要做的就是在添加新节点时正常设置配置文件，然后你可以通过在 Wings 代码目录中执行 `make debug` 来构建和运行本地版本的 Wings。这必须在某些 Linux 虚拟机上运行，你不能在 MacOS 或 Windows 上本地运行。\n"
  },
  {
    "path": "CHANGELOG.md",
    "content": "# Changelog\nThis file is a running track of new features and fixes to each version of the panel released starting with `v0.4.0`.\n\nThis project follows [Semantic Versioning](http://semver.org) guidelines.\n\n## v1.12.2\n### Fixed\n* Fixes task execution jobs to correctly dispatch the next job in the chain.\n* Fixes dropdown menu not appearing correctly inside modal when transferring a server.\n* Fixes startup variables logging as changed in the activity log even when no change was actually made.\n* Fixes multiple issues with the docker image.\n* Fixes server transfers getting stuck due to incorrect permission checks in the API.\n\n## v1.12.1\n### Fixed\n* [CVE-2026-26016](https://github.com/pterodactyl/panel/security/advisories/GHSA-g7vw-f8p5-c728)\n* [GHSA-hr7j-63v7-vj7g](https://github.com/pterodactyl/panel/security/advisories/GHSA-hr7j-63v7-vj7g)\n* Fixes bug where presigned URLs would \n* Fixes issue where certain input values would cause the activity log screen to stop rendering properly due to improper element encoding.\n* Fixes improper display of unicode characters in console output.\n* Fixes page number not resetting when toggling between \"Show My Servers\" and \"Show All Servers\" on the dashboard.\n\n### Changed\n* SFTP sessions are now revoked on nodes when a user changes their password or their account is deleted.\n* Remote node access tokens are now scoped to only allow access to servers that belong to the same node. Previously a node could access information and control the installation status for any server in the system.\n* The default rate limit for the client API was bumped from `128` to `256` requests per minute.\n\n### Added\n* HTTP responses now include default security headers if not otherwise set.\n* Adds modal popup when running a Hytale server that requires additional auth.\n* Adds support for administrators to view any application API key that has been created, regardless of the owning account.\n\n## v1.12.0\n### Fixed\n\n* [CVE-2025-68954](https://github.com/pterodactyl/panel/security/advisories/GHSA-8c39-xppg-479c)\n* [CVE-2025-69197](https://github.com/pterodactyl/panel/security/advisories/GHSA-rgmp-4873-r683)\n* [CVE-2025-69198](https://github.com/pterodactyl/panel/security/advisories/GHSA-jw2v-cq5x-q68g)\n* Fixes a self-XSS issue when entering random data into boxes while creating a new database host.\n* Fixes missing `HttpForbiddenException` import in the backup status controller.\n* Fixes issue where scheduled tasks would execute every minute regardless of their configured cron syntax.\n* Pressing `Ctrl+Z` to undo while editing a file no longer deletes the initial file content.\n* Fixed incorrect error message being returned when attempting to delete your own account as an admin.\n* Fixes node description not being settable via the API.\n* Fixes 0-bytes files returning an error when attempting to upload.\n* Fixes nodes displaying the first available location even when that field was not edited and the node has a different value set.\n* Fixes allocation notes not being reset when a server is deleted. ([#5157](https://github.com/pterodactyl/panel/pull/5157))\n\n### Changed\n* Minimum NodeJS version updated to 22 for building.\n* Updated all JS and PHP dependencies to their latest versions (where feasible).\n* The endpoint for disabling 2FA on an account using the client API changed from `DELETE /api/client/account/two-factor` to `POST /api/client/account/two-factor/disable`\n* `^C` in an egg's stop configuration no longer rewrites itself into the default stop configuration.\n* `IBM Plex Sans` font is now bundled with the local assets instead of loading from Google CDNs.\n* Upload size on nodes is no longer restricted to a max of 1024MB, any positive integer value can be used.\n* Administrators are now listed first when viewing a list of all users on the system.\n* Websocket no longer endlessly polls when connection issues are encountered, or when Wings disconnects the user for a reason that should not be re-attempted.\n\n## v1.11.10\n### Fixed\n* Update Laravel to address [CVE-2024-52301](https://github.com/advisories/GHSA-gv7v-rgg6-548h)\n\n### Changed\n* Minimum PHP version is now 8.2 due to Laravel upgrade!\n\n## v1.11.9\n### Fixed\n* Fixed issue with CI not pushing Docker image\n\n## v1.11.8\n### Fixed\n* Fixed an issue where a `DELETE` request was used instead of a `POST`, potentially logging user passwords in plain text if they disable 2FA.\n\n## v1.11.7\n### Added\n* Java 21 to Minecraft eggs\n\n### Changed\n* Updated Minecraft EULA link\n\n### Fixed\n* Fixed backups not ever being marked as completed (#5088)\n* Fixed `.7z` files not being detected as a compressed file (#5016)\n\n## v1.11.6\n### Changed\n* Better node ownership checks for internal backup endpoints\n* Improved validation rules on `docker_image` fields to prevent invalid inputs\n\n### Fixed\n* Multiple XSS vulnerabilities in the admin area ([GHSA-384w-wffr-x63q](https://github.com/pterodactyl/panel/security/advisories/GHSA-384w-wffr-x63q))\n\n## v1.11.5\n### Fixed\n* Rust egg using the wrong Docker image, breaking Rust modding frameworks.\n\n## v1.11.4\n### Added\n* Added support for the `server.queryport` option on the Rust egg.\n* Added support for the Carbon modding framework to the Rust egg.\n\n### Changed\n* Upgraded to Laravel 10.\n* Sensitive data is no longer shown in the CopyOnClick toast notification.\n\n### Fixed\n* Allow SVGs to be edited in the server's file manager.\n* Properly validate the request body when creating a backup.\n* Fixed issue with schedules running at the wrong time when the panel utilized a timezone with non-hour offsets (such as `Australia/Darwin`).\n* Fixes the log directory when running the Panel in a container.\n* Fixes the permission name used to check if a user has permission to read files/folders.\n* Fixes the ability to unset a server's description through the client API.\n* Fixed the MassActionBar on the server's file manager blocking elements below it, preventing them from being interacted with.\n\n## v1.11.3\n### Changed\n* When updating a server's description through the client API, if no value is specified, the description will now remain unchanged.\n* When installing the Panel for the first time, the queue driver will now all default to `redis` instead of `sync`.\n\n### Fixed\n* `php artisan p:environment:mail` not correctly setting the right variable for `MAIL_FROM_ADDRESS`.\n* Fixed the conflict state rendering on the UI for a server showing `reinstall_failed` as `restoring_backup`.\n* Fixed the unknown column `uuid` error when jobs fail, causing them not to get stored correctly.\n* Fixed the server task endpoints in the client API not allowing `sequence_id` and `continue_on_failure` to be set.\n\n## v1.11.2\n### Changed\n* Telemetry no longer sends a map of Egg and Nest UUIDs to the number of servers using them.\n* Increased the timeout for the decompress files endpoint in the client API from 15 seconds to 15 minutes.\n\n### Fixed\n* Fixed Panel Docker image having a `v` prefix in the version displayed in the admin area.\n* Fixed emails using the wrong queue name, causing them to not be sent.\n* Fixed the settings keys used for configuring SMTP settings, causing settings to not save properly.\n* Fixed the `MAIL_EHLO_DOMAIN` environment variable not being properly backwards compatible with the old `SERVER_NAME` variable.\n\n## v1.11.1\n### Fixed\n* Fixed Panel Docker image showing `canary` as it's version.\n\n## v1.11.0\n### Changed (since 1.10.4)\n* Changed minimum PHP version requirement from `7.4` to `8.0`.\n* Upgraded from Laravel 8 to Laravel 9.\n* This release requires Wings v1.11.x in order for Server Transfers to work.\n* `MB` byte suffixes are now displayed as `MiB` to more accurately reflect the actual value.\n* Server re-installation failures are tracked independently of the initial installation process.\n\n### Fixed (since 1.10.4)\n* Node maintenance mode now properly blocks access to servers.\n* Fixed the length validation on the Minecraft Forge egg.\n* Fixed the password in the JDBC string not being properly URL encoded.\n* Fixed an issue where Wings would throw a validation error while attempting to upload activity logs.\n* Properly handle a missing `Content-Length` header in the response from the daemon.\n* Ensure activity log properties are always returned as an object instead of an empty array.\n\n### Added (since 1.10.4)\n* Added the `server:settings.description` activity log event for when a server description is changed.\n* Added the ability to cancel file uploads in the file manager for a server.\n* Added a telemetry service to collect anonymous metrics from the panel, this feature is *enabled* by default and can be toggled using the `PTERODACTYL_TELEMETRY_ENABLED` environment variable.\n\n## v1.11.0-rc.2\n### Changed\n* `MB` byte suffixes are now displayed as `MiB` to more accurately reflect the actual value.\n* Server re-installation failures are tracked independently of the initial installation process.\n\n### Fixed\n* Properly handle a missing `Content-Length` header in the response from the daemon.\n* Ensure activity log properties are always returned as an object instead of an empty array.\n\n### Added\n* Added the `server:settings.description` activity log event for when a server description is changed.\n* Added the ability to cancel file uploads in the file manager for a server.\n* Added a telemetry service to collect anonymous metrics from the panel, this feature is disabled by default and can be toggled using the `PTERODACTYL_TELEMETRY_ENABLED` environment variable.\n\n## v1.11.0-rc.1\n### Changed\n* Changed minimum PHP version requirement from `7.4` to `8.0`.\n* Upgraded from Laravel 8 to Laravel 9.\n* This release requires Wings v1.11.x in order for Server Transfers to work.\n\n### Fixed\n* Node maintenance mode now properly blocks access to servers.\n* Fixed the length validation on the Minecraft Forge egg.\n* Fixed the password in the JDBC string not being properly URL encoded.\n* Fixed an issue where Wings would throw a validation error while attempting to upload activity logs.\n\n## v1.10.4\n### Fixed\n* Fixed an issue where subusers could be given permissions that are not actually registered or used.\n* Fixed an issue where node FQDNs could not just be IP addresses.\n\n### Changed\n* Change maximum number of API keys per user from `10` to `25`.\n* Change byte unit prefix from `B` to `iB` to better reflect our usage of base 2 (multiples of 1024).\n\n## v1.10.3\n### Fixed\n* S3 Backup driver now supports Cloudflare R2.\n* Node FQDNs can now be used with AAAA records with no A records present.\n* Server transfers can no longer be initiated if the server is being installed, transferred, or restoring a backup.\n* Fixed an issue relating to the use of arrays in the `config_files` field with eggs.\n* Fixed `oom_disabled` not being mapped in the Application API when creating a new server.\n\n### Added\n* File manager now supports selecting multiple files for upload (when using the upload button).\n* Added a configuration option for specifying the S3 storage class for backups.\n\n### Changed\n* Servers will now show the current uptime when the server is starting rather than only showing when the server is marked as online.\n\n## v1.10.2\n### Fixed\n* Fixes a rendering issue with egg descriptions in the admin area\n* Fixes the page title on the SSH Keys page\n\n### Changed\n* Additional validation rules will now show a toggle switch rather than an input when editing server variables\n* The eggs endpoint will now always return an empty JSON object for the `config_files` field, even if the field is completely empty\n\n### Added\n* Adds a `Force Outgoing IP` option for eggs that can be used to ensure servers making outgoing connections use their allocation IP rather than the node's primary ip\n* Adds options to configure sending of email (re)install notifications\n* Add an option to configure the part size for backups uploaded to S3\n\n## v1.10.1\n### 修复\n* 修复了一个 `clock()` 函数，该函数用于调试并且不应该进入发行版。这导致面板和 Wings 之间的活动事件无法正确同步。\n\n## v1.10.0\n### 修复\n* 修复了前端缓存键命名不当导致服务器活动日志在服务器页面视图中重复的问题。\n* 修复了内部内容过长时对话框的溢出问题。\n* 修复了控制台上的微调器覆盖不正确地占用整个页面，从而无法使用导航控件。\n* 修复了动态口令认证的二维码背景太暗导致某些手机无法正确扫描的问题。\n* 如果用户尝试上传文件夹而不是文件，文件管理器现在会正确显示错误消息。\n* 修复了“创建目录”对话框在重新打开时会保留先前输入的值。\n\n### 更新\n* 现在，无论管理员是否拥有服务器，活动日志中的 IP 地址都会始终显示给管理员。\n* 控制台上的向下滚动指示器已更改为向下箭头，以便更清晰。\n* Docker 构建已更新为使用 `PHP 8.1`。\n* Recaptcha 验证域现在可以使用 `RECAPTCHA_DOMAIN` 环境变量进行配置（默认域中国可用）。\n* 文件管理器上的拖放覆盖已经过调整，使其与前端样式更加一致，并且更易于阅读。\n\n### 新增\n* 在所有生成的 JWT 上添加对 `user_uuid` 声明支持，这允许 Wings 正确识别执行每个操作的用户。\n* 添加了对从 Wings 实例接收外部活动日志事件（电源状态、命令、SFTP 和上传）的支持。\n* 添加了对跟踪基于密码的 SFTP 登录失败的日志支持。\n* 服务器名称和描述现在传递给 Wings，使它们可以在预设变量中进行解析和包含。\n* 添加了对在文件管理器中显示所有活动文件上传的支持。\n\n## v1.9.2\n### 修复\n* 修复了图表侧边栏里的 CPU 使用率中渲染过多的零导致的问题。\n* 修复了 Java 版本选择器模式，最初选择了错误的默认值。\n* 修复了 Safari 中的控制台渲染导致控制台过度调整大小和图形覆盖内容。\n* 修复服务器正常运行时间块中缺少 \"正在启动\" / \"停止中\" 的状态显示。\n* 修复查看某些文件操作时活动日志格式不正确的问题。\n\n### 调整\n* 更新了帐户动态口令认证授权设置的 UI，以使用新的对话框 UI，并为新用户提供更好更容易理解。\n\n### 新增\n* 在模板输出中添加了缺少的 `<DOCTYPE html>` 标签，以避免在浏览器中进入怪异模式。\n* 在账户上启用 TOTP 时添加密码要求。\n----\n### Fixed\n* Fixes rouding in sidebar of CPU usage graph that was causing an excessive number of zeros to be rendered.\n* Fixes the Java Version selector modal having the wrong default value selected initially.\n* Fixes console rendering in Safari that was causing the console to resize excessively and graphs to overlay content.\n* Fixes missing \"Starting\"/\"Stopping\" status display in the server uptime block.\n* Fixes incorrect formatting of activity log when viewing certain file actions.\n\n### Changed\n* Updated the UI for the two-step authorization setup on accounts to use new Dialog UI and provide better clarity to new users.\n\n### Added\n* Added missing `<DOCTYPE html>` tag to template output to avoid entering quirks mode in browsers.\n* Added password requirement when enabling TOTP on an account.\n\n## v1.9.1\n### Fixed\n* Fixes missing \"Click to Copy\" for server address on the console data blocks.\n* Fixes data points on the graphs not being properly rounded to two decimal places.\n* Returns byte formatting logic to use `1024` as the base value, rather than `1000`.\n* Fixes permission error occurring when a server is marked as installing and an admin navigates to the console screen.\n* Fixes improper display of install/transfer warning on the server console page.\n* Fixes permission matching for the server settings page to correctly allow access when a user has _any_ of the needed permissions.\n\n### Changed\n* Moves the server data blocks to the right-hand side of the console, rather than the left.\n* Rather than defaulting graph values at `0` when resetting or refreshing the page, their values are now hidden entirely.\n* **[security]** Hides IP addresses from all activity log entries that are not directly associated with the currently signed in user.\n\n### Added\n* Adds the current resource limits for a server next to each data block on the console screen.\n\n## v1.9.0\n### Added\n* Added support for using Tailwind classes inside components using `className={}` rather than having to use `twin.macro` with the `css={}` prop.\n* Added HeadlessUI and Heroicons packages.\n* Added new `Tooltip.tsx` component to support displaying tooltips within the Panel.\n* Adds a new activity log view for both user accounts and individual servers. This builds upon data collected in previous releases.\n* Added a new column `api_key_id` to the `activity_logs` table to indicate if the user performed the action while using an API key.\n* Adds initial support for language translations on the front-end. The underlying implementation details are working, however work has not yet begun on actually translating all of the strings yet. Expect this to continue in future releases.\n* Improved accessibility for navigation icons by adding a tooltip on hover to indicate what each one does.\n* Adds logging for API keys that are blocked from performing an API action due to IP address limiting.\n* Adds support for `?filter[description]=foo` when querying servers on both the client and application API.\n\n### Changed\n* Updated how release assets are generated to perform more logical bundle splitting. This should help reduce the amount of data users have to download at once in order to render the UI.\n* Upgraded From TailwindCSS 2 to 3 — for most people this should have minimal if any impact.\n* Chart.js updated from v2 to v3.\n* Reduced the number of custom colors in use — by default we now use Tailwind's default color pallet, with the exception of a custom gray scheme.\n* **[deprecated]** The use of `neutral` and `primary` have been deprecated in class names, prefer `gray` and `blue` respectively.\n* Begins the process of dropping the use of Gravatars for user avatars and replaces them with dynamically generated SVG images.\n* Improved front-end route definitions to make it easier for external modifications to inject their routes and components into the codebase without having to modify as many core files.\n* Redesigned the server console screen to better display data users might be looking for, and increase the height of the console itself.\n* Merged the two network data graphs into a single dual-line graph to better display incoming and outgoing data volumes.\n* Updated all byte formatting logic to use `1000` as the divisor rather than `1024` to be more consistent with what users most likely expect.\n* Changed the underlying `eslint` rules applied to the front-end codebase to simplify them dramatically. We now utilize `prettier` in combination with some basic default rulesets to make it easier to understand the expected formatting.\n\n### Fixed\n* Fixes a bug causing a 404 error when attempting to delete a database from a server in the admin control panel.\n* Fixes console input auto-capitalizing and auto-correcting when entering text on some mobile devices.\n* Fixes SES service configuration using a hard-coded `us-east-1` region.\n* Fixes a bug causing a 404 error when attempting to delete an SSH key from your account when the SHA256 hash includes a slash.\n* Fixes mobile keyboards automatically attempting to capitalize and spellcheck typing on the server console.\n* Fixes improper support for IP address CIDR ranges when creating API keys for the client area.\n* Fixes a bug preventing additional included details from being returned from the application API when utilizing a client API key as an administrator.\n\n## v1.8.1\n### Fixed\n* Fixes a bug causing mounts to return a 404 error when adding them to a server.\n* Fixes a bug causing the Egg Image dropdown to not display properly when creating a new server.\n* Fixes a bug causing an error when attemping to create a new server via the API.\n\n## v1.8.0\n**Important:** this version updates the `version` field on generated Eggs to be `PTDL_v2` due to formatting changes. This\nshould be completely seamless for most installations as the Panel is able to convert between the two. Custom solutions\nusing these eggs should be updated to account for the new format.\n\nThis release also changes API key behavior — \"client\" keys belonging to admin users can now be used to access\nthe `/api/application` endpoints in their entirety. Existing \"application\" keys generated in the admin area should\nbe considered deprecated, but will continue to work. Application keys _will not_ work with the client API.\n\n### Fixed\n* Schedules are no longer run when a server is suspended or marked as installing.\n* The remote field when creating a database is no longer limited to an IP address and `%` wildcard — all expected MySQL remote host values are allowed.\n* Allocations cannot be deleted from a server by a user if the server is configured with an `allocation_limit` set to `0`.\n* The Java Version modal no longer shows a dropdown and update option to users that do not have permission to make those changes.\n* The Java Version modal now correctly returns only the images available to the server's selected Egg.\n* Fixes leading and trailing spaces being removed from variable values on file manager endpoints, causing errors when trying to perform actions against certain files and folders.\n\n### Changed\n* Forces HTTPS on URLs when the `APP_URL` value is set and includes `https://` within the URL. This addresses proxy misconfiguration issues that would cause URLs to be generated incorrectly.\n* Lowers the default timeout values for requests to Wings instances from 10 seconds to 5 seconds.\n* Additional permissions (`CREATE TEMPORARY TABLES`, `CREATE VIEW`, `SHOW VIEW`, `EVENT`, and `TRIGGER`) are granted to users when creating new databases for servers.\n* development: removed Laravel Debugbar in favor of Clockwork for debugging.\n* The 2FA input field when logging in is now correctly identified as `one-time-password` to help browser autofill capabilities.\n* Changed API authentication mechanisms to make use of Laravel Sanctum to significantly clean up our internal handling of sessions.\n* API keys generated by the system now set a prefix to identify them as Pterodactyl API keys, and if they are client or application keys. This prefix looks like `ptlc_` for client keys, and `ptla_` for application keys. Existing API keys are unaffected by this change.\n\n### Added\n* Added support for PHP 8.1 in addition to PHP 8.0 and 7.4.\n* Adds more support for catching potential PID exhaustion errors in different games.\n* It is now possible to create a new node on the Panel using an artisan command.\n* A new cron cheatsheet has been added which appears when creating a schedule.\n* Adds support for filtering the `/api/application/nodes/:id/allocations` endpoint using `?filter[server_id]=0` to only return allocations that are not currently assigned to a server on that node.\n* Adds support for naming docker image values in an Egg to improve front-end display capabilities.\n* Adds command to return the configuration for a specific node in both YAML and JSON format (`php artisan p:node:configuration`).\n* Adds command to return a list of all nodes available on the Panel in both table and JSON format (`php artisan p:node:list`).\n* Adds server network (inbound/outbound) usage graphs to the console screen.\n* Adds support for configuring CORS on the API by setting the `APP_CORS_ALLOWED_ORIGINS=example.com,dashboard.example.com` environment variable. By default all instances are configured with this set to `*` which allows any origin.\n* Adds proper activity logging for the following areas of the Panel: authentication, user account modifications, server modification. This is an initial test implementation before further roll-out in the software. Events are logged into the database but are not currently exposed in the UI — they will be displayed in a future update.\n\n### Removed\n* Removes Google Analytics from the front end code.\n* Removes multiple middleware that were previously used for configuring API access and controlling model fetching. This has all been replaced with Laravel Sanctum and standard Laravel API tooling. This should make codebase discovery significantly more simple.\n* **DEPRECATED**: The use of `Pterodactyl\\Models\\AuditLog` is deprecated and all references to this model have been removed from the codebase. In the next major release this model and table will be fully dropped.\n\n## v1.7.0\n### Fixed\n* Fixes typo in message shown to user when deleting a database.\n* Fixes formatting of IPv6 addresses when displaying allocations to users.\n* Fixes an exception thrown while trying to return error messages from API endpoints that inproperly masked the true underlying error.\n* Fixes SSL certificate path generation for Let's Encrypt by ensuring they are always transformed to lowercase.\n* Removes duplicate entries when creating a nested folder in the file manager.\n* Fixes missing validation of Egg Author email addresses during the setup process that could cause unexpected failures later on.\n* Fixes font rendering issues of the console on Firefox due to an outdated version of xterm.js being used.\n* Fixes display overlap issues of the two-factor configuration form in a user's settings.\n* **[security]** When authenticating using an API key a user session is now only persisted for the duration of the request before being destroyed.\n\n### Changed\n* CPU graph changed to show the maximum amount of CPU available to a server to better match how the memory graph is displayed.\n\n### Added\n* Adds support for `DB_PORT` environment variable in the Docker enterpoint for the Panel image.\n* Adds suport for ARM environments in the Docker image.\n* Adds a new warning modal for Steam servers shown when an invalid Game Server Login Token (GSL Token) is detected.\n* Adds a new warning modal for Steam servers shown when the installation process runs out of available disk space.\n* Adds a new warning modal for Minecraft servers shown when a server exceeds the maximum number of child processes.\n* Adds support for displaying certain server variable fields as a checkbox when they're detected as using `boolean` or `in:0,1` validation rules.\n* Adds support for Pug and Jade in the file editor.\n* Adds an entry to the `robots.txt` file to correctly disallow all bot indexing.\n\n\n## v1.6.6\n### Fixed\n* **[security]** Fixes a CSRF vulnerability for both the administrative test email endpoint and node auto-deployment token generation endpoint. [GHSA-wwgq-9jhf-qgw6](https://github.com/pterodactyl/panel/security/advisories/GHSA-wwgq-9jhf-qgw6)\n\n### Changed\n* Updates Minecraft eggs to include latest Java 17 yolk by default.\n\n## v1.6.5\n### Fixed\n* Fixes broken application API endpoints due to changes introduced with session management in 1.6.4.\n\n## v1.6.4\n_This release should not be used, please use `1.6.5`. It has been pulled from our releases._\n\n### Fixed\n* Fixes a session management bug that would cause a user who signs out of one browser to be unintentionally logged out of other browser sessions when using the client API.\n\n## v1.6.3\n### Fixed\n* **[Security]** Changes logout endpoint to be a POST request with CSRF-token validation to prevent a malicious actor from triggering a user logout.\n* Fixes Wings receiving the wrong server suspension state when syncing servers.\n\n### Added\n* Adds additional throttling to login and password reset endpoints.\n* Adds server uptime display when viewing a server console.\n\n## v1.6.2\n### Fixed\n* **[Security]** Fixes an authentication bypass vulerability that could allow a malicious actor to login as another user in the Panel without knowing that user's email or password.\n\n## v1.6.1\n### Fixed\n* Fixes server build modifications not being properly persisted to the database when edited.\n* Correctly exposes the `oom_disabled` field in the `build` limits block for a server build so that Wings can pick it up.\n* \n## v1.6.0\n### Fixed\n* Fixes array merging logic for server transfers that would cause a 500 error to occur in some scenarios.\n* Fixes user password updates not correctly logging the user out and returning a failure message even upon successful update.\n* Fixes the count of used backups when browsing a paginated backup list for a server.\n* Fixes an error being triggered when API endpoints are called with no `User-Agent` header and an audit log is generated for the action.\n* Fixes state management on the frontend not properly resetting the loading indicator when adding subusers to a server.\n* Fixes extraneous API calls being made to Wings for the server file listing when not on a file manager screen.\n\n### Added\n* Adds foreign key relationship on the `mount_node`, `mount_server` and `egg_mount` tables.\n* Adds environment variable `PER_SCHEDULE_TASK_LIMIT` to allow manual overrides for the number of tasks that can exist on a single schedule. This is currently defaulted to `10`.\n* OOM killer can now be configured at the time of server creation.\n\n### Changed\n* Server updates are not dependent on a successful call to Wings occurring — if the API call fails internally the error will be logged but the server update will still be persisted.\n\n### Removed\n* Removed `WingsServerRepository::update()` function — if you were previously using this to modify server elements on Wings please replace calls to it with `::sync()` after updating Wings.\n\n## v1.5.1\n### Fixed\n* Fixes Docker image 404ing instead of being able to access the Panel.\n* Fixes Java version feature being only loaded when the `eula` feature is specified.\n* Fixes `php artisan p:upgrade` not forcing and seeding while running migrations.\n* Fixes spinner overlays overlapping on the server console page.\n* Fixes Wings being unable to update backup statuses.\n\n## v1.5.0\n### Fixed\n* Fixes deleting a locked backup that has also been marked as failed to allow deletion rather than returning an error about being locked.\n* Fixes server creation process not correctly sending `start_on_completion` to Wings instance.\n* Fixes `z-index` on file mass delete modal so it is displayed on top of all elements, rather than hidden under some.\n* Supports re-sending requests to the Panel API for backups that are currently marked as failed, allowing a previously failed backup to be marked as successful.\n* Minor updates to multiple default eggs for improved error handling and more accurate field-level validation.\n\n### Updated\n* Updates help text for CPU limiting when creating a new server to properly indicate virtual threads are included, rather than only physical threads.\n* Updates all of the default eggs shipped with the Panel to reference new [`ghcr.io` yolks repository](https://github.com/pterodactyl/yolks).\n* When adding 2FA to an account the key used to generate the token is now displayed to the user allowing them to manually input into their app if necessary.\n\n### Added\n* Adds SSL/TLS options for MySQL and Redis in line with most recent Laravel updates.\n* New users created for server MySQL instances will now have the correct permissions for creating foreign keys on tables.\n* Adds new automatic popup feature to allow users to quickly update their Minecraft servers to the latest Java® eggs as necessary if unsupported versions are detected.\n\n### Removed\n* Removes legacy `userInteraction` key from eggs which was unused.\n\n## v1.4.2\n### Fixed\n* Fixes logic to disallow creating a backup schedule if the server's backup limit is set to 0.\n* Fixes bug preventing a database host from being updated if the linked node is set to \"none\".\n* Fixes files and menus under the \"Mass Actions Bar\" being unclickable when it is visible.\n* Fixes issues with the Teamspeak and Mumble eggs causing installs to fail.\n* Fixes automated query to avoid pruning backups that are still running unintentionally.\n* Fixes \"Delete Server\" confirmation modal on the admin screen to actually show up when deleting rather than immediately deleting the server.\n\n### Added\n* Adds support for locking individual server backups to prevent deletion by users or automated backup processes.\n* List of files to be deleted is now shown on the delete file confirmation modal.\n* Adds support for using `IF` statements in database queries when a database user is created through the Panel.\n* Adds support for using a custom mailgun API endpoint rather than only the US based endpoint.\n* Adds CPU limit display next to the current CPU usage to match disk and memory usage reporting.\n* Adds a \"Scroll to Bottom\" helper element to the server console when not scrolled to the bottom currently.\n* Adds support for querying the API for servers by using the `uuidShort` field rather than only the `uuid` field.\n\n### Changed\n* Updates codebase to use TypeScript 4.\n* **[security]**: removes the external dependency for loading QRCode images. They're now generated directly on the frontend using JavaScript.\n\n## v1.4.1\n### Added\n* Adds support for only running a schedule if the server is currently in an online state.\n* Adds support for ignoring errors during task execution and continuing on to the next item in the sequence. For example, continuing to a server restart even if sending a command beforehand failed.\n* Adds the ability to specify the group to use for file permissions when using the `p:upgrade` command.\n* Adds the ability to manually run a schedule even if it is currently disabled.\n\n## v1.4.0\n### Fixed\n* Removes the use of tagging when storing server resource usage in the cache. This addresses errors encountered when using the `file` driver.\n* Fixes Wings response handling if Wings returns an error response with a 200-level status code that would improperly be passed back to the client as a successful request.\n* Fixes use of JSON specific functions in SQL queries to better support MariaDB users.\n* Fixes a migration that could fail on some MySQL/MariaDB setups when trying to encrypt node token values.\n\n### Changed\n* Increases the maximum length allowed for a server name using the Rust egg.\n* Updated server resource utilization API call to Wings to use new API response format used by `Wings@1.4.0`.\n\n## v1.3.2\n### Fixed\n* Fixes self-upgrade incorrectly executing the command to un-tar downloaded archives.\n* Fixes the checkbox to delete all files when restoring a backup not actually passing that along in the API call. Files will now properly be deleted when restoring if selected.\n* Fixes some keybindings not working correctly in the server console on Windows machines.\n* Fixes mobile UI incorrectly squishing the Docker image selector on the server settings page.\n* Fixes recovery tokens not having a `created_at` value set on them properly when they are created.\n* Fixes flawed migration that would not correctly set the month value into schedule crons.\n* Fixes incorrect mounting for Docker compose file that would cause error logs to be missing.\n\n### Changed\n* Server resource lookups are now cached on the Panel for 20 seconds at a time to reduce the load from multiple clients requesting the same server's stats.\n* Bungeecord egg no longer force-enables the query listener.\n* Adds page to the dashboard URL to allow easy loading of a specific pagination page rather than resetting back to the first page when refreshing.\n* All application API endpoints now correctly support the `?per_page=N` query parameter to specify how many resources to return at once.\n\n## v1.3.1\n### Fixed\n* Fixes the Rust egg not properly seeding during the upgrade & installation process.\n* Fixes backups not being downloadable via the frontend.\n* Fixes backup listing showing the wrong number of existing backups based on the current page you're on.\n\n## v1.3.0\n### Fixed\n* Fixes administrator \"Other Servers\" toggle being persisted wrongly when signing out and signing into a non-administrator account on the server dashboard.\n* Fixes composer failing to run properly in local environments where there is no database connection available once configured.\n* Fixes SQL exception caused by the Panel attempting to store null values in the database.\n* Fixes validation errors caused by improper defaults when trying to edit system settings in the admin area.\n* Fixes console overflow when using smaller-than-default font sizes in Firefox.\n* Fixes console text input field having a white background when manually building new assets from the release build due to a missing `babel-macros` definition file.\n* Fixes database improperly using a signed `smallint` field rather than an unsigned field which restricted SFTP ports to 32767 or less.\n* Fixes server console resize handler to no longer encounter an exception at random that breaks the entire UI.\n* Fixes unhandled error caused by entering an invalid IP address or FQDN when creating a new node allocation.\n* Fixes unhandled error when Wings would fetch a server configuration from the Panel that uses an Egg with invalid JSON data for the configuration fields.\n* Fixes email not being sent to a user when their server is done installing.\n\n### Added\n* Adds support for automatically copying SFTP connection details when clicking into the text field.\n* Messaging about a node not having any allocations available for deployment has been adjusted to be more understandable by users.\n* Adds automated self-upgrade process for Pterodactyl Panel once this version is installed on servers. This allows users to update by using a single command.\n* Adds support for specifying a month when creating or modifying a server schedule.\n* Adds support for restoring backups (including those in S3 buckets) to a server and optionally deleting all existing files when doing so.\n* Adds underlying support for audit logging on servers. Currently this is only used by some internal functionality but will be slowly expanded as time permits to allow more robust logging.\n* Adds logic to automatically reset failed server states when Wings is rebooted. This will kick servers out of \"installing\" and \"restoring from backup\" states automatically.\n\n### Changed\n* Updated to `Laravel 8` and bumped minimum PHP version from `7.3` to `7.4` with PHP `8.0` being the recommended.\n* Server state is now stored in a single `status` column within the database rather than multiple different `tinyint` columns.\n\n## v1.2.2\n### Fixed\n* **[security]** Fixes authentication bypass allowing a user to take control of specific server actions such as executing schedules, rotating database passwords, and viewing or deleting a backup.\n\n## v1.2.1\n### Fixed\n* Fixes URL-encoding of filenames when working in the filemanager to fix issues when moving, renaming, or deleting files.\n* Fixes URL-encoding of email addresses when requesting a password reset.\n\n### Added\n* Adds the ability for users to select a base Java Docker image for most Minecraft specific eggs shipped as defaults.\n\n## v1.2.0\n### Fixed\n* Fixes newest backup being deleted when creating a new one using the schedule tasks, rather than the oldest backup.\n* Fixes multiple encoding issues when handling file names in the manager.\n* Fixes database password not properly being copied to the clipboard when clicked.\n* Fixes failed transfers unintentionally locking a server into a failed state and not properly releasing allocations that were reserved.\n* Fixes error box on server pages having an oval refresh button rather than a perfect circle.\n* Fixes a bunch of errors and usage issues relating to backups especially when uploading to S3-based systems.\n* Fixes HMR breaking navigation in development modes on the frontend.\n\n### Changed\n* Updated Paper egg to default to Java 11 as the base docker image.\n* Removes the file mode display from the File Manager row listing.\n* Updated input UI elements to have thicker borders and more consistent highlighting when active.\n* Changed searchbar toggle from `\"k\"` to `Cmd/Ctrl + \"/\"` to avoid accidental toggles and be more consistent with other sites.\n* Upgrades TailwindCSS to `v2`.\n\n### Added\n* Adds support for eggs to define multiple Docker images that can be selected by users (e.g. Java 8 & 11 images for a single egg).\n* Adds support for configuring the default interval for failed backups to be pruned from the system to avoid long running backups being incorrectly cleared.\n* Adds server transfer output logging to the server console allowing admins to see how a transfer is progressing directly in the UI.\n* Adds client API endpoint to download a file from a remote souce. This functionality is not currently expressed in the UI.\n\n## v1.1.3\n### Fixed\n* Server bulk power actions command will no longer attempt to run commands against installing or suspended servers.\n* Fixes the application API throwing an error when attempting to return variables for a server.\n* Fixes an error when attempting to install Panel dependencies without specifying an `.env` file due to an unset default timezone.\n* Fixes a null value flip in the database migrations.\n* Fixes password change endpoint for users allowing a blank value to be provided (even if nothing actually happened).\n* Fixes database IP addresses not allowing a `0` in the first octet field.\n* Fixes node information being impossible to update if there was a network error during the process. Any errors encountered communicating with Wings are now reported but will not block the actual saving of the changes.\n* **[Security]** When 2FA is required on an account the client API endpoints will now properly return an error and the UI will redirect the user to setup 2FA.\n* **[Security]** When changing the owner of a server the old owner's JWT is now properly invalidated on Wings.\n* Fixes a server error when requesting database information for a server as a subuser and the account is not granted `view_password` permissions.\n\n### Added\n* Adds support for basic backup rotation on a server when creating scheduled backup tasks.\n* Makes URLs present in the console clickable.\n* Adds `chmod` support to the file manager so that users can manually make modifications to file permissions as they need.\n\n### Changed\n* UI will no longer show a delete button to users when they're editing themselves.\n* Updated logic for bulk power actions to no longer run actions against suspended or installing servers.\n\n## v1.1.2\n### Fixed\n* Fixes an exception thrown while trying to validate IP access for the client API.\n* Fixes command history scrolling not putting the cursor at the end of the line.\n* Fixes file manager rows triggering a 404 when middle-clicked to open in a new tab.\n\n## v1.1.1\n### Fixed\n* Fixes allocation permissions checking on the frontend checking the wrong permission therefore leading to the item never showing up.\n* Fixes allocations not updating correctly when added or deleted and switching between pages.\n\n## v1.1.0\nThis release **requires** `Wings@1.1.0` in order to work properly due to breaking internal API changes.\n\n### Fixed\n* Fixes subuser creation/edit modal not submitting correctly when attemping to make modifications.\n* Fixes a few remaining issues with multiple egg install scripts.\n* Removes the ability for a schedule to have a null name and replaces any existing null names with a randomly generated name.\n* Fixes schedules aborting the entire run process if a single schedule encountered an exception. This resolves batches of schedules never running correctly if they occur after a broken schedule.\n* Fixes schedules not properly resetting themselves if an exception was encountered during the run.\n* Fixes numerous N+1 query run-aways when loading multiple servers via the API.\n* Fixes numerous issues with displaying directory and file names in the file manager if they included special characters that could not be decoded properly.\n* Fixes CPU pinning not being properly passed along to Wings when updated (this also fixes memory/CPU/disk not passing along correctly as well).\n* Fixes spinner not displaying properly when displayed over a modal.\n\n### Added\n* Adds ability for users to generate their own additional server allocations via the frontend if enabled.\n* Adds the ability for a user to remove un-needed allocations from their server (as long as it is not the primary allocation).\n* Adds support for tracking the last 32 sent console commands for a server. Access the history by using the arrow keys when the command field is active.\n* Adds S3 specific environment variables allowing for backups to use any S3 compatiable system, not just AWS.\n* Adds support for copying a server allocation address to the clipboard when clicked.\n* Adds information about the next schedule run time when viewing an individual schedule.\n* Adds link to view a server in the admin control panel to the frontend server view when logged in as a root admin.\n* Adds support for egg-specific frontend/backend functionality. This is a beta feature meant for internal features at this time.\n* Adds back the EULA warning popup when starting a Minecraft server without an accepted EULA.\n* Adds missing descriptions for some user permissions on the frontend UI.\n\n### Changed\n* Adds Save/Invite button to top of subuser edit/creation modal to reduce the need for scrolling.\n* Updated language for server transfers and mounts to be less confusing.\n* Wings API endpoint for fetching all servers on a node is now properly paginated to reduce system load when returning hundreds or thousands of servers at once.\n* Removes unnecessary Wings API calls when adding/editing/deleting mounts.\n* Primary allocation for a server is now always returned, even if the subuser does not have permission to view all of the server allocations.\n* Google Analytics frontend code is now only loaded when a valid key is provided.\n\n## v1.0.3\n### Fixed\n* Fixes bug causing subusers to not be creatable or editable via the frontend for servers.\n* Fixes system timezone not being passed along properly to the MySQL connection causing scheduled tasks to run every minute when the MySQL instance and Panel timezone did not line up.\n* Fixes listing servers owned by a user in the admin area to actually list their servers.\n\n### Changed\n* Adds SameSite `lax` attribute for cookies generated by the Panel.\n* Adds better filtering for searching servers in the admin area to better key off name, uuid, or owner username/email.\n\n## v1.0.2\n### Added\n* Adds support for searching inside the file editor.\n* Adds support for manually executing a schedule regardless of if it is currently queued or not.\n* Adds an indicator to the schedule UI to show when a schedule is currently processing.\n* Adds support for setting the `backup_limit` of a server via the API.\n* **[Security]** Adds login throttling to the 2FA verification endpoint.\n\n### Fixed\n* Fixes subuser page title missing server name.\n* Fixes schedule task `sequence_id` not properly being reset when a schedule's task is deleted.\n* Fixes misc. UI bugs throughout the frontend when long text overflows its bounds.\n* Fixes user deletion command to properly handle email & ID searching.\n* Fixes color issues in the terminal causing certain text & background combinations to be illegible.\n* Fixes reCAPTCHA not properly resetting on login failure.\n* Fixes error messages not properly resetting between login screens.\n* Fixes a UI crash when attempting to create or view a directory or file that contained the `%` somewhere in the name.\n\n### Changed\n* Updated the search modal to close itself when the ESC key is pressed.\n* Updates the schedule view and editing UI to better display information to users.\n* Changed logic powering server searching on the frontend to return more accurate results and return all servers when executing the query as an admin.\n* Admin CP link no longer opens in a new tab.\n* Mounts will no longer allow a user to mount certain directory combinations. This blocks mounting one server's files into another server, and blocks using the server data directory as a mount destination.\n* Cleaned up assorted server build modification code.\n* Updates default eggs to have improved install scripts and more consistent container usage.\n\n## v1.0.1\n### Fixed\n* Fixes 500 error when mounting a mount to a server, and other related errors when handling mounts.\n* Ensures that `server_transfers` database is deleted if it already exists to avoid unnecessary error.\n* Fixes servers getting marked as \"not installed\" when modifying their startup arguments.\n* Fixes filemanager breadcrumbs being set incorrectly when navigating between files and folders.\n\n### Changed\n* Change the requests per minute from 240 to 720 for the client API to avoid unecessarily displaying\n\"Too Many Requests\" errors.\n* Added error output to certain commands that will output and terminate the command execution if the database\nmigrations have not been run correctly for the instance.\n\n## v1.0.0\nPterodactyl 1.0 represents the culmination of over two years of work, almost 2,000 commits, endless bug and feature requests, and a dream that\nhas been in the making since 2013. 🎉\n\nDue to the sheer size and timeline of this release I've massively truncated the listing below. There are numerous smaller\nbug fixes and changes that would simply be too difficult to keep track of here. Please feel free to browse through the releases\ntab for this repository to see more specific changes that have been made.\n\n### Added\n* Adds a new client-facing API allowing a user to control all aspects of their individual servers, or servers\nwhich they have been granted access to as a subuser.\n* Adds the ability for backups to be created for a server both manually and via a scheduled task.\n* Adds the ability for users to modify their server allocations on the fly and include notes for each allocation.\n* Adds the ability for users to generate recovery tokens for 2FA protected logins which can be used in place of\na code should their device be inaccessible.\n* Adds support for transfering servers between Nodes via the Panel.\n* Adds the ability to assign specific CPU cores to a server (CPU Pinning) process.\n* Server owners can now reinstall their assigned server egg automatically with a button on the frontend.\n\n### Changed\n* The entire user frontend has been replaced with a responsive, React backed design implemented using Tailwind CSS.\n* Replaces a large amount of complex daemon authentication logic by funneling most API calls through the Panel, and using\nJSON Web Tokens where necessary to handle one-time direct authentication with Wings.\n* Frontend server listing now includes a toggle to show or hide servers which an administrator has access to, rather\nthan always showing all servers on the system when logged into an admin account.\n* We've replaced Ace Editor on the frontend with a better solution to allow lighter builds and more end-user functionality.\n* Server permissions have been overhauled to be both easier to understand in the codebase, and allows plugins to better\nhook into the permission system.\n\n### Removed\n* Removes large swaths of code complexity and confusing interface designs that caused a lot of pain to new developers\ntrying to jump into the codebase. We've simplified this to stick to more established Laravel design standards to make\nit easy to parse through the project and make contributions.\n\n## v0.7.19 (Derelict Dermodactylus)\n### Fixed\n* **[Security]** Fixes XSS in the admin area's server owner selection.\n\n## v0.7.18 (Derelict Dermodactylus)\n### Fixed\n* **[Security]** Re-addressed missed endpoint that would not properly limit a user account to 5 API keys.\n* **[Security]** Addresses a Client API vulnerability that would allow a user to list all servers on the system ([`GHSA-6888-7f3w-92jx`](https://github.com/pterodactyl/panel/security/advisories/GHSA-6888-7f3w-92jx))\n\n## v0.7.17 (Derelict Dermodactylus)\n### Fixed\n* Limited accounts to 5 API keys at a time.\n* Fixes database passwords not being generated with the proper requirements for some MySQL setups.\n* Hostnames that are not FQDNs/IP addresses can now be used for connecting to a MySQL host.\n\n## v0.7.16 (Derelict Dermodactylus)\n### Fixed\n* Fixed the /api/application/servers endpoint erroring when including subusers or egg\n* Fixed bug in migration files causing failures when using MySQL 8.\n* Fixed missing redirect return when an error occurs while modifying database information.\n* Fixes bug in login attempt tracking.\n* Fixes a bug where certain URL encoded files would not be editable in the file manager.\n\n### Added\n* The application API now includes the egg's name in the egg model's response.\n* The /api/application/servers endpoint can now include server's databases and subusers.\n\n## v0.7.15 (Derelict Dermodactylus)\n### Fixed\n* Fixes support for PHP 7.3 when running `composer install` commands due to a dependency that needed updating.\n* Automatic allocation field when creating a new node (or updating one) should now properly remeber its old\nvalue when showing an error state.\n* Mass deleting files now executes properly and doesn't result in a JS console error.\n* Scrolling on email settings page now works.\n* Database host management will now properly display an error message to the user when there is any type of MySQL related\nerror encountered during creation or update.\n* Two-factor tokens generated when a company name has a space in it will now properly be parsed on iOS authenticator devices.\n* Fixed 500 error when trying to request subuser's from a server in the application API.\n* Creating a node allocation via the API no longer requires an alias field be passed through in the request.\n* Bulk power management for servers via the CLI no longer fails when servers span multiple nodes.\n\n### Added\n* Server listing view now displays the total used disk space for each server.\n* Client API endpoint to list all servers now supports an additional `?filter=subuser-of|all|admin|owner` parameter to\nreturn different groupings of servers. The default value is `subuser-of` which will include all of the user's servers\nthat they are the owner of, as well as all servers they're a subuser of.\n* Added back ability to toggle OOM killer status on a per-server basis.\n* Added `LOCK TABLES` permission for generated database users.\n\n### Changed\n* Updated Paper egg to not download `server.properties` each time. [parkervcp/eggs#260](https://github.com/parkervcp/eggs/issues/260)\n* Insurgency egg now uses the proper dedicated server ID.\n* Teamspeak egg updated with improved installation process and grabbing latest versions.\n* OOM killer disabled by default on all new servers.\n* Passwords generated for MySQL now include special characters and are 24 characters in length.\n\n## v0.7.14 (Derelict Dermodactylus)\n### Fixed\n* **[SECURITY]** Fixes an XSS vulnerability when performing certain actions in the file manager.\n* **[SECURITY]** Attempting to login as a user who has 2FA enabled will no longer request the 2FA token before validating\nthat their password is correct. This closes a user existence leak that would expose that an account exists if\nit had 2FA enabled.\n\n### Changed\n* Support for setting a node to listen on ports lower than 1024.\n* QR code URLs are now generated without the use of an external library to reduce the dependency tree.\n* Regenerated database passwords now respect the same settings that were used when initially created.\n* Cleaned up 2FA QR code generation to use a more up-to-date library and API.\n* Console charts now properly start at 0 and scale based on server configuration. No more crazy spikes that\nare due to a change of one unit.\n\n## v0.7.13 (Derelict Dermodactylus)\n### Fixed\n* Fixes a bug with the location update API endpoint throwing an error due to an unexected response value.\n* Fixes bug where node creation API endpoint was not correctly requiring the `disk_overallocate` key.\n* Prevents an exception from being thrown when a database with the same name is created on two different hosts.\n* Fixes the redis password not saving correctly when setting up the environment from the command line.\n* Fixes a bug with transaction handling in many areas of the application that would cause validation error messages\nand other session data to not be persisted properly when using the database as the session driver.\n* Fix a bug introduced at some point in the past that causes internal data integrity exceptions to not bubble up to\nthe user correctly, leading to extraneous and confusing exception messages.\n* Fixes a bug causing servers to not be marked as having failed installation in some cases.\n\n### Changed\n* `allocation_limit` for servers now defaults to a null value, and is not required in PATCH/POST requests when adding\na server through the API.\n* The `PATCH` endpoint for `/api/applications/servers/{server}/build` now accepts an array called `limits` to match\nthe response from the server `GET` endpoint.\n\n### Added\n* The server listing for a node is now paginated to 25 servers per page to improve performance on large nodes.\n\n## v0.7.12 (Derelict Dermodactylus)\n### Fixed\n* Fixes an issue with the locations API endpoint referencing an invalid namespace.\n* Fixes the `store()` function on the locations API not working due to an incorrect return typehint.\n* Fixes daemon secrets not being able to be reset on a Node.\n* Fixes an issue where files were not editable due to missing URL encoding in the file manager.\n* Fixed checking of language changes\n* Fixed Spigot egg not building versions other than `latest`.\n* Fixed the Forge egg install script.\n* Fixes a bug that would ignore the `skip_scripts` setting when creating or editing a server.\n\n### Updated\n* Upgraded core to use Laravel `5.7.14`.\n* Updated Simplified Chinese translation pack.\n\n### Added\n* Added support for opening and editing Python files through the web editor.\n* Adds Russian translation.\n\n## v0.7.11 (Derelict Dermodactylus)\n### Fixed\n* Fixes an issue with certain systems not handling an API folder that was named `API` but referenced as `Api` in the namespace.\n* TS3 egg updated to use CLI arguments correctly and have a more minimalistic installation script.\n* Terminal was not properly displaying longer lines leading to some visual inconsistency.\n* Assorted translation updates.\n* Pagination for server listing now properly respects configuration setting.\n* Client API now properly respects permissions that are set and allows subusers to access their assigned servers.\n\n### Changed\n* Removed PhraseApp integration from Panel code as it is no longer used.\n* SFTP login endpoint now returns the permissions for that user rather than requiring additional queries to get that data.\n\n### Added\n* You can now test your mail settings from the Admin CP without waiting to see if things are working correctly.\n\n## v0.7.10 (Derelict Dermodactylus)\n### Fixed\n* Scheduled tasks triggered manually no longer improperly change the `next_run_at` time and do not run twice in a row anymore.\n* Changing the maximum web-based file upload size for a node now properly validates and updates.\n* Changing configuration values for a node now correctly updates them on the daemon on the first request, rather than requiring a second request to set them.\n\n### Changed\n* Egg and server variable values are no longer limited to 191 characters. Turns out some games require a large number of characters in these fields.\n\n### Added\n* Users can now select their preferred language in their account settings.\n\n## v0.7.9 (Derelict Dermodactylus)\n### Fixed\n* Fixes a two-factor authentication bypass present in the password reset process for an account.\n\n## v0.7.8 (Derelict Dermodactylus)\n### Added\n* Nodes can now be put into maintenance mode to deny access to servers temporarily.\n* Basic statistics about your panel are now available in the Admin CP.\n* Added support for using a MySQL socket location for connections rather than a TCP connection. Set a `DB_SOCKET` variable in your `.env` file to use this.\n\n### Fixed\n* Hitting Ctrl+Z when editing a file on the web now works as expected.\n* Logo now links to the correct location on all pages.\n* Permissions checking to determine if a user can see the task management page now works correctly.\n* Fixed `pterodactyl.environment_variables` to be used correctly for global environment variables. The wrong config variable name was being using previously.\n* Fixes tokens being sent to users when their account is created to actually work. Implements Laravel's internal token creation mechanisms rather than trying to do it custom.\n* Updates some eggs to ensure they have the correct data and will continue working down the road. Fixes autoupdating on some source servers and MC related download links.\n* Emails should send properly now when a server is marked as installed to let the owner know it is ready for action.\n* Cancelling a file manager operation should cancel correctly across all browsers now.\n\n### Changed\n* Attempting to upload a folder via the web file manager will now display a warning telling the user to use SFTP.\n* Changing your account password will now log out all other sessions that currently exist for that user.\n* Subusers with no permissions selected can be created.\n\n## v0.7.7 (Derelict Dermodactylus)\n### Fixed\n* Fixes an issue with the sidebar logo not working correctly in some browsers due to the CSS being assigned.\n* Fixes a bunch of typos through the code base.\n* Fixes a bug when attempting to load the dropdown menu for server owner in some cases.\n* Fixes an exception thrown when the database connection address was not filled out correctly while adding a database to a server.\n* Fixes some mistakes in the German translation of the panel.\n\n### Added\n* Added a new client API endpoint for gathering the utilization stats for servers including disk, cpu, and memory. `GET /api/client/servers/<id>/utilization`\n* Added validation to variable validation rules to validate that the validation rules are valid because we heard you like validating your validation.\n* Added German translations for many previously untranslated parts of the panel.\n\n### Changed\n* Updated core framework from Laravel 5.5 to Laravel 5.6.\n* Improved support for Windows based environments.\n* Spigot Egg now builds spigot for you rather than requiring a download location be specified.\n\n## v0.7.6 (Derelict Dermodactylus)\n### Fixed\n* Fixes a UI error when attempting to change the default Nest and Egg for an existing server.\n* Correct permissions check in UI to allow subusers with permission to `view-allocations` the ability to actually see the sidebar link.\n* Fixes improper behavior when marking an egg as copying the configuration from another.\n* Debug bar is only checked when the app is set to debug mode in the API session handler, rather than when it is in local mode to match the plugin settings.\n* Added validation to port allocations to prevent allocation of restricted or invalid ports.\n* Fix data integrity exception thrown when attempting to store updated server egg variables.\n* Added missing permissions check on 'SFTP Configuration' page to ensure user has permission to access a server's SFTP server before showing a user credentials.\n\n### Added\n* Added ability for end users to change the name of their server through the UI. This option is only open to the server owner or an admin.\n* Added giant warning message if you attempt to change an encryption key once one has been set.\n\n### Changed\n* Panel now throws proper 504: Gateway Timeout errors on server listing when daemon is offline.\n* Sessions handled through redis now use a separate database (default `1`) to store session database to avoid logging users out when flushing the cache.\n* File manager UI improved to be clearer with buttons and cleaner on mobile.\n* reCAPTCHA's secret key position swapped with website key in advanced panel settings to be consistent with Google's reCAPTCHA dashboard.\n* Changed DisplayException to handle its own logging correctly and check if the previous exception is marked as one that should not be logged.\n* Changed 'New Folder' modal in file manager to include a trailing slash.\n\n## v0.7.5 (Derelict Dermodactylus)\n### Fixed\n* Fixes application API keys being created as a client API key.\n* Search term is now passed through when using paginated result sets.\n* Reduces the number of SQL queries executed when rendering the server listing to increase performance.\n* Fixes exceptions being thrown for non-existent subuser permissions.\n* Fixes exception caused when trying to revoke admin privileges from a user account due to a bad endpoint.\n\n### Changed\n* Databases are now properly paginated when viewing a database host.\n* No more loading daemon keys for every server model being loaded, some of us value our databases.\n* Changed behavior of the subuser middleware to add a daemon access key if one is missing from the database for some reason.\n* Server short-codes are now based on the UUID as they were in previous versions of Pterodactyl.\n\n## v0.7.4-h1 (Derelict Dermodactylus)\n### Fixed\n* Being able to create servers is kind of a core aspect of the software, pushing releases late at night is not a great idea.\n\n## v0.7.4 (Derelict Dermodactylus)\n### Fixed\n* Fixes a bug when reinstalling a server that would not mark the server as installing, resulting in some UI issues.\n* Handle 404 errors from missing models in the application API bindings correctly.\n* Fix validation error returned when no environment variables are passed, even if there are no variables required.\n* Fix improper permissions on `PATCH /api/servers/<id>/startup` endpoint which was preventing editing any start variables.\n* Should fix migration issues from 0.6 when there are more than API key in the database.\n\n### Changed\n* Changes order that validation of resource existence occurs in API requests to not try and use a non-existent model when validating data.\n\n### Added\n* Adds back client API for sending commands or power toggles to a server though the Panel API: `/api/client/servers/<identifier>`\n* Added proper transformer for Packs and re-enabled missing includes on server.\n* Added support for using Filesystem as a caching driver, although not recommended.\n* Added support for user management of server databases.\n* **Added bulk power management CLI interface to send start, stop, kill, restart actions to servers across configurable nodes.**\n\n## v0.7.3 (Derelict Dermodactylus)\n### Fixed\n* Fixes server creation API endpoint not passing the provided `external_id` to the creation service.\n* Fixes a bug causing users to be un-editable on new installations once more than one user exists.\n* Fixes default order of buttons in certain parts of the panel that would default to 'Delete' rather than 'Save' when pressing enter.\n\n### Added\n* Adds ability to modify the external ID for a server through the API.\n\n## v0.7.2 (Derelict Dermodactylus)\n### Fixed\n* Fixes an exception thrown when trying to access the `/nests/:id/eggs/:id` API endpoint.\n* Fixes search on server listing page.\n* Schedules with no names are now clickable to allow editing.\n* Fixes broken permissions check that would deny access to API keys that did in fact have permission.\n\n### Added\n* Adds ability to include egg variables on an API request.\n* Added `external_id` column to servers that allows for easier linking with external services such as WHMCS.\n* Added back the sidebar when viewing servers that allows for quick-switching to a different server.\n* Added API endpoint to get a server by external ID.\n\n## v0.7.1 (Derelict Dermodactylus)\n### Fixed\n* Fixes an exception when no token is entered on the 2-Factor enable/disable page and the form is submitted.\n* Fixes an exception when trying to perform actions against a User model due to a validator that could not be cast to a string correctly.\n* Allow FQDNs in database host creation UI correctly.\n* Fixes database naming scheme using `d###_` rather than `s###_` when creating server databases.\n* Fix exception thrown when attempting to update an existing database host.\n\n### Changed\n* Adjusted exception handler behavior to log more stack information for PDO exceptions while not exposing credentials.\n\n### Added\n* Very basic cache busting until asset management can be changed to make use of better systems.\n\n## v0.7.0 (Derelict Dermodactylus)\n### Fixed\n* `[rc.2]` — Fixes bad API behavior on `/user` routes.\n* `[rc.2]` — Fixes Admin CP user editing resetting a password on users unintentionally.\n* `[rc.2]` — Fixes bug with server creation API endpoint that would fail to validate `allocation.default` correctly.\n* `[rc.2]` — Fix data integrity exception occurring due to invalid data being passed to server creation service on the API.\n* `[rc.2]` — Fix data integrity exception that could occur when an email containing non-username characters was passed.\n* `[rc.2]` — Fix data integrity exception occurring when no default value is provided for an egg variable.\n* `[rc.2]` — Fixes a bug that would cause non-editable variables on the front-end to throw a validation error.\n* `[rc.2]` — Fixes a data integrity exception occurring when saving egg variables with no value.\n* Fixes a design bug in the database that prevented the storage of negative numbers, thus preventing a server from being assigned unlimited swap.\n* Fixes a bug where the 'Assign New Allocations' box would only show IPs that were present in the current pagination block.\n* Unable to change the daemon secret for a server via the Admin CP.\n* Using default value in rules when creating a new variable if the rules is empty.\n* Fixes a design-flaw in the allocation management part of nodes that would run a MySQL query for each port being allocated. This behavior is now changed to only execute one query to add multiple ports at once.\n* Attempting to create a server when no nodes are configured now redirects to the node creation page.\n* Fixes missing library issue for teamspeak when used with mariadb.\n* Fixes inability to change the default port on front-end when viewing a server.\n* Fixes bug preventing deletion of nests that have other nests referencing them as children.\n* Fixes console sometimes not loading properly on slow connections\n\n### Added\n* Added ability to search the following API endpoints: list users, list servers, and list locations.\n* Add support for finding a user by external ID using `/api/application/users/external/<id>` or by passing it as the search term when listing all users.\n* Added a unique key to the servers table to data integrity issues where an allocation would be assigned to more than one server at once.\n* Added support for editing an existing schedule.\n* Added support for editing symlinked files on the Panel.\n* Added new application specific API to Panel with endpoints at `/api/application`. Includes new Admin CP interface for managing keys and an easier permissions system.\n* Nest and Egg listings now show the associated ID in order to make API requests easier.\n* Added star indicators to user listing in Admin CP to indicate users who are set as a root admin.\n* Creating a new node will now requires a SSL connection if the Panel is configured to use SSL as well.\n* Socketio error messages due to permissions are now rendered correctly in the UI rather than causing a silent failure.\n* File manager now supports mass deletion option for files and folders.\n* Support for CS:GO as a default service option selection.\n* Support for GMOD as a default service option selection.\n* Added test suite for core aspects of the project (Services, Repositories, Commands, etc.) to lessen the chances for bugs to escape into releases.\n* New CLI command to disabled 2-Factor Authentication on an account if necessary.\n* Ability to delete users and locations via the CLI.\n* You can now require 2FA for all users, admins only, or at will using a simple configuration in the Admin CP.\n* **Added ability to export and import service options and their associated settings and environment variables via the Admin CP.**\n* Default allocation for a server can be changed on the front-end by users. This includes two new subuser permissions as well.\n* Significant improvements to environment variable control for servers. Now ships with built-in abilities to define extra variables in the Panel's configuration file, or in-code for those heavily modifying the Panel.\n* Quick link to server edit view in ACP on frontend when viewing servers.\n* Databases created in the Panel now include `EXECUTE` privilege.\n\n### Changed\n* PHP 7.2 is now the minimum required version for this software.\n* Egg variable default values are no longer validated against the ruleset when configuring them. Validation of those rules will only occur when editing or creating a server.\n* Changed logger to skip reporting stack-traces on PDO exceptions due to sensitive information being contained within.\n* Changed behavior of allocation IP Address/Ports box to automatically store the value entered if a user unfocuses the field without hitting space.\n* Changed order in which allocations are displayed to prioritize those with servers attached (in ascending IP & port order) followed by ascending IP & port order where no server is attached.\n* Revoking the administrative status for an admin will revoke all authentication tokens currently assigned to their account.\n* Updated core framework to Laravel 5.5. This includes many dependency updates.\n* Certain AWS specific environment keys were changed, this should have minimal impact on users unless you specifically enabled AWS specific features. The renames are: `AWS_KEY -> AWS_ACCESS_KEY_ID`, `AWS_SECRET -> AWS_SECRET_ACCESS_KEY`, `AWS_REGION -> AWS_DEFAULT_REGION`\n* API keys have been changed to only use a single public key passed in a bearer token. All existing keys can continue being used, however only the first 32 characters should be sent.\n* Moved Docker image setting to be on the startup management page for a server rather than the details page. This value changes based on the Nest and Egg that are selected.\n* Two-Factor authentication tokens are now 32 bytes in length, and are stored encrypted at rest in the database.\n* Login page UI has been improved to be more sleek and welcoming to users.\n* Changed 2FA login process to be more secure. Previously authentication checking happened on the 2FA post page, now it happens prior and is passed along to the 2FA page to avoid storing any credentials.\n* **Services renamed to Nests. Service Options renamed to Eggs.** 🥚\n* Theme colors and login pages updated to give a more unique feel to the project.\n* Massive overhaul to the backend code that allows for much easier updating of core functionality as well as support for better testing. This overhaul also reduces complex code logic, and allows for faster response times in the application.\n* CLI commands updated to be easier to type, now stored in the `p:` namespace.\n* Logout icon is now more universal and not just a power icon.\n* Administrative logout notice now uses SWAL rather than a generic javascript popup.\n* Server creation page now only asks for a node to deploy to, rather than requiring a location and then a node.\n* Database passwords are now hidden by default and will only show if clicked on. In addition, database view in ACP now indicates that passwords must be viewed on the front-end.\n* Localhost cannot be used as a connection address in the environment configuration script. `127.0.0.1` is allowed.\n* Application locale can now be quickly set using an environment variable `APP_LOCALE` rather than having to edit core files.\n\n### Removed\n* OOM exceptions can no longer be disabled on servers due to a startling number of users that were using it to avoid allocating proper amounts of resources to servers.\n* SFTP settings page now only displays connection address and username. Password setting was removed as it is no longer necessary with Daemon changes.\n\n## v0.7.0-rc.2 (Derelict Dermodactylus)\n### Fixed\n* `[rc.1]` — Fixes exception thrown when revoking user sessions.\n* `[rc.1]` — Fixes exception that would occur when trying to delete allocations from a node.\n* `[rc.1]` — Fixes exception thrown when attempting to adjust mail settings as well as a validation error thrown afterwards.\n* `[rc.1]` — Fixes bug preventing modification of the default value for an Egg variable.\n* `[rc.1]` — Fixed a bug that would occur when attempting to reset the daemon secret for a node.\n* `[rc.1]` — Fix exception thrown when attempting to modify an existing database host.\n* `[rc.1]` — Fix an auto deployment bug causing a node to be ignored if it had no servers already attached to it.\n\n### Changed\n* Changed logger to skip reporting stack-traces on PDO exceptions due to sensitive information being contained within.\n\n### Added\n* Added support for editing an existing schedule.\n\n## v0.7.0-rc.1 (Derelict Dermodactylus)\n### Fixed\n* `[beta.4]` — Fixes some bad search and replace action that happened previously and was throwing errors when validating user permissions.\n* `[beta.4]` — Fixes behavior of variable validation to not break the page when no rules are provided.\n* `[beta.4]` — Fix bug preventing the editing of files in the file manager.\n\n### Added\n* Added support for editing symlinked files on the Panel.\n* Added new application specific API to Panel with endpoints at `/api/application`. Includes new Admin CP interface for managing keys and an easier permissions system.\n\n## v0.7.0-beta.4 (Derelict Dermodactylus)\n### Fixed\n* `[beta.3]` — Fixes a bug with the default environment file that was causing an inability to perform a fresh install when running package discovery.\n* `[beta.3]` — Fixes an edge case caused by the Laravel 5.5 upgrade that would try to perform an in_array check against a null value.\n* `[beta.3]` — Fixes a bug that would cause an error when attempting to create a new user on the Panel.\n* `[beta.3]` — Fixes error handling of the settings service provider when no migrations have been run.\n* `[beta.3]` — Fixes validation error when trying to use 'None' as the 'Copy Script From' option for an egg script.\n* Fixes a design bug in the database that prevented the storage of negative numbers, thus preventing a server from being assigned unlimited swap.\n* Fixes a bug where the 'Assign New Allocations' box would only show IPs that were present in the current pagination block.\n\n### Added\n* Nest and Egg listings now show the associated ID in order to make API requests easier.\n\n### Changed\n* Changed behavior of allocation IP Address/Ports box to automatically store the value entered if a user unfocuses the field without hitting space.\n* Changed order in which allocations are displayed to prioritize those with servers attached (in ascending IP & port order) followed by ascending IP & port order where no server is attached.\n\n### Removed\n* OOM exceptions can no longer be disabled on servers due to a startling number of users that were using it to avoid allocating proper amounts of resources to servers.\n\n## v0.7.0-beta.3 (Derelict Dermodactylus)\n### Fixed\n* `[beta.2]` — Fixes a bug that would cause an endless exception message stream in the console when attempting to setup environment settings in certain instances.\n* `[beta.2]` — Fixes a bug causing the dropdown menu for a server's egg to display the wrong selected value.\n* `[beta.2]` — Fixes a bug that would throw a red page of death when submitting an invalid egg variable value for a server in the Admin CP.\n* `[beta.2]` — Someone found a `@todo` that I never `@todid` and thus database hosts could not be created without being linked to a node. This is fixed...\n* `[beta.2]` — Fixes bug that caused incorrect rendering of CPU usage on server graphs due to missing variable.\n* `[beta.2]` — Fixes bug causing schedules to be un-deletable.\n* `[beta.2]` — Fixes bug that prevented the deletion of nodes due to an allocation deletion cascade issue with the SQL schema.\n* `[beta.2]` — Fixes a bug causing eggs not extending other eggs to fail validation.\n\n### Changed\n* Revoking the administrative status for an admin will revoke all authentication tokens currently assigned to their account.\n* Updated core framework to Laravel 5.5. This includes many dependency updates.\n* Certain AWS specific environment keys were changed, this should have minimal impact on users unless you specifically enabled AWS specific features. The renames are: `AWS_KEY -> AWS_ACCESS_KEY_ID`, `AWS_SECRET -> AWS_SECRET_ACCESS_KEY`, `AWS_REGION -> AWS_DEFAULT_REGION`\n* API keys have been changed to only use a single public key passed in a bearer token. All existing keys can continue being used, however only the first 32 characters should be sent.\n\n### Added\n* Added star indicators to user listing in Admin CP to indicate users who are set as a root admin.\n* Creating a new node will now requires a SSL connection if the Panel is configured to use SSL as well.\n\n## v0.7.0-beta.2 (Derelict Dermodactylus)\n### Fixed\n* `[beta.1]` — Fixes a CORS header issue due to a wrong API endpoint being provided in the administrative node listing.\n* `[beta.1]` — Fixes bug that would prevent root admins from accessing servers they were not set as the owner of.\n* `[beta.1]` — Fixes wrong URL redirect being provided when creating a subuser.\n* `[beta.1]` — Fixes missing check in environment setup that would leave the Hashids salt empty.\n* `[beta.1]` — Fixes bug preventing loading of allocations when trying to create a new server.\n* `[beta.1]` — Fixes bug causing inability to create new servers on the Panel.\n* `[beta.1]` — Fixes bug causing inability to delete an allocation due to misconfigured JS.\n* `[beta.1]` — Fixes bug causing inability to set the IP alias for an allocation to an empty value.\n* `[beta.1]` — Fixes bug that caused startup changes to not propagate to the server correctly on the first save.\n* `[beta.1]` — Fixes bug that prevented subusers from accessing anything over socketio due to a missing permission.\n\n### Changed\n* Moved Docker image setting to be on the startup management page for a server rather than the details page. This value changes based on the Nest and Egg that are selected.\n* Two-Factor authentication tokens are now 32 bytes in length, and are stored encrypted at rest in the database.\n* Login page UI has been improved to be more sleek and welcoming to users.\n* Changed 2FA login process to be more secure. Previously authentication checking happened on the 2FA post page, now it happens prior and is passed along to the 2FA page to avoid storing any credentials.\n\n### Added\n* Socketio error messages due to permissions are now rendered correctly in the UI rather than causing a silent failure.\n\n## v0.7.0-beta.1 (Derelict Dermodactylus)\n### Added\n* File manager now supports mass deletion option for files and folders.\n* Support for CS:GO as a default service option selection.\n* Support for GMOD as a default service option selection.\n* Added test suite for core aspects of the project (Services, Repositories, Commands, etc.) to lessen the chances for bugs to escape into releases.\n* New CLI command to disabled 2-Factor Authentication on an account if necessary.\n* Ability to delete users and locations via the CLI.\n* You can now require 2FA for all users, admins only, or at will using a simple configuration in the Admin CP.\n* **Added ability to export and import service options and their associated settings and environment variables via the Admin CP.**\n* Default allocation for a server can be changed on the front-end by users. This includes two new subuser permissions as well.\n* Significant improvements to environment variable control for servers. Now ships with built-in abilities to define extra variables in the Panel's configuration file, or in-code for those heavily modifying the Panel.\n* Quick link to server edit view in ACP on frontend when viewing servers.\n* Databases created in the Panel now include `EXECUTE` privilege.\n\n### Changed\n* **Services renamed to Nests. Service Options renamed to Eggs.** 🥚\n* Theme colors and login pages updated to give a more unique feel to the project.\n* Massive overhaul to the backend code that allows for much easier updating of core functionality as well as support for better testing. This overhaul also reduces complex code logic, and allows for faster response times in the application.\n* CLI commands updated to be easier to type, now stored in the `p:` namespace.\n* Logout icon is now more universal and not just a power icon.\n* Administrative logout notice now uses SWAL rather than a generic javascript popup.\n* Server creation page now only asks for a node to deploy to, rather than requiring a location and then a node.\n* Database passwords are now hidden by default and will only show if clicked on. In addition, database view in ACP now indicates that passwords must be viewed on the front-end.\n* Localhost cannot be used as a connection address in the environment configuration script. `127.0.0.1` is allowed.\n* Application locale can now be quickly set using an environment variable `APP_LOCALE` rather than having to edit core files.\n\n### Fixed\n* Unable to change the daemon secret for a server via the Admin CP.\n* Using default value in rules when creating a new variable if the rules is empty.\n* Fixes a design-flaw in the allocation management part of nodes that would run a MySQL query for each port being allocated. This behavior is now changed to only execute one query to add multiple ports at once.\n* Attempting to create a server when no nodes are configured now redirects to the node creation page.\n* Fixes missing library issue for teamspeak when used with mariadb.\n* Fixes inability to change the default port on front-end when viewing a server.\n* Fixes bug preventing deletion of nests that have other nests referencing them as children.\n* Fixes console sometimes not loading properly on slow connections\n\n### Removed\n* SFTP settings page now only displays connection address and username. Password setting was removed as it is no longer necessary with Daemon changes.\n\n## v0.6.4 (Courageous Carniadactylus)\n### Fixed\n* Fixed the console rendering on page load, I guess people don't like watching it load line-by-line for 10 minutes. Who would have guessed...\n* Re-added support for up/down arrows loading previous commands in the console window.\n\n### Changed\n* Panel API for Daemon now responds with a `HTTP/401 Unauthorized` error when unable to locate a node with a given authentication token, rather than a `HTTP/404 Not Found` response.\n* Added better colors and styling for the terminal that can be adjusted per-theme.\n* Session timeout adjusted to be 7 days by default.\n\n## v0.6.3 (Courageous Carniadactylus)\n### Fixed\n* **[Security]** — Addresses an oversight in how the terminal rendered information sent from the server feed which allowed a malicious user to execute arbitrary commands on the game-server process itself by using a specifically crafted in-game command.\n\n### Changed\n* Removed `jquery.terminal` and replaced it with an in-house developed terminal with less potential for security issues.\n\n## v0.6.2 (Courageous Carniadactylus)\n### Fixed\n* Fixes a few typos throughout the panel, there are more don't worry.\n* Fixes bug when disabling 2FA due to a misnamed route.\n* API now returns a 404 error when deleting a user that doesn't exist, rather than saying it was successful.\n* Service variables that allow empty input now allow you to empty out the assigned value and set it back to blank.\n* Fixes a bug where changing the default allocation for a server would not actually apply that allocation as the default on the daemon.\n* Newly created service variables are now backfilled and assigned to existing servers properly.\n\n### Added\n* Added a `Vagrantfile` to the repository to help speed up development and testing for those who don't want to do a full dedicated install.\n* Added a confirmation dialog to the logout button for admins to prevent misguided clickers from accidentally logging out when they wanted to switch to Admin or Server views.\n\n### Changed\n* Blocked out the `Reinstall` button for servers that have failed installation to avoid confusion and bugs causing the daemon to break.\n* Updated dependencies, listed below.\n```\naws/aws-sdk-php (3.26.5 => 3.29.7)       \nlaravel/framework (v5.4.21 => v5.4.27)        \nbarryvdh/laravel-debugbar (v2.3.2 => v2.4.0)     \nfideloper/proxy (3.3.0 => 3.3.3)\nigaster/laravel-theme (v1.14 => v1.16)    \nlaravel/tinker (v1.0.0 => v1.0.1)  \nspatie/laravel-fractal (4.0.0 => 4.0.1)\n```\n\n## v0.6.1 (Courageous Carniadactylus)\n### Fixed\n* Fixes a bug preventing the use of services that have no variables attached to them.\n* Fixes 'Remember Me' checkbox being ignored when using 2FA on an account.\n* API now returns a useful error displaying what went wrong rather than an obscure 'An Error was Encountered' message when API issues arise.\n* Fixes bug preventing the creation of new files in the file manager due to a missing JS dependency on page load.\n* Prevent using a service option tag that contains special characters that are not valid. Now only allows alpha-numeric, no spaces or underscores.\n* Fix unhandled exception due to missing `Log` class when using the API and causing an error.\n\n### Changed\n* Renamed session cookies from `laravel_session` to `pterodactyl_session`.\n* Sessions are now encrypted before being stored as an additional layer of security.\n* It is now possible to clear out a server description and have it be blank, rather than throwing an error about the field being required.\n\n## v0.6.0 (Courageous Carniadactylus)\n### Fixed\n* Bug causing error logs to be spammed if someone timed out on an ajax based page.\n* Fixes edge case where specific server names could cause daemon errors due to an invalid SFTP username being created by the panel.\n* Fixes sessions being removed on browser close, and set sessions to idle for up to 3 hours before being marked as expired.\n* Emails sending with 'Pterodactyl Panel' as the from name. Now configurable by using `php artisan pterodactyl:mail` to update.\n* Fixes potential bug with invalid CIDR notation (ex: `192.168.1.1/z`) when adding allocations that could cause over 4 million records to be created at once.\n* Fixes bug where daemon was unable to register that certain games had fully booted and were ready to play on.\n* Fixes bug causing MySQL user accounts to be corrupted when resetting a password via the panel.\n* Fixes remote timing attack vulnerability due to hmac comparison in API middleware.\n* `[rc.1]` — Server deletion is fixed, caused by removed download table.\n* `[rc.1]` — Server status indication on front-end no longer shows `Error` when server is marked as installing or suspended.\n* `[rc.1]` — Fixes issues with SteamCMD not registering and installing games properly.\n\n### Changed\n* Admin API and base routes for user management now define the fields that should be passed to repositories rather than passing all fields.\n* User model now defines mass assignment fields using `$fillable` rather than `$guarded`.\n* 2FA checkpoint on login is now its own page, and not an AJAX based call. Improves security on that front.\n* Updated Server model code to be more efficient, as well as make life easier for backend changes and work.\n* Reduced the number of database queries being executed when viewing a specific server. This is done by caching the query for up to 15 minutes in memcached.\n* User creation emails include more information and are sent by the event listener rather than the repository.\n* Account password reset emails now auto-fill the email when clicking the link.\n* New theme applied to Admin CP. Many graphical changes were made, some data was moved around and some display data changed. Too much was changed to feasibly log it all in here. Major breaking changes or notable new features will be logged.\n* New server creation page now makes significantly less AJAX calls and is much quicker to respond.\n* Server and Node view pages wee modified to split tabs into individual pages to make re-themeing and modifications significantly easier, and reduce MySQL query loads on page.\n* Most of the backend `UnhandledException` display errors now include a clearer error that directs admins to the program's logs.\n* Table seeders for services now can be run during upgrades and will attempt to locate and update, or create new if not found in the database.\n* Many structural changes to the database and `Pterodactyl\\Models` classes that would flood this changelog if they were all included. All required migrations included to handle database changes.\n* Clarified details for database hosts to prevent users entering invalid account details, as well as renamed tables and columns relating to it to keep things clearer.\n* Updated all code to be Laravel compliant when using `env()` and moved to using `config()` throughout non `config/*.php` files.\n* Subuser permissions are now stored in `Permission::listPermissions()` to make views way cleaner and make adding to views significantly cleaner.\n* Attempting to reset a password for an account that does not exist no longer returns an error, rather it displays a success message. Failed resets trigger a `Pterodactyl\\Events\\Auth\\FailedPasswordReset` event that can be caught if needed to perform other actions.\n* Servers are no longer queued for deletion due to the general hassle and extra logic required.\n* Updated all panel components to run on Laravel v5.4 rather than 5.3 which is EOL.\n* Routes are now handled in the `routes/` folder, and use a significantly cleaner syntax. Controller names and methods have been updated as well to be clearer as well as avoid conflicts with PHP reserved keywords.\n* API has been completely overhauled to use new permissions system. **Any old API keys will immediately become invalid and fail to operate properly anymore. You will need to generate new keys.**\n* Cleaned up dynamic database connection setting to use a single function call from the host model.\n* Deleting a server safely now continues even if the daemon reports a `HTTP/404` missing server error (requires `Daemon@0.4.0-beta.2.1`)\n* Changed behavior when modifying server allocation information. You can now remove the default allocation assuming you are passing a new allocation at the same time. Reduces the number of steps to change the default allocation for a server.\n* Environment setting commands now attempt to auto-quote strings with spaces in them, as well as comment lines that are edited to avoid manual changes being overwritten.\n* Version in footer of panel now displays correctly if panel is installed using Git rather than a download from source.\n* Mobile views are now more... viewable. Fixes `col-xs-6` usage throughout the Admin CP where it was intended to be `col-md-6`.\n* Node Configuration tokens and Download tokens are stored using the cache helpers rather than a database to speed up functions and make use of auto-expiration/deletion functions.\n* Old daemon routes using `/remote` have been changed to use `/daemon`, panel changes now reflect this.\n* Only display servers that a user is owner of or subuser of in the Admin CP rather than all servers if the user is marked as an admin.\n* Panel now sends all non-default allocations as `ALLOC_#__IP` and `ALLOC_#__PORT` to the daemon, as well as the location.\n\n### Added\n* Remote routes for daemon to contact in order to allow Daemon to retrieve updated service configuration files on boot. Centralizes services to the panel rather than to each daemon.\n* Basic service pack implementation to allow assignment of modpacks or software to a server to pre-install applications and allow users to update.\n* Users can now have a username as well as client name assigned to their account.\n* Ability to create a node through the CLI using `pterodactyl:node` as well as locations via `pterodactyl:location`.\n* New theme (AdminLTE) for front-end with tweaks to backend files to work properly with it.\n* Add support for PhraseApp's in-context editor\n* Notifications when a user is added or removed as a subuser for a server.\n* New cache policy for ServerPolicy to avoid making 15+ queries per page load when confirming if a user has permission to perform an action.\n* Ability to assign multiple allocations at once when creating a new server.\n* New `humanReadable` macro on `File` facade that accepts a file path and returns a human readable size. (`File::humanReadable(path, precision)`)\n* Added ability to edit database host details after creation on the system.\n* Login attempts and password reset requests are now protected by invisible ReCaptcha. This feature can be disabled with a `.env` variable.\n* Server listing for individual users is now searchable on the front-end.\n* Servers that a user is associated with as a subuser are now displayed in addition to owned servers when listing users in the Admin CP.\n* Ability to launch the console in a new window as an individual unit. https://s3.kelp.in/IrTyE.png\n* Server listing and view in Admin CP now shows the SFTP username/Docker container name.\n* Administrative server view includes link in navigation to go to server console/frontend management.\n* Added new scripts for service options that allows installation of software in a privileged Docker container on the node prior to marking a server as installed.\n* Added ability to reinstall a server using the currently assigned service and option.\n* Added ability to change a server's service and service option, as well as change pack assignments and other management services in that regard.\n* Added support for using a proxy such as Cloudflare with a node connection. Previously there was no way to tell the panel to connect over SSL without marking the Daemon as also using SSL.\n\n### Removed\n* Removed all old theme JS and CSS folders to cleanup and avoid confusion in the future.\n* Old API calls to `Server::create` will fail due to changed data structure.\n* Many old routes were modified to reflect new standards in panel, and many of the controller functions being called were also modified. This shouldn't really impact anyone unless you have been digging into the code and modifying things.\n* `Server::getUserDaemonSecret(Server $server)` was removed and replaced with `User::daemonSecret(Server $server)` in order to clean up models.\n* `Server::getByUUID()` was replaced with `Server::byUuid()` as well as various other functions through-out the Server model.\n* `Server::getHeaders()` was removed and replaced with `Server::getClient()` which returns a Guzzle Client with the correct headers already assigned.\n\n## v0.6.0-rc.1\n### Fixed\n* `[beta.2.1]` — Fixed a bug preventing the deletion of a server.\n* It is now possible to modify a server's disk limits after the server is created.\n* `[beta.2.1]` — Fixes a bug causing login issues and password reset failures when reCAPTCHA is enabled.\n* Fixes remote timing attack vulnerability due to hmac comparison in API middleware.\n* `[beta.2.1]` — Fixes bug requiring docker image field to be filled out when adding a service option.\n* `[beta.2.1]` — Fixes inability to mark a user as a non-admin once they were assigned the role.\n\n### Added\n* Added new scripts for service options that allows installation of software in a privileged Docker container on the node prior to marking a server as installed.\n* Added ability to reinstall a server using the currently assigned service and option.\n* Added ability to change a server's service and service option, as well as change pack assignments and other management services in that regard.\n* Added support for using a proxy such as Cloudflare with a node connection. Previously there was no way to tell the panel to connect over SSL without marking the Daemon as also using SSL.\n\n### Changed\n* Environment setting commands now attempt to auto-quote strings with spaces in them, as well as comment lines that are edited to avoid manual changes being overwritten.\n* Version in footer of panel now displays correctly if panel is installed using Git rather than a download from source.\n* Mobile views are now more... viewable. Fixes `col-xs-6` usage throughout the Admin CP where it was intended to be `col-md-6`.\n* Node Configuration tokens and Download tokens are stored using the cache helpers rather than a database to speed up functions and make use of auto-expiration/deletion functions.\n* Old daemon routes using `/remote` have been changed to use `/daemon`, panel changes now reflect this.\n* Only display servers that a user is owner of or subuser of in the Admin CP rather than all servers if the user is marked as an admin.\n\n## v0.6.0-beta.2.1\n### Fixed\n* `[beta.2]` — Suspended servers now show as suspended.\n* `[beta.2]` — Corrected the information when a task has not run yet.\n* `[beta.2]` — Fixes filemanager 404 when editing a file within a directory.\n* `[beta.2]` — Fixes exception in tasks when deleting a server.\n* `[beta.2]` — Fixes bug with Terarria and Voice servers reporting a `TypeError: Service is not a constructor` in the daemon due to a missing service configuration.\n* `[beta.2]` — Fixes password reset form throwing a MethodNotAllowed error when accessed.\n* `[beta.2]` — Fixes invalid password bug when attempting to change account email address.\n* `[beta.2]` — New attempt at fixing the issues when rendering files in the browser file editor on certain browsers.\n* `[beta.2]` — Fixes broken auto-deploy time checking causing no tokens to work.\n* `[beta.2]` — Fixes display of subusers after creation.\n* `[beta.2]` — Fixes bug throwing model not found exception when editing an existing subuser.\n\n### Changed\n* Deleting a server safely now continues even if the daemon reports a `HTTP/404` missing server error (requires `Daemon@0.4.0-beta.2.1`)\n* Changed behavior when modifying server allocation information. You can now remove the default allocation assuming you are passing a new allocation at the same time. Reduces the number of steps to change the default allocation for a server.\n\n### Added\n* Server listing and view in Admin CP now shows the SFTP username/Docker container name.\n* Administrative server view includes link in navigation to go to server console/frontend management.\n\n## v0.6.0-beta.2\n### Fixed\n* `[beta.1]` — Fixes task management system not running correctly.\n* `[beta.1]` — Fixes API endpoint for command sending missing the required class definition.\n* `[beta.1]` — Fixes panel looking for an old compiled classfile that is no longer used. This was causing errors relating to `missing class DingoAPI` when trying to upgrade the panel.\n* `[beta.1]` — Should fix render issues when trying to edit some files via the panel file editor.\n\n### Added\n* Ability to launch the console in a new window as an individual unit. https://s3.kelp.in/IrTyE.png\n\n## v0.6.0-beta.1\n### Fixed\n* `[pre.7]` — Fixes bug with subuser checkbox display.\n* `[pre.7]` — Fixes bug with injected JS that was causing `<!DOCTYPE html>` to be ignored in templates.\n* `[pre.7]` — Fixes exception thrown when trying to delete a node due to a misnamed model.\n* `[pre.7]` — Fixes username vanishing on failed login attempts.\n* `[pre.7]` — Terminal is now fixed to actually output all lines, rather than leaving one hanging in neverland until the browser is resized.\n\n### Added\n* Login attempts and password reset requests are now protected by invisible ReCaptcha. This feature can be disabled with a `.env` variable.\n* Server listing for individual users is now searchable on the front-end.\n* Servers that a user is associated with as a subuser are now displayed in addition to owned servers when listing users in the Admin CP.\n\n### Changed\n* Subuser permissions are now stored in `Permission::listPermissions()` to make views way cleaner and make adding to views significantly cleaner.\n* `[pre.7]` — Sidebar for file manager now is a single link rather than a dropdown.\n* Attempting to reset a password for an account that does not exist no longer returns an error, rather it displays a success message. Failed resets trigger a `Pterodactyl\\Events\\Auth\\FailedPasswordReset` event that can be caught if needed to perform other actions.\n* Servers are no longer queued for deletion due to the general hassle and extra logic required.\n* Updated all panel components to run on Laravel v5.4 rather than 5.3 which is EOL.\n* Routes are now handled in the `routes/` folder, and use a significantly cleaner syntax. Controller names and methods have been updated as well to be clearer as well as avoid conflicts with PHP reserved keywords.\n* API has been completely overhauled to use new permissions system. **Any old API keys will immediately become invalid and fail to operate properly anymore. You will need to generate new keys.**\n* Cleaned up dynamic database connection setting to use a single function call from the host model.\n* `[pre.7]` — Corrected a config option for spigot servers to set a boolean value as boolean, and not as a string.\n\n## v0.6.0-pre.7\n### Fixed\n* `[pre.6]` — Addresses misconfigured console queue that was still sending data way to quickly thus causing the console to explode on some devices when large amounts of data were sent.\n* `[pre.6]` — Fixes bug in allocation parsing for a node that prevented adding new allocations.\n* `[pre.6]` — Fixes typo in migrations that wouldn't save custom regex for non-required variables.\n* `[pre.6]` — Fixes auto-deploy checkbox on server creation causing validation error.\n\n## v0.6.0-pre.6\n### Fixed\n* `[pre.5]` — Console based server rebuild tool now actually rebuilds the servers with the correct information.\n* `[pre.5]` — Fixes typo and wrong docker container for certain applications.\n\n### Changed\n* Removed all old theme JS and CSS folders to cleanup and avoid confusion in the future.\n\n### Added\n* `[pre.5]` — Added foreign key to `pack_id` to ensure nothing eds up breaking there.\n\n## v0.6.0-pre.5\n### Changed\n* New theme applied to Admin CP. Many graphical changes were made, some data was moved around and some display data changed. Too much was changed to feasibly log it all in here. Major breaking changes or notable new features will be logged.\n* New server creation page now makes significantly less AJAX calls and is much quicker to respond.\n* Server and Node view pages wee modified to split tabs into individual pages to make re-themeing and modifications significantly easier, and reduce MySQL query loads on page.\n* `[pre.4]` — Service and Pack management overhauled to be faster, cleaner, and more extensible in the future.\n* Most of the backend `UnhandledException` display errors now include a clearer error that directs admins to the program's logs.\n* Table seeders for services now can be run during upgrades and will attempt to locate and update, or create new if not found in the database.\n* Many structural changes to the database and `Pterodactyl\\Models` classes that would flood this changelog if they were all included. All required migrations included to handle database changes.\n* `[pre.4]` — Service pack files are now stored in the database rather than on the host system to make updates easier.\n* Clarified details for database hosts to prevent users entering invalid account details, as well as renamed tables and columns relating to it to keep things clearer.\n* Updated all code to be Laravel compliant when using `env()` and moved to using `config()` throughout non `config/*.php` files.\n\n### Fixed\n* Fixes potential bug with invalid CIDR notation (ex: `192.168.1.1/z`) when adding allocations that could cause over 4 million records to be created at once.\n* `[pre.4]` — Fixes bug preventing server updates from occurring by the system due to undefined `Auth::user()` in the event listener.\n* `[pre.4]` — Fixes `Server::byUuid()` caching to actually clear the cache for *all* users, rather than the logged in user by using cache tags.\n* `[pre.4]` — Fixes server listing on frontend not displaying a page selector when more than 10 servers exist.\n* `[pre.4]` — Fixes non-admin users being unable to create personal API keys.\n* Fixes bug where daemon was unable to register that certain games had fully booted and were ready to play on.\n* Fixes bug causing MySQL user accounts to be corrupted when resetting a password via the panel.\n* `[pre.4]` — Multiple clients refreshing the console no longer clears the console for all parties involved... sorry about that.\n* `[pre.4]` — Fixes bug in environment setting script that would not remember defaults and try to re-assign values.\n\n### Added\n* Ability to assign multiple allocations at once when creating a new server.\n* New `humanReadable` macro on `File` facade that accepts a file path and returns a human readable size. (`File::humanReadable(path, precision)`)\n* Added ability to edit database host details after creation on the system.\n\n### Deprecated\n* Old API calls to `Server::create` will fail due to changed data structure.\n* Many old routes were modified to reflect new standards in panel, and many of the controller functions being called were also modified. This shouldn't really impact anyone unless you have been digging into the code and modifying things.\n\n## v0.6.0-pre.4\n### Fixed\n* `[pre.3]` — Fixes bug in cache handler that doesn't cache against the user making the request. Would have allowed for users to access servers not belonging to themselves in production.\n* `[pre.3]` — Fixes misnamed MySQL column that was causing the inability to delete certain port ranges from the database.\n* `[pre.3]` — Fixes bug preventing rebuilding server containers through the Admin CP.\n\n### Added\n* New cache policy for ServerPolicy to avoid making 15+ queries per page load when confirming if a user has permission to perform an action.\n\n## v0.6.0-pre.3\n### Fixed\n* `[pre.2]` — Fixes bug where servers could not be manually deployed to nodes due to a broken SQL call.\n* `[pre.2]` — Fixes inability to edit a server due to owner_id issues.\n* `[pre.2]` — Fixes bug when trying to add new subusers.\n* Emails sending with 'Pterodactyl Panel' as the from name. Now configurable by using `php artisan pterodactyl:mail` to update.\n* `[pre.2]` — Fixes inability to delete accounts due to SQL changes.\n* `[pre.2]` — Fixes bug with checking power-permissions that showed the wrong buttons. Also adds check back to sidebar to only show options a user can use.\n* `[pre.2]` — Fixes allocation listing on node allocations tab as well as bug preventing deletion of port.\n* `[pre.2]` — Fixes bug in services that prevented saving updated settings or creating new services.\n\n### Changed\n* `[pre.2]` — File Manager now displays relevant information on all screen sizes, and includes better button clicking mechanics for dropdown menu.\n* Reduced the number of database queries being executed when viewing a specific server. This is done by caching the query for up to 60 minutes in memcached.\n* User creation emails include more information and are sent by the event listener rather than the repository.\n* Account password reset emails now auto-fill the email when clicking the link.\n\n### Added\n* Notifications when a user is added or removed as a subuser for a server.\n\n## v0.6.0-pre.2\n### Fixed\n* `[pre.1]` — Fixes bug with database seeders that prevented correctly installing the panel.\n\n### Changed\n* `[pre.1]` — Moved around navigation bar on fronted to make it more obvious where logout and admin buttons were, as well as use the right icon for server listing.\n\n## v0.6.0-pre.1\n### Added\n* Remote routes for daemon to contact in order to allow Daemon to retrieve updated service configuration files on boot. Centralizes services to the panel rather than to each daemon.\n* Basic service pack implementation to allow assignment of modpacks or software to a server to pre-install applications and allow users to update.\n* Users can now have a username as well as client name assigned to their account.\n* Ability to create a node through the CLI using `pterodactyl:node` as well as locations via `pterodactyl:location`.\n* New theme (AdminLTE) for front-end with tweaks to backend files to work properly with it.\n* Add support for PhraseApp's in-context editor\n\n### Fixed\n* Bug causing error logs to be spammed if someone timed out on an ajax based page.\n* Fixes edge case where specific server names could cause daemon errors due to an invalid SFTP username being created by the panel.\n* Fixes sessions being removed on browser close, and set sessions to idle for up to 3 hours before being marked as expired.\n\n### Changed\n* Admin API and base routes for user management now define the fields that should be passed to repositories rather than passing all fields.\n* User model now defines mass assignment fields using `$fillable` rather than `$guarded`.\n* 2FA checkpoint on login is now its own page, and not an AJAX based call. Improves security on that front.\n* Updated Server model code to be more efficient, as well as make life easier for backend changes and work.\n\n### Deprecated\n* `Server::getUserDaemonSecret(Server $server)` was removed and replaced with `User::daemonSecret(Server $server)` in order to clean up models.\n* `Server::getByUUID()` was replaced with `Server::byUuid()` as well as various other functions through-out the Server model.\n* `Server::getHeaders()` was removed and replaced with `Server::getClient()` which returns a Guzzle Client with the correct headers already assigned.\n\n## v0.5.6 (Bodacious Boreopterus)\n### Added\n* Added the following languages: Estonian `et`, Dutch `nl`, Norwegian `nb` (partial), Romanian `ro`, and Russian `ru`. Interested in helping us translate the panel into more languages, or improving existing translations? Contact us on Discord and let us know.\n* Added missing `strings.password` to language file for English.\n* Allow listing of users from the API by passing either the user ID or their email.\n\n### Fixed\n* Fixes bug where assigning a variable a default value (or valid value) of `0` would cause the panel to reject the value thinking it did not exist.\n* Addresses potential for crash by limiting total ports that can be assigned per-range to 2000.\n* Fixes server names requiring at minimum 4 characters. Name can now be 1 to 200 characters long. :pencil2:\n* Fixes bug that would allow adding the owner of a server as a subuser for that same server.\n* Fixes bug that would allow creating multiple subusers with the same email address.\n* Fixes bug where Sponge servers were improperly tagged as a spigot server in the daemon causing issues when booting or modifying configuration files.\n* Use transpiled ES6 -> ES5 filemanager code in browsers.\n* Fixes service option name displaying the name of a newly added variable after the variable is added and until the page is refreshed. (see #208)\n\n### Changed\n* Filemanager and EULA checking javascript is now written in pure ES6 code rather than as a blade-syntax template. This allows the use of babel to transpile into ES5 as a minified version.\n\n## v0.5.5 (Bodacious Boreopterus)\n### Added\n* New API route to return allocations given a server ID. This adds support for a community-driven WHMCS module :rocket: available [here](https://github.com/hammerdawn/Pterodactyl-WHMCS).\n\n### Fixed\n* Fixes subuser display when trying to edit an existing subuser.\n\n## v0.5.4 (Bodacious Boreopterus)\n### Added\n* Changing node configuration values now automatically makes a call to the daemon and updates the configuration there. Changing daemon tokens now does not require any intervention, and takes effect immediately. SSL & Port configurations will still require a daemon reboot.\n* New button in file manager that triggers the right click menu to enable support on mobile devices and those who cannot right click (blessed be them).\n* Support for filtering users when listing all users on the system.\n* Container ID and User ID on the daemon are now shown when viewing a server in the panel.\n\n### Changed\n* File uploads now account for a maximum file size that is assigned for the daemon, and gives cleaner errors when that limit is reached.\n* File upload limit can now be controlled from the panel.\n* Updates regex and default values for some Minecraft services to reflect current technology.\n\n### Fixed\n* Fixes potential for generated password to not meet own validation requirements.\n* Fixes some regex checking issues with newer versions of Minecraft.\n\n## v0.5.3 (Bodacious Boreopterus)\n### Fixed\n* Fixed an error that occurred when viewing a node listing when no nodes were created yet due to a mis-declared variable. Also fixes a bug that would have all nodes trying to connect to the daemon using the same secret token on the node listing, causing only the last node to display properly.\n* Fixes a bug that displayed the panel version rather than the daemon version when viewing a node.\n* Fixes a multiplicator being applied to an overallocation field rather than a storage space field when adding a node.\n\n### Changed\n* Added a few new configuration variables for nodes to the default config, as well as a variable that will be used in future versions of the daemon.\n\n## v0.5.2 (Bodacious Boreopterus)\n### Fixed\n* Time axis on server graphs is corrected to show the minutes rather than the current month.\n* Node deletion now works correctly and deletes allocations as well.\n* Fixes a bug that would leave orphaned databases on the system if there was an error during creation.\n* Fixes an issue that could occur if a UUID contained `#e#` formatting within it when it comes to creating databases.\n* Fixed node status display to account for updated daemon security changes.\n* Fixes default language being selected as German (defaults to English now).\n* Fixes bug preventing the deletion of database servers.\n\n### Changed\n* Using `node:<name>` when filtering servers now properly filters the servers by node name, rather than looking for the node ID.\n* Using `owner:<email>` when filtering servers now properly filters by the owner's email rather than ID.\n* Added some quick help buttons to the admin index page for getting support or checking the documentation.\n* Panel now displays `Pterodactyl Panel` as the company name if one is not set.\n\n### Added\n* Added basic information about the daemon when viewing a node, including the host OS and version, CPU count, and the daemon version.\n* Added version checking for the daemon and panel that alerts admins when daemons or the panel is out of date.\n* Added multiplicator support to certain memory and disk fields that allow users to enter `10g` and have it converted to MB automatically.\n\n## v0.5.1 (Bodacious Boreopterus)\n### Fixed\n* Fixes a bug that allowed a user to bypass 2FA authentication if using the correct username and password for an account.\n\n## v0.5.0 (Bodacious Boreopterus)\nAfter nearly a month in the works, version `v0.5.0` is finally here! 🎉\n\n### Added\n* Foreign keys are now enabled on all tables that the panel makes use of to prevent accidental data deletion when associated with other tables.\n* Javascript changes to prevent crashing browsers when large quantities of data are sent over the websocket to the console. Includes a small popover message on the console to alert users that it is being throttled.\n* Support for 'ARK: Survival Evolved' servers through the panel.\n* Support for filtering servers within Admin CP to narrow down results by name, email, allocation, or defined fields.\n* Setup scripts (user, mail, env) now support argument flags for use in containers and other non-terminal environments.\n* New API endpoints for individual users to control their servers with at `/api/me/*`.\n* Typeahead support for owner email when adding a new server.\n* Scheduled command to clear out task log every month (configurable timespan).\n* Support for allocating a FQDN as an allocation (panel will convert to IP and assign the FQDN as the alias automatically).\n* Refresh files button in file manager to reload file listing without full page refresh.\n* Added support for file copying through the file manager. [#127](https://github.com/Pterodactyl/Panel/issues/127)\n* Creating new files and folders directly from the right-click dropdown menu in the file manager.\n* Support for setting custom `user_id` when using the API to create users.\n* Support for creating a new server through the API by passing a user ID rather than an email.\n* Passing `?daemon=true` flag to [`/api/servers/:id`](https://pterodactyl.readme.io/v0.5.0/reference#single-server) will return the daemon stats as well as the `daemon_token` if using HTTPS.\n* Small check for current node status that shows up to the left of the name when viewing a listing of all nodes.\n* Support for creating server without having to assign a node and allocation manually. Simply select the checkbox or pass `auto_deploy=true` to the API to auto-select a node and allocation given a location.\n* Support for setting IP Aliases through the panel on the node overview page. Also cleaned up allocation removal.\n* Support for renaming files through the panel's file manager.\n\n### Changed\n* Servers are now queued for deletion to allow for cancellation of deletion, as well as run in the background to speed up page loading.\n* Switched to new graphing library to make graphs less... broken.\n* Rebuild triggers are only sent to the node if there is actually something changed that requires a rebuild.\n* Dependencies are now hard-coded into the `composer.json` file to prevent users installing slightly different versions with different features or bugs.\n* Server related tasks now use the lowest priority queue to prevent clogging the pipes when there are more important tasks to be run by the panel.\n* Dates displayed in the file manager are now more user friendly.\n* Creating a user, server, or node now returns `HTTP/1.1 200` and a JSON element with the user/server/node's ID.\n* Environment setting script is much more user friendly and does not require an excessive amount of clicking and typing.\n* File upload method switched from BinaryJS to Socket.io implementation to fix bugs as well as be a little speedier and allow upload throttling.\n* `Server::getbyUUID()` now accepts either the `uuidShort` or full-length `uuid` for server identification.\n* API keys are tied to individual users and no longer created through the Admin CP.\n* **ALL** API routes previously returning paginated result sets, or result sets nested inside a descriptive block (e.g. `servers:`) have been changed to return a single array of all associated items. Please see the [updated documentation](https://pterodactyl.readme.io/v0.5.0/reference) for how this change might effect your API use.\n* API route for [`/api/users/:id`](https://pterodactyl.readme.io/v0.5.0/reference#single-user) now includes an array of all servers the user is set as the owner of.\n* Prevent clicking server start button until server is completely off, not just stopping.\n* Upon successful creation of a node it will redirect to the allocation tab and display a clearer message to add allocations.\n* Trying to add a new node if no location exists redirects user to location management page and alerts them to add a location first.\n* `Server\\AjaxController@postSetConnection` is now `Server\\AjaxController@postSetPrimary` and accepts one post parameter of `allocation` rather than a combined `ip:port` value.\n* Port allocations on server view are now cleaner and should make more sense.\n* Improved File Manager\n  * Rewritten Javascript to load, rename, and handle other file actions.\n  * Uses Ace Editor for editing files rather than a non-formatted textarea\n  * File actions that were previously icons to the right are now contained in a menu that appears when right-clicking a file or folder.\n\n### Fixed\n* Fixes bug where resetting a user password through the login form would not hold passwords to the same requirements as the rest of the panel (mixed case and at least one numeric character).\n* Fixes bug where no error would be displayed when adding a new server with an invalid owner email.\n* Fixes a bug that could allow an admin to delete the default allocation for a server causing all sorts of issues.\n* Databases assigned to a server are now actually deleted when a server is removed.\n* Server overview listing the location short-code as the name of the node.\n* Server task manager only sending commands every 5 minutes at the quickest.\n* Fixes additional port allocation from removing the wrong row when clicking 'x'.\n* Updated Socket.io client file to version `1.5.0` to match the latest release. Correlates with setting hard dependencies in the Daemon.\n* Team Fortress named 'Insurgency' in panel in database seeder. ([#96](https://github.com/Pterodactyl/Panel/issues/96), PR by [@MeltedLux](https://github.com/MeltedLux))\n* Server allocation listing display now showing the connection IP unless an alias was assigned.\n* Fixed bug where node allocation would appear to be successful but actual encounter an error. Made it cleared how to enter ports.\n* Fixes display where an extra space was added to the end of SFTP passwords when they were copied from the panel. [#116](https://github.com/Pterodactyl/Panel/issues/116), thanks [@OrangeJuiced](https://github.com/OrangeJuiced)\n* Fixes a bug that prevented viewing database servers if not assigned to a node.\n* Checkboxes previously not displayed checkmarks are now fixed.\n\n### Fixed (bugs from v0.5.0-rc.2)\n* Fixes a bug causing password resets to fail for server databases.\n* Fixes a bug during installation that would prevent the 'Ark: Survival Evolved' service option from being added to the panel unless it was an update.\n* Fixes constant scrolling to bottom of console; console now only scrolls to the bottom on new data.\n\n### Removed\n* Removed active session management table displaying the last location of a session.\n* Removed online player listing due to inconsistency in query library and an assortment of query related bugs. This will return in future versions when we get it working correctly.\n\n## v0.5.0-rc.2 (Bodacious Boreopterus)\n\n### Fixed\n* Fixes a bug that would cause MySQL errors when attempting to install the panel rather than upgrading.\n\n## v0.5.0-rc.1 (Bodacious Boreopterus)\n\n### Added\n* Foreign keys are now enabled on all tables that the panel makes use of to prevent accidental data deletion when associated with other tables.\n* Javascript changes to prevent crashing browsers when large quantities of data are sent over the websocket to the console. Includes a small popover message on the console to alert users that it is being throttled.\n* Support for 'ARK: Survival Evolved' servers through the panel.\n\n### Fixed\n* Fixes bug where resetting a user password through the login form would not hold passwords to the same requirements as the rest of the panel (mixed case and at least one numeric character).\n* Fixes misnamed environment variable for Bungeecord Servers (`BUNGE_VERSION` -> `BUNGEE_VERSION`).\n* Fixes bug where no error would be displayed when adding a new server with an invalid owner email.\n* Fixes a bug that could allow an admin to delete the default allocation for a server causing all sorts of issues.\n* Databases assigned to a server are now actually deleted when a server is removed.\n* Fixes file uploads being improperly throttled.\n\n### Changed\n* Servers are now queued for deletion to allow for cancellation of deletion, as well as run in the background to speed up page loading.\n* Switched to new graphing library to make graphs less... broken.\n* Rebuild triggers are only sent to the node if there is actually something changed that requires a rebuild.\n* Dependencies are now hard-coded into the `composer.json` file to prevent users installing slightly different versions with different features or bugs.\n* Server related tasks now use the lowest priority queue to prevent clogging the pipes when there are more important tasks to be run by the panel.\n* Decompressing files now shows a pop-over box that does not dismiss until it is complete.\n* Dates displayed in the file manager are now more user friendly.\n\n### Removed\n* Removed online player listing due to inconsistency in query library and an assortment of query related bugs. This will return in future versions when we get it working correctly.\n\n## v0.5.0-pre.3 (Bodacious Boreopterus)\n\n### Added\n* Return node configuration from remote API by using `/api/nodes/{id}/config` endpoint. Only accepts SSL connections.\n* Support for filtering servers within Admin CP to narrow down results by name, email, allocation, or defined fields.\n* Setup scripts (user, mail, env) now support argument flags for use in containers and other non-terminal environments.\n* New API endpoints for individual users to control their servers with at `/api/me/*`.\n* Typeahead support for owner email when adding a new server.\n* Scheduled command to clear out task log every month (configurable timespan).\n* Support for allocating a FQDN as an allocation (panel will convert to IP and assign the FQDN as the alias automatically).\n* Refresh files button in file manager to reload file listing without full page refresh.\n\n### Changed\n* Creating a user, server, or node now returns `HTTP/1.1 200` and a JSON element with the user/server/node's ID.\n* Environment setting script is much more user friendly and does not require an excessive amount of clicking and typing.\n* File upload method switched from BinaryJS to Socket.io implementation to fix bugs as well as be a little speedier and allow upload throttling.\n* `Server::getbyUUID()` now accepts either the `uuidShort` or full-length `uuid` for server identification.\n* API keys are tied to individual users and no longer created through the Admin CP.\n\n### Fixed\n* Server overview listing the location short-code as the name of the node.\n* Server task manager only sending commands every 5 minutes at the quickest.\n* Fixes additional port allocation from removing the wrong row when clicking 'x'.\n\n## v0.5.0-pre.2 (Bodacious Boreopterus)\n\n### Added\n* Added support for file copying through the file manager. [#127](https://github.com/Pterodactyl/Panel/issues/127)\n* Creating new files and folders directly from the right-click dropdown menu in the file manager.\n* Support for setting custom `user_id` when using the API to create users.\n* Support for creating a new server through the API by passing a user ID rather than an email.\n* Passing `?daemon=true` flag to [`/api/servers/:id`](https://pterodactyl.readme.io/v0.5.0/reference#single-server) will return the daemon stats as well as the `daemon_token` if using HTTPS.\n* Small check for current node status that shows up to the left of the name when viewing a listing of all nodes.\n\n### Changed\n* Support for sub-folders within the `getJavascript()` route for servers.\n* **ALL** API routes previously returning paginated result sets, or result sets nested inside a descriptive block (e.g. `servers:`) have been changed to return a single array of all associated items. Please see the [updated documentation](https://pterodactyl.readme.io/v0.5.0/reference) for how this change might effect your API use.\n* API route for [`/api/users/:id`](https://pterodactyl.readme.io/v0.5.0/reference#single-user) now includes an array of all servers the user is set as the owner of.\n\n### Fixed\n* File manager would do multiple up-down-up-down loading actions if you escaped renaming a file. Fixed the binding issue. [#122](https://github.com/Pterodactyl/Panel/issues/122)\n* File manager actions would not trigger properly if text in a row was used to right-click from.\n* File manager rename field would not disappear when pressing the escape key in chrome. [#121](https://github.com/Pterodactyl/Panel/issues/121)\n* Fixes bug where server image assigned was not being saved to the database.\n* Fixes instances where selecting auto-deploy would not hide the node selection dropdown.\n* Fixes bug in auto-deployment that would throw a `ModelNotFoundException` if the location passed was not valid. Not normally an issue in the panel, but caused display issues for the API.\n* Updated Socket.io client file to version `1.5.0` to match the latest release. Correlates with setting hard dependencies in the Daemon.\n\n## v0.5.0-pre.1 (Bodacious Boreopterus)\n\n### Added\n* Support for creating server without having to assign a node and allocation manually. Simply select the checkbox or pass `auto_deploy=true` to the API to auto-select a node and allocation given a location.\n* Support for setting IP Aliases through the panel on the node overview page. Also cleaned up allocation removal.\n* Support for renaming files through the panel's file manager.\n\n### Changed\n* Prevent clicking server start button until server is completely off, not just stopping.\n* Upon successful creation of a node it will redirect to the allocation tab and display a clearer message to add allocations.\n* Trying to add a new node if no location exists redirects user to location management page and alerts them to add a location first.\n* `Server\\AjaxController@postSetConnection` is now `Server\\AjaxController@postSetPrimary` and accepts one post parameter of `allocation` rather than a combined `ip:port` value.\n* Port allocations on server view are now cleaner and should make more sense.\n* Improved File Manager\n  * Rewritten Javascript to load, rename, and handle other file actions.\n  * Uses Ace Editor for editing files rather than a non-formatted textarea\n  * File actions that were previously icons to the right are now contained in a menu that appears when right-clicking a file or folder.\n\n### Fixed\n* Team Fortress named 'Insurgency' in panel in database seeder. ([#96](https://github.com/Pterodactyl/Panel/issues/96), PR by [@MeltedLux](https://github.com/MeltedLux))\n* Server allocation listing display now showing the connection IP unless an alias was assigned.\n* Fixed bug where node allocation would appear to be successful but actual encounter an error. Made it cleared how to enter ports.\n* Fixes display where an extra space was added to the end of SFTP passwords when they were copied from the panel. [#116](https://github.com/Pterodactyl/Panel/issues/116), thanks [@OrangeJuiced](https://github.com/OrangeJuiced)\n\n### Removed\n* Removed active session management table displaying the last location of a session.\n\n## v0.4.1 (Articulate Aerotitan)\n\n### Changed\n* Overallocate fields are now auto-filled with a value of `0`\n\n### Fixed\n* Wrong error highlighting of overallocate fields on Node creation ([#90](https://github.com/Pterodactyl/Panel/issues/90), thanks [@schrej](https://github.com/schrej))\n* Server link in navbar directed to 404 link (PR by [@Randomfish132](https://github.com/Randomfish132))\n* Composer fails to finish ([#92](https://github.com/Pterodactyl/Panel/issues/92), PR by [@schrej](https://github.com/schrej), thanks [@parkervcp](https://github.com/parkervcp))\n\n## v0.4.0 (Arty Aerodactylus)\n\n### Added\n* Task scheduler supporting customized CRON syntax or dropdown selected options. (currently only support command and power options)\n* Adds support for changing per-server database passwords from the panel.\n* Allows for use of IP rather than a FQDN if the node is not using SSL\n* Adds support for IP Aliases on display pages for users. This makes it possible to use GRE tunnels and still show the user what IP they should be connecting to.\n* Adds support for suspending servers\n* Adds support for viewing SFTP password within the panel ([#74](https://github.com/Pterodactyl/Panel/issues/74), thanks [@ET-Bent](https://github.com/ET-Bent))\n* Improved API with support for server suspension and build modification.\n* Improved service management and setup on first install.\n* New terminal that supports ANSI color codes as well as cleaner output. You can also simply type `start` or `boot` to start your server rather than having to use the start button.\n\n### Fixed\n* Fixes password auto-generation on 'Manage Server' page. ([#67](https://github.com/Pterodactyl/Panel/issues/67), thanks [@ET-Bent](https://github.com/ET-Bent))\n* Fixes some overly verbose user output when an error occurs\n* Prevent calling daemon until database call has been confirmed when changing default connection.\n* Fixes a few display issues relating to subusers and database management.\n* Fixes the server name in the header not linking to the server correctly. ([#79](https://github.com/Pterodactyl/Panel/issues/79), thanks [@xX1bumblebee1Xx](https://github.com/xX1bumblebee1Xx))\n* Fixes bug where non-admins could not see command box on servers. ([#83](https://github.com/Pterodactyl/Panel/issues/83), thanks [@xX1bumblebee1Xx](https://github.com/xX1bumblebee1Xx))\n* Fixes bug where files could not be uploaded through the \"click and select\" system, only through \"drag and drop.\" ([#82](https://github.com/Pterodactyl/Panel/issues/83), thanks [@xX1bumblebee1Xx](https://github.com/xX1bumblebee1Xx))\n* Fixes a bug where new files could not be created through the panel for a server. ([#85](https://github.com/Pterodactyl/Panel/issues/85), thanks [@xX1bumblebee1Xx](https://github.com/xX1bumblebee1Xx))\n* Fixes the exception handler to properly display and log exceptions that might occur rather than leaving a vague error. ([#81](https://github.com/Pterodactyl/Panel/issues/83))\n\n### Changed\n* Update Laravel to version `5.3` and update dependencies.\n\n### Deprecated\n* Requires Pterodactyl Daemon `v0.2.*`\n\n### Security\n* Fixes listing of server variables for server. Previously a bug made it possible to view settings for all servers, even if the user didn't own that server. ([#69](https://github.com/Pterodactyl/Panel/issues/69))\n"
  },
  {
    "path": "CONTRIBUTING.md",
    "content": "# 贡献\n\n**关于新功能的拉取请求**  \n翼龙（Pterodactyl）项目**不接受未经项目维护者在 GitHub discussions 中事先批准的新功能**拉取请求。由于这类复杂的拉取请求往往需要投入大量时间和精力进行审查，为保障项目质量，我们将新功能的工作范围限定在核心项目团队内部完成。\n\n对于修复现有缺陷或改进**已在问题跟踪器中创建对应工单**的功能的拉取请求，我们仍会接受并审核。这类请求的范围通常更加明确，且仅针对现有逻辑进行优化。\n\n## 关于人工智能辅助\n\n若您在为翼龙项目进行开发时使用任何形式的人工智能辅助工具，**必须在相关审查的拉取请求中明确声明**，并说明具体用途。所有与社区的互动内容必须由人工撰写。**禁止使用人工智能撰写任何拉取请求的标题、描述或评论**，也不得使用人工智能参与 GitHub Discussions 社区的交流。\n\n## 负责任的安全披露\n\n本项目结构复杂，涉及众多动态组件。我们致力于保障系统安全，并欢迎您自行审查项目代码。但请您体谅其他软件使用者，切勿公开披露安全问题。请查阅 [`SECURITY.md`](/SECURITY.md) 了解如何向团队报告安全问题。\n\n## 联系我们\n\n您可以通过以下渠道找到我们：  \n- 主要在 GitHub 平台活跃，如遇程序错误或其他问题，请在此提交工单\n- 功能请求、常规咨询或软件帮助请使用 [GitHub Discussions](https://github.com/orgs/pterodactyl/discussions/categories/feature-requests)\n- 也可通过 [Discord](https://discord.gg/pterodactyl) 与我们交流\n\n**此内容为翼龙官方，与翼龙中国无关，所以在询问他们时用英语交流**\n"
  },
  {
    "path": "Dockerfile",
    "content": "# Stage 0:\n# Build the assets that are needed for the frontend. This build stage is then discarded\n# since we won't need NodeJS anymore in the future. This Docker image ships a final production\n# level distribution of Pterodactyl.\nFROM --platform=$TARGETOS/$TARGETARCH node:22-alpine\nWORKDIR /app\nCOPY . ./\nRUN yarn install --frozen-lockfile \\\n    && yarn run build:production\n\n# Stage 1:\n# Build the actual container with all of the needed PHP dependencies that will run the application.\nFROM --platform=$TARGETOS/$TARGETARCH php:8.3-fpm-alpine\nWORKDIR /app\nCOPY . ./\nCOPY --from=0 /app/public/assets ./public/assets\nRUN apk add --no-cache --update ca-certificates dcron curl git supervisor tar unzip nginx libpng-dev libxml2-dev libzip-dev certbot certbot-nginx mysql-client \\\n    && docker-php-ext-configure zip \\\n    && docker-php-ext-install bcmath gd pdo_mysql zip \\\n    && curl -sS https://getcomposer.org/installer | php -- --install-dir=/usr/local/bin --filename=composer \\\n    && cp .env.example .env \\\n    && mkdir -p bootstrap/cache/ storage/logs storage/framework/sessions storage/framework/views storage/framework/cache \\\n    && chmod 777 -R bootstrap storage \\\n    && composer install --no-dev --optimize-autoloader \\\n    && rm -rf .env bootstrap/cache/*.php \\\n    && mkdir -p /app/storage/logs/ \\\n    && chown -R nginx:nginx .\n\nRUN rm /usr/local/etc/php-fpm.conf \\\n    && echo \"* * * * * /usr/local/bin/php /app/artisan schedule:run >> /dev/null 2>&1\" >> /var/spool/cron/crontabs/root \\\n    && echo \"0 23 * * * certbot renew --nginx --quiet\" >> /var/spool/cron/crontabs/root \\\n    && sed -i s/ssl_session_cache/#ssl_session_cache/g /etc/nginx/nginx.conf \\\n    && mkdir -p /var/run/php /var/run/nginx\n\nCOPY .github/docker/default.conf /etc/nginx/http.d/default.conf\nCOPY .github/docker/www.conf /usr/local/etc/php-fpm.conf\nCOPY .github/docker/supervisord.conf /etc/supervisord.conf\n\nEXPOSE 80 443\nENTRYPOINT [ \"/bin/ash\", \".github/docker/entrypoint.sh\" ]\nCMD [ \"supervisord\", \"-n\", \"-c\", \"/etc/supervisord.conf\" ]\n"
  },
  {
    "path": "LICENSE.md",
    "content": "# The MIT License (MIT)\n\n```\nPterodactyl®\nCopyright © Dane Everitt <dane@daneeveritt.com> and contributors\n\nPermission is hereby granted, free of charge, to any person obtaining a copy\nof this software and associated documentation files (the \"Software\"), to deal\nin the Software without restriction, including without limitation the rights\nto use, copy, modify, merge, publish, distribute, sublicense, and/or sell\ncopies of the Software, and to permit persons to whom the Software is\nfurnished to do so, subject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in all\ncopies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\nFITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\nAUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\nLIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\nSOFTWARE.\n```\n"
  },
  {
    "path": "README.md",
    "content": "[![Logo Image](https://api.pterodactyl.top/logos/new/pterodactyl_china_logo.png)](https://pterodactyl.top)\n\n![GitHub Stars](https://img.shields.io/github/stars/pterodactyl-china/panel?style=for-the-badge&logo=appveyor)\n![GitHub Releases](https://img.shields.io/github/v/release/pterodactyl-china/panel?style=for-the-badge&logo=appveyor)\n![GitHub Releases](https://img.shields.io/github/downloads/pterodactyl-china/panel/total?style=for-the-badge)\n![GitHub Releases Latest](https://img.shields.io/github/downloads/pterodactyl-china/panel/latest/total?style=for-the-badge)\n![Alt](https://repobeats.axiom.co/api/embed/9e3f7d2c6db2f248adf85b55e7ebd4a3a4911bdf.svg \"Repobeats analytics image\")\n\n# 翼龙面板\n\nPterodactyl® 是一个免费的开源游戏服务器管理面板，使用 PHP、React 和 Go 构建。Pterodactyl 在设计时考虑了安全性，在隔离的 Docker 容器中运行所有游戏服务器，同时向最终用户展示了美观直观的 UI。\n\n不要再安于现状了。让该面板成为您游戏服务器是上上之选。\n\n**此仓库将实时同步上游进行汉化 , 发布的 Releases 均通过 Github Actions 的构建测试，并在发布前会经过本地环境测试。**\n\n![Image](https://cdn.pterodactyl.io/site-assets/pterodactyl_v1_demo.gif)\n\n## 翼龙中国文档\n\n* [Panel 文档](https://pterodactyl.top/panel/1.0/getting_started.html)\n* [Wings 文档](https://pterodactyl.top/wings/1.0/installing.html)\n* [社区指南文档](https://pterodactyl.top/community/about.html)\n* 或者，[通过 腾讯频道](https://pd.qq.com/s/2schz3it0) 或 [通过 翼龙中国社区](https://bbs.pterodactyl.top) 来获得更多帮助\n\n## 赞助商\n\n衷心感谢以下赞助商为翼龙中国的发展提供资金支持。\n[有兴趣成为赞助商吗？](https://afdian.com/a/vlssu)\n\n| 公司/个人 | 关于 |\n| ------- | ----- |\n| [**VLssu公益服**](https://vlssu.cn) | 一个热衷于美好社区的我的世界服务器。 |\n| [**速特互联**](https://www.suteidc.com) | 我的世界服务器出租，支持一键安装MOD插件 |\n| [**裕米云计算**](https://comcorn.cn) | COMCORN公共服务平台，提供优质项目云资源支持 |\n\n### 支持的游戏\n\n我们通过使用 Docker 容器隔离每个实例来支持各种游戏，为您提供强大的功能\n在全球范围内托管您的游戏，而不必让每台物理机器都因安装额外的依赖而变得臃肿。\n\n我们支持的一些核心游戏包括:\n\n* Minecraft（我的世界） — 包括 Paper, Sponge, Bungeecord, Waterfall, 等....\n* Rust （腐蚀）\n* Terraria （泰拉瑞亚）\n* Teamspeak\n* Mumble\n* Team Fortress 2 （军团要塞2）\n* Counter Strike: Global Offensive （反恐精英：全球攻势）\n* Garry's Mod （盖瑞的模组）\n* ARK: Survival Evolved （方舟：生存进化）\n\n除了我们支持的标准游戏预设外，我们的社区还在不断突破这个软件的极限\n社区提供的游戏还有很多。其中一些游戏包括：\n\n* Factorio （异星工厂）\n* San Andreas: MP\n* Pocketmine MP\n* Squad （战术小队）\n* FiveM\n* Xonotic\n* Starmade\n* Discord ATLBot, and most other Node.js/Python discord bots\n* [更多...](https://pterodactyleggs.com)\n\n## 开源协议\n\nPterodactyl® Copyright © 2015 - 2022 Dane Everitt and contributors.     \nCode released under the [MIT License](./LICENSE.md).\n\n此本地化项目同样遵循 翼龙开源协议 与 MIT 开源协议   \n引用资源文件/汉化文本请注意作者署名。\n"
  },
  {
    "path": "SECURITY.md",
    "content": "此内容为翼龙官方，与翼龙中国无关\n# 安全策略\n\n## 支持的版本\n\n翼龙（Pterodactyl）仅为面板（Panel）和翼（Wings）软件的最新 `major.minor` 主次版本提供安全支持。\n如果在旧版本中发现安全漏洞，但无法在受支持的版本中复现，该漏洞将不被受理。\n此外，在未发布的代码中发现的安全问题将会被处理，但通常不会为此单独发布安全公告。\n\n例如，如果面板（Panel）的最新版本是 `1.2.5`，那么我们仅接受发生在版本 `>= 1.2.x`（即大于等于1.2.x版本）的面板软件上的安全漏洞报告。面板与翼（Wings）拥有各自的版本号，但它们的版本通常互相匹配。\n\n## 漏洞报告\n\n请使用我们的 GitHub 安全报告机制，以便在您发现任何安全问题时快速通知团队，\n或发送电子邮件至 `security@pterodactyl.io` (请使用英文)并附上您报告的详细信息。\n\n我们会尽最大努力尽快响应，但由于需要内部同步并评估报告的严重性及影响范围，可能需要一至两天时间。\n**请注意**：报告敏感的安全问题时，切勿使用公开渠道或 GitHub Issues。\n\n根据我们的处理流程，我们将为受影响的版本创建安全公告，并通常在发布修复版本后的**两至四周内**进行公开披露。\n"
  },
  {
    "path": "app/Console/Commands/Environment/AppSettingsCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Environment;\n\nuse Illuminate\\Console\\Command;\nuse Illuminate\\Contracts\\Console\\Kernel;\nuse Pterodactyl\\Traits\\Commands\\EnvironmentWriterTrait;\n\nclass AppSettingsCommand extends Command\n{\n    use EnvironmentWriterTrait;\n\n    public const CACHE_DRIVERS = [\n        'redis' => 'Redis (推荐)',\n        'memcached' => 'Memcached',\n        'file' => 'Filesystem',\n    ];\n\n    public const SESSION_DRIVERS = [\n        'redis' => 'Redis (推荐)',\n        'memcached' => 'Memcached',\n        'database' => 'MySQL 数据库',\n        'file' => 'Filesystem',\n        'cookie' => 'Cookie',\n    ];\n\n    public const QUEUE_DRIVERS = [\n        'redis' => 'Redis (推荐)',\n        'database' => 'MySQL 数据库',\n        'sync' => 'Sync',\n    ];\n\n    protected $description = '进行面板的基本环境配置.';\n\n    protected $signature = 'p:environment:setup\n                            {--new-salt : 是否为 HashIDs 生成新 Salt,若生成新 Salt 当前用户所有密码验证都会失效，需要重设密码.}\n                            {--author= : 在此实例上创建的服务应链接到的电子邮箱.}\n                            {--url= : 运行此面板的 URL 例如 https://pterodactyl.cn}\n                            {--timezone= : 用于面板时间的时区 北京时区为 Asia/Shanghai.}\n                            {--cache= : 要使用的缓存驱动程序后端 不懂就用默认值.}\n                            {--session= : 要使用的会话驱动程序后端 不懂就用默认值.}\n                            {--queue= : 要使用的队列驱动程序后端 不懂就用默认值.}\n                            {--redis-host= : 用于连接的 Redis 主机.}\n                            {--redis-pass= : 用于连接 Redis 的密码.}\n                            {--redis-port= : 连接到 Redis 的端口.}\n                            {--settings-ui= : 启用或禁用设置 UI.}\n                            {--telemetry= : 启用或禁用匿名遥测.}';\n\n    protected array $variables = [];\n\n    /**\n     * AppSettingsCommand constructor.\n     */\n    public function __construct(private Kernel $console)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Handle command execution.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\PterodactylException\n     */\n    public function handle(): int\n    {\n        if (empty(config('hashids.salt')) || $this->option('new-salt')) {\n            $this->variables['HASHIDS_SALT'] = str_random(20);\n        }\n\n        $this->output->comment('提供预设导出中作者使用的电子邮箱地址.');\n        $this->variables['APP_SERVICE_AUTHOR'] = $this->option('author') ?? $this->ask(\n            '预设作者邮箱',\n            config('pterodactyl.service.author', 'unknown@unknown.com')\n        );\n\n        if (!filter_var($this->variables['APP_SERVICE_AUTHOR'], FILTER_VALIDATE_EMAIL)) {\n            $this->output->error('提供的邮箱地址无效.');\n\n            return 1;\n        }\n\n        $this->output->comment('面板 URL 取决于是否使用 SSL 安全连接必须以 https:// 或 http:// 开头. 如果此处填写错误，您的电子邮箱和其他内容将被链接到错误的地址.');\n        $this->variables['APP_URL'] = $this->option('url') ?? $this->ask(\n            '应用 URL',\n            config('app.url', 'https://example.com')\n        );\n\n        $this->output->comment('时区应与 PHP 支持的时区之一匹配 北京时区是 Asia/Shanghai。如果不确定，请参考 https://php.net/manual/zh/timezones.php.');\n        $this->variables['APP_TIMEZONE'] = $this->option('timezone') ?? $this->anticipate(\n            '应用时区',\n            \\DateTimeZone::listIdentifiers(),\n            config('app.timezone')\n        );\n\n        $selected = config('cache.default', 'redis');\n        $this->variables['CACHE_DRIVER'] = $this->option('cache') ?? $this->choice(\n            'Cache 缓存驱动程序 不懂你就按回车',\n            self::CACHE_DRIVERS,\n            array_key_exists($selected, self::CACHE_DRIVERS) ? $selected : null\n        );\n\n        $selected = config('session.driver', 'redis');\n        $this->variables['SESSION_DRIVER'] = $this->option('session') ?? $this->choice(\n            'Session 会话驱动程序 不懂你就按回车',\n            self::SESSION_DRIVERS,\n            array_key_exists($selected, self::SESSION_DRIVERS) ? $selected : null\n        );\n\n        $selected = config('queue.default', 'redis');\n        $this->variables['QUEUE_CONNECTION'] = $this->option('queue') ?? $this->choice(\n            'Queue 队列驱动程序 不懂你就按回车',\n            self::QUEUE_DRIVERS,\n            array_key_exists($selected, self::QUEUE_DRIVERS) ? $selected : null\n        );\n\n        if (!is_null($this->option('settings-ui'))) {\n            $this->variables['APP_ENVIRONMENT_ONLY'] = $this->option('settings-ui') == 'true' ? 'false' : 'true';\n        } else {\n            $this->variables['APP_ENVIRONMENT_ONLY'] = $this->confirm('启用基于 UI 的设置编辑器?', true) ? 'false' : 'true';\n        }\n\n        $this->output->comment('有关遥测数据和收集的更多详细信息，请参考 https://pterodactyl.top/panel/1.0/additional_configuration.html#telemetry。');\n        $this->variables['PTERODACTYL_TELEMETRY_ENABLED'] = $this->option('telemetry') ?? $this->confirm(\n            '允许发送匿名遥测数据？',\n            config('pterodactyl.telemetry.enabled', true)\n        ) ? 'true' : 'false';\n\n        // Make sure session cookies are set as \"secure\" when using HTTPS\n        if (str_starts_with($this->variables['APP_URL'], 'https://')) {\n            $this->variables['SESSION_SECURE_COOKIE'] = 'true';\n        }\n\n        $this->checkForRedis();\n        $this->writeToEnvironment($this->variables);\n\n        $this->info($this->console->output());\n\n        return 0;\n    }\n\n    /**\n     * Check if redis is selected, if so, request connection details and verify them.\n     */\n    private function checkForRedis()\n    {\n        $items = collect($this->variables)->filter(function ($item) {\n            return $item === 'redis';\n        });\n\n        // Redis was not selected, no need to continue.\n        if (count($items) === 0) {\n            return;\n        }\n\n        $this->output->note('您为一个或多个选项选择了 Redis 驱动程序，请在下面提供有效的连接信息。在大多数情况下，您可以使用提供的默认值，除非您修改了 Redis 主机设置.');\n        $this->variables['REDIS_HOST'] = $this->option('redis-host') ?? $this->ask(\n            'Redis 主机',\n            config('database.redis.default.host')\n        );\n\n        $askForRedisPassword = true;\n        if (!empty(config('database.redis.default.password'))) {\n            $this->variables['REDIS_PASSWORD'] = config('database.redis.default.password');\n            $askForRedisPassword = $this->confirm('似乎已经为 Redis 定义了密码，您要更改吗?');\n        }\n\n        if ($askForRedisPassword) {\n            $this->output->comment('默认情况下，Redis 服务器连接无需密码，因为它在本地运行并且不允许外部访问。在这种情况下，阁下只需直接按回车键表示留空.');\n            $this->variables['REDIS_PASSWORD'] = $this->option('redis-pass') ?? $this->output->askHidden(\n                'Redis 密码'\n            );\n        }\n\n        if (empty($this->variables['REDIS_PASSWORD'])) {\n            $this->variables['REDIS_PASSWORD'] = 'null';\n        }\n\n        $this->variables['REDIS_PORT'] = $this->option('redis-port') ?? $this->ask(\n            'Redis 端口',\n            config('database.redis.default.port')\n        );\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Environment/DatabaseSettingsCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Environment;\n\nuse Illuminate\\Console\\Command;\nuse Illuminate\\Contracts\\Console\\Kernel;\nuse Illuminate\\Database\\DatabaseManager;\nuse Pterodactyl\\Traits\\Commands\\EnvironmentWriterTrait;\n\nclass DatabaseSettingsCommand extends Command\n{\n    use EnvironmentWriterTrait;\n\n    protected $description = '为面板配置数据库设置.';\n\n    protected $signature = 'p:environment:database\n                            {--host= : MySQL服务器的连接地址.}\n                            {--port= : MySQL服务器的连接端口.}\n                            {--database= : 要使用的数据库.}\n                            {--username= : 连接数据库时使用的用户名.}\n                            {--password= : 用于连接此数据库的密码.}';\n\n    protected array $variables = [];\n\n    /**\n     * DatabaseSettingsCommand constructor.\n     */\n    public function __construct(private DatabaseManager $database, private Kernel $console)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Handle command execution.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\PterodactylException\n     */\n    public function handle(): int\n    {\n        $this->output->note('强烈建议不要使用\"localhost\"作为您的数据库主机，因为我们已经看到频繁的套接字连接问题。如果你想使用本地连接，你应该使用“127.0.0.1”.');\n        $this->variables['DB_HOST'] = $this->option('host') ?? $this->ask(\n            '数据库地址',\n            config('database.connections.mysql.host', '127.0.0.1')\n        );\n\n        $this->variables['DB_PORT'] = $this->option('port') ?? $this->ask(\n            '数据库端口',\n            config('database.connections.mysql.port', 3306)\n        );\n\n        $this->variables['DB_DATABASE'] = $this->option('database') ?? $this->ask(\n            '数据库名称',\n            config('database.connections.mysql.database', 'panel')\n        );\n\n        $this->output->note('使用“root”帐户进行 MySQL 连接不仅非常不被推荐，而且此应用程序也不允许这样做。您需要专门为此软件创建一个有权限的 MySQL 用户.');\n        $this->variables['DB_USERNAME'] = $this->option('username') ?? $this->ask(\n            '数据库用户名',\n            config('database.connections.mysql.username', 'pterodactyl')\n        );\n\n        $askForMySQLPassword = true;\n        if (!empty(config('database.connections.mysql.password')) && $this->input->isInteractive()) {\n            $this->variables['DB_PASSWORD'] = config('database.connections.mysql.password');\n            $askForMySQLPassword = $this->confirm('您似乎已经定义了 MySQL 连接密码，您想更改它吗?');\n        }\n\n        if ($askForMySQLPassword) {\n            $this->variables['DB_PASSWORD'] = $this->option('password') ?? $this->secret('数据库密码');\n        }\n\n        try {\n            $this->testMySQLConnection();\n        } catch (\\PDOException $exception) {\n            $this->output->error(sprintf('无法使用提供的凭证连接到 MySQL 服务器。返回的错误是 \"%s\".', $exception->getMessage()));\n            $this->output->error('您的连接凭证尚未保存。在继续之前，您需要提供有效的连接信息.');\n\n            if ($this->confirm('回去再试一次?')) {\n                $this->database->disconnect('_pterodactyl_command_test');\n\n                return $this->handle();\n            }\n\n            return 1;\n        }\n\n        $this->writeToEnvironment($this->variables);\n\n        $this->info($this->console->output());\n\n        return 0;\n    }\n\n    /**\n     * Test that we can connect to the provided MySQL instance and perform a selection.\n     */\n    private function testMySQLConnection()\n    {\n        config()->set('database.connections._pterodactyl_command_test', [\n            'driver' => 'mysql',\n            'host' => $this->variables['DB_HOST'],\n            'port' => $this->variables['DB_PORT'],\n            'database' => $this->variables['DB_DATABASE'],\n            'username' => $this->variables['DB_USERNAME'],\n            'password' => $this->variables['DB_PASSWORD'],\n            'charset' => 'utf8mb4',\n            'collation' => 'utf8mb4_unicode_ci',\n            'strict' => true,\n        ]);\n\n        $this->database->connection('_pterodactyl_command_test')->getPdo();\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Environment/EmailSettingsCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Environment;\n\nuse Illuminate\\Console\\Command;\nuse Pterodactyl\\Traits\\Commands\\EnvironmentWriterTrait;\nuse Illuminate\\Contracts\\Config\\Repository as ConfigRepository;\n\nclass EmailSettingsCommand extends Command\n{\n    use EnvironmentWriterTrait;\n\n    protected $description = '设置或更新面板前端的电子邮件发送配置.';\n\n    protected $signature = 'p:environment:mail\n                            {--driver= : 要使用的邮件驱动程序.}\n                            {--email= : 邮件地址.}\n                            {--from= : 发件人地址.}\n                            {--encryption=}\n                            {--host=}\n                            {--port=}\n                            {--endpoint=}\n                            {--username=}\n                            {--password=}';\n\n    protected array $variables = [];\n\n    /**\n     * EmailSettingsCommand constructor.\n     */\n    public function __construct(private ConfigRepository $config)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Handle command execution.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\PterodactylException\n     */\n    public function handle()\n    {\n        $this->variables['MAIL_DRIVER'] = $this->option('driver') ?? $this->choice(\n            trans('command/messages.environment.mail.ask_driver'),\n            [\n                'smtp' => 'SMTP 服务器',\n                'sendmail' => 'sendmail 二进制文件',\n                'mailgun' => 'Mailgun 交易电子邮件',\n                'mandrill' => 'Mandrill 交易电子邮件',\n                'postmark' => 'Postmark 交易电子邮件',\n            ],\n            $this->config->get('mail.default', 'smtp')\n        );\n\n        $method = 'setup' . studly_case($this->variables['MAIL_DRIVER']) . '驱动程序设置';\n        if (method_exists($this, $method)) {\n            $this->{$method}();\n        }\n\n        $this->variables['MAIL_FROM_ADDRESS'] = $this->option('email') ?? $this->ask(\n            trans('command/messages.environment.mail.ask_mail_from'),\n            $this->config->get('mail.from.address')\n        );\n\n        $this->variables['MAIL_FROM_NAME'] = $this->option('from') ?? $this->ask(\n            trans('command/messages.environment.mail.ask_mail_name'),\n            $this->config->get('mail.from.name')\n        );\n\n        $this->writeToEnvironment($this->variables);\n\n        $this->line('正在更新本地环境配置文件.');\n        $this->line('');\n    }\n\n    /**\n     * Handle variables for SMTP driver.\n     */\n    private function setupSmtpDriverVariables()\n    {\n        $this->variables['MAIL_HOST'] = $this->option('host') ?? $this->ask(\n            trans('command/messages.environment.mail.ask_smtp_host'),\n            $this->config->get('mail.mailers.smtp.host')\n        );\n\n        $this->variables['MAIL_PORT'] = $this->option('port') ?? $this->ask(\n            trans('command/messages.environment.mail.ask_smtp_port'),\n            $this->config->get('mail.mailers.smtp.port')\n        );\n\n        $this->variables['MAIL_USERNAME'] = $this->option('username') ?? $this->ask(\n            trans('command/messages.environment.mail.ask_smtp_username'),\n            $this->config->get('mail.mailers.smtp.username')\n        );\n\n        $this->variables['MAIL_PASSWORD'] = $this->option('password') ?? $this->secret(\n            trans('command/messages.environment.mail.ask_smtp_password')\n        );\n\n        $this->variables['MAIL_ENCRYPTION'] = $this->option('encryption') ?? $this->choice(\n            trans('command/messages.environment.mail.ask_encryption'),\n            ['tls' => 'TLS', 'ssl' => 'SSL', '' => 'None'],\n            $this->config->get('mail.mailers.smtp.encryption', 'tls')\n        );\n    }\n\n    /**\n     * Handle variables for mailgun driver.\n     */\n    private function setupMailgunDriverVariables()\n    {\n        $this->variables['MAILGUN_DOMAIN'] = $this->option('host') ?? $this->ask(\n            trans('command/messages.environment.mail.ask_mailgun_domain'),\n            $this->config->get('services.mailgun.domain')\n        );\n\n        $this->variables['MAILGUN_SECRET'] = $this->option('password') ?? $this->ask(\n            trans('command/messages.environment.mail.ask_mailgun_secret'),\n            $this->config->get('services.mailgun.secret')\n        );\n\n        $this->variables['MAILGUN_ENDPOINT'] = $this->option('endpoint') ?? $this->ask(\n            trans('command/messages.environment.mail.ask_mailgun_endpoint'),\n            $this->config->get('services.mailgun.endpoint')\n        );\n    }\n\n    /**\n     * Handle variables for mandrill driver.\n     */\n    private function setupMandrillDriverVariables()\n    {\n        $this->variables['MANDRILL_SECRET'] = $this->option('password') ?? $this->ask(\n            trans('command/messages.environment.mail.ask_mandrill_secret'),\n            $this->config->get('services.mandrill.secret')\n        );\n    }\n\n    /**\n     * Handle variables for postmark driver.\n     */\n    private function setupPostmarkDriverVariables()\n    {\n        $this->variables['MAIL_DRIVER'] = 'smtp';\n        $this->variables['MAIL_HOST'] = 'smtp.postmarkapp.com';\n        $this->variables['MAIL_PORT'] = 587;\n        $this->variables['MAIL_USERNAME'] = $this->variables['MAIL_PASSWORD'] = $this->option('username') ?? $this->ask(\n            trans('command/messages.environment.mail.ask_postmark_username'),\n            $this->config->get('mail.username')\n        );\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/InfoCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands;\n\nuse Illuminate\\Console\\Command;\nuse Pterodactyl\\Services\\Helpers\\SoftwareVersionService;\nuse Illuminate\\Contracts\\Config\\Repository as ConfigRepository;\n\nclass InfoCommand extends Command\n{\n    protected $description = '显示应用程序、数据库和电子邮件配置以及面板版本。';\n\n    protected $signature = 'p:info';\n\n    /**\n     * VersionCommand constructor.\n     */\n    public function __construct(private ConfigRepository $config, private SoftwareVersionService $versionService)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Handle execution of command.\n     */\n    public function handle()\n    {\n        $this->output->title('版本信息');\n        $this->table([], [\n            ['面板版本', $this->config->get('app.version')],\n            ['最新版本', $this->versionService->getPanel()],\n            ['是否为最新版', $this->versionService->isLatestPanel() ? '是' : $this->formatText('否', 'bg=red')],\n            ['服务作者', $this->config->get('pterodactyl.service.author')],\n        ], 'compact');\n\n        $this->output->title('应用配置');\n        $this->table([], [\n            ['环境', $this->formatText($this->config->get('app.env'), $this->config->get('app.env') === '生产' ?: 'bg=red')],\n            ['是否处于调试模式', $this->formatText($this->config->get('app.debug') ? '是' : '否', !$this->config->get('app.debug') ?: 'bg=red')],\n            ['安装 URL', $this->config->get('app.url')],\n            ['安装路径', base_path()],\n            ['时区', $this->config->get('app.timezone')],\n            ['Cache 缓存驱动器', $this->config->get('cache.default')],\n            ['Queue 队列驱动器', $this->config->get('queue.default')],\n            ['Session 会话驱动器', $this->config->get('session.driver')],\n            ['Filesystem 文件系统驱动器', $this->config->get('filesystems.default')],\n            ['默认主题', $this->config->get('themes.active')],\n            ['代理', $this->config->get('trustedproxies.proxies')],\n        ], 'compact');\n\n        $this->output->title('数据库配置');\n        $driver = $this->config->get('database.default');\n        $this->table([], [\n            ['驱动器', $driver],\n            ['主机', $this->config->get(\"database.connections.$driver.host\")],\n            ['端口', $this->config->get(\"database.connections.$driver.port\")],\n            ['数据库', $this->config->get(\"database.connections.$driver.database\")],\n            ['用户名', $this->config->get(\"database.connections.$driver.username\")],\n        ], 'compact');\n\n        // TODO: Update this to handle other mail drivers\n        $this->output->title('邮件发件配置');\n        $this->table([], [\n            ['驱动器', $this->config->get('mail.default')],\n            ['主机', $this->config->get('mail.mailers.smtp.host')],\n            ['端口', $this->config->get('mail.mailers.smtp.port')],\n            ['用户名', $this->config->get('mail.mailers.smtp.username')],\n            ['发件地址', $this->config->get('mail.from.address')],\n            ['发件人', $this->config->get('mail.from.name')],\n            ['加密方式', $this->config->get('mail.mailers.smtp.encryption')],\n        ], 'compact');\n    }\n\n    /**\n     * Format output in a Name: Value manner.\n     */\n    private function formatText(string $value, string $opts = ''): string\n    {\n        return sprintf('<%s>%s</>', $opts, $value);\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Location/DeleteLocationCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Location;\n\nuse Illuminate\\Console\\Command;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Services\\Locations\\LocationDeletionService;\nuse Pterodactyl\\Contracts\\Repository\\LocationRepositoryInterface;\n\nclass DeleteLocationCommand extends Command\n{\n    protected $description = 'Deletes a location from the Panel.';\n\n    protected $signature = 'p:location:delete {--short= : The short code of the location to delete.}';\n\n    protected Collection $locations;\n\n    /**\n     * DeleteLocationCommand constructor.\n     */\n    public function __construct(\n        private LocationDeletionService $deletionService,\n        private LocationRepositoryInterface $repository,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Respond to the command request.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Location\\HasActiveNodesException\n     */\n    public function handle()\n    {\n        $this->locations = $this->locations ?? $this->repository->all();\n        $short = $this->option('short') ?? $this->anticipate(\n            trans('command/messages.location.ask_short'),\n            $this->locations->pluck('short')->toArray()\n        );\n\n        $location = $this->locations->where('short', $short)->first();\n        if (is_null($location)) {\n            $this->error(trans('command/messages.location.no_location_found'));\n            if ($this->input->isInteractive()) {\n                $this->handle();\n            }\n\n            return;\n        }\n\n        $this->deletionService->handle($location->id);\n        $this->line(trans('command/messages.location.deleted'));\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Location/MakeLocationCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Location;\n\nuse Illuminate\\Console\\Command;\nuse Pterodactyl\\Services\\Locations\\LocationCreationService;\n\nclass MakeLocationCommand extends Command\n{\n    protected $signature = 'p:location:make\n                            {--short= : The shortcode name of this location (ex. us1).}\n                            {--long= : A longer description of this location.}';\n\n    protected $description = 'Creates a new location on the system via the CLI.';\n\n    /**\n     * Create a new command instance.\n     */\n    public function __construct(private LocationCreationService $creationService)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Handle the command execution process.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function handle()\n    {\n        $short = $this->option('short') ?? $this->ask(trans('command/messages.location.ask_short'));\n        $long = $this->option('long') ?? $this->ask(trans('command/messages.location.ask_long'));\n\n        $location = $this->creationService->handle(compact('short', 'long'));\n        $this->line(trans('command/messages.location.created', [\n            'name' => $location->short,\n            'id' => $location->id,\n        ]));\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Maintenance/CleanServiceBackupFilesCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Maintenance;\n\nuse Carbon\\Carbon;\nuse Illuminate\\Console\\Command;\nuse Illuminate\\Contracts\\Filesystem\\Filesystem;\nuse Illuminate\\Contracts\\Filesystem\\Factory as FilesystemFactory;\n\nclass CleanServiceBackupFilesCommand extends Command\n{\n    public const BACKUP_THRESHOLD_MINUTES = 5;\n\n    protected $description = 'Clean orphaned .bak files created when modifying services.';\n\n    protected $signature = 'p:maintenance:clean-service-backups';\n\n    protected Filesystem $disk;\n\n    /**\n     * CleanServiceBackupFilesCommand constructor.\n     */\n    public function __construct(FilesystemFactory $filesystem)\n    {\n        parent::__construct();\n\n        $this->disk = $filesystem->disk();\n    }\n\n    /**\n     * Handle command execution.\n     */\n    public function handle()\n    {\n        $files = $this->disk->files('services/.bak');\n\n        collect($files)->each(function (\\SplFileInfo $file) {\n            $lastModified = Carbon::createFromTimestamp($this->disk->lastModified($file->getPath()));\n            if ((int) $lastModified->diffInMinutes(Carbon::now()) > self::BACKUP_THRESHOLD_MINUTES) {\n                $this->disk->delete($file->getPath());\n                $this->info(trans('command/messages.maintenance.deleting_service_backup', ['file' => $file->getFilename()]));\n            }\n        });\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Maintenance/PruneOrphanedBackupsCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Maintenance;\n\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Console\\Command;\nuse Pterodactyl\\Repositories\\Eloquent\\BackupRepository;\n\nclass PruneOrphanedBackupsCommand extends Command\n{\n    protected $signature = 'p:maintenance:prune-backups {--prune-age=}';\n\n    protected $description = '将所有过去 \"n\" 分钟内未完成备份的标记为失败。';\n\n    /**\n     * PruneOrphanedBackupsCommand constructor.\n     */\n    public function __construct(private BackupRepository $backupRepository)\n    {\n        parent::__construct();\n    }\n\n    public function handle()\n    {\n        $since = $this->option('prune-age') ?? config('backups.prune_age', 360);\n        if (!$since || !is_digit($since)) {\n            throw new \\InvalidArgumentException('\"--prune-age\" 参数的值必须大于 0。');\n        }\n\n        $query = $this->backupRepository->getBuilder()\n            ->whereNull('completed_at')\n            ->where('created_at', '<=', CarbonImmutable::now()->subMinutes($since)->toDateTimeString());\n\n        $count = $query->count();\n        if (!$count) {\n            $this->info('没有被标记为失败的无主备份。');\n\n            return;\n        }\n\n        $this->warn(\"将过去 $since 分钟内未完成的 $count 个备份标记为失败。\");\n\n        $query->update([\n            'is_successful' => false,\n            'completed_at' => CarbonImmutable::now(),\n            'updated_at' => CarbonImmutable::now(),\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Node/MakeNodeCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Node;\n\nuse Illuminate\\Console\\Command;\nuse Pterodactyl\\Services\\Nodes\\NodeCreationService;\n\nclass MakeNodeCommand extends Command\n{\n    protected $signature = 'p:node:make\n                            {--name= : 用于标识节点的名称。}\n                            {--description= : 用于标识节点的描述。}\n                            {--locationId= : 一个有效的地域 ID。}\n                            {--fqdn= : 请输入用于连接守护程序的域名 (例如 node.example.com)。仅在 您没有为此节点使用 SSL 连接的情况下才可以使用 IP 地址。}\n                            {--public= : 节点应该是公共的还是私有的？ （公共 = 1 / 私人 = 0）。}\n                            {--scheme= : 应该使用哪种方案？ （启用 SSL=https / 禁用 SSL=http）。}\n                            {--proxy= : 守护进程是否使用了代理？ （是=1 / 否=0）。}\n                            {--maintenance= : 是否应该启用维护模式？ （启用维护模式 = 1 / 禁用维护模式 = 0）。}\n                            {--maxMemory= : 设置最大内存容量。}\n                            {--overallocateMemory= : 输入要过度分配的内存容量 (% or -1 to overallocate the maximum).}\n                            {--maxDisk= : 设置最大存储容量。}\n                            {--overallocateDisk= : 输入要过度分配的存储容量 (% or -1 to overallocate the maximum).}\n                            {--uploadSize= : 输入最大文件上传大小}\n                            {--daemonListeningPort= : 输入wings监听端口。}\n                            {--daemonSFTPPort= : 输入wings SFTP监听端口。}\n                            {--daemonBase= : 输入服务器文件存储目录}';\n\n    protected $description = 'Creates a new node on the system via the CLI.';\n\n    /**\n     * MakeNodeCommand constructor.\n     */\n    public function __construct(private NodeCreationService $creationService)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Handle the command execution process.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function handle()\n    {\n        $data['name'] = $this->option('name') ?? $this->ask('输入用于区分此节点与其他节点的简短标识符');\n        $data['description'] = $this->option('description') ?? $this->ask('输入描述以识别节点');\n        $data['location_id'] = $this->option('locationId') ?? $this->ask('输入有效的地域 ID');\n        $data['scheme'] = $this->option('scheme') ?? $this->anticipate(\n            '请为 SSL 输入 https 或为非 SSL 连接输入 http',\n            ['https', 'http'],\n            'https'\n        );\n        $data['fqdn'] = $this->option('fqdn') ?? $this->ask('请输入用于连接守护程序的域名 (例如 node.example.com). 仅当您没有为此节点使用 SSL 时才可以使用 IP 地址.');\n        $data['public'] = $this->option('public') ?? $this->confirm('该节点是否应该公开？ 请注意，将节点设置为私有将拒绝自动部署到此节点的能力。', true);\n        $data['behind_proxy'] = $this->option('proxy') ?? $this->confirm('您的 FQDN(域名) 是否使用了代理？');\n        $data['maintenance_mode'] = $this->option('maintenance') ?? $this->confirm('是否应该启用维护模式？');\n        $data['memory'] = $this->option('maxMemory') ?? $this->ask('输入最大内存容量');\n        $data['memory_overallocate'] = $this->option('overallocateMemory') ?? $this->ask('输入要过度分配的内存容量，-1 将禁用检查，0 将阻止创建新服务器');\n        $data['disk'] = $this->option('maxDisk') ?? $this->ask('输入最大存储空间容量');\n        $data['disk_overallocate'] = $this->option('overallocateDisk') ?? $this->ask('输入要过度分配的存储空间容量，-1 将禁用检查，0 将阻止创建新服务器');\n        $data['upload_size'] = $this->option('uploadSize') ?? $this->ask('输入最大文件上传大小', '100');\n        $data['daemonListen'] = $this->option('daemonListeningPort') ?? $this->ask('输入wings监听端口', '8080');\n        $data['daemonSFTP'] = $this->option('daemonSFTPPort') ?? $this->ask('输入wings SFTP监听端口', '2022');\n        $data['daemonBase'] = $this->option('daemonBase') ?? $this->ask('输入服务器文件存储目录', '/var/lib/pterodactyl/volumes');\n\n        $node = $this->creationService->handle($data);\n        $this->line('在地域 ' . $data['location_id'] . ' 上成功创建了一个名为 ' . $data['name'] . ' 且 id 为 ' . $node->id . ' 的新节点。');\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Node/NodeConfigurationCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Node;\n\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Console\\Command;\n\nclass NodeConfigurationCommand extends Command\n{\n    protected $signature = 'p:node:configuration\n                            {node : The ID or UUID of the node to return the configuration for.}\n                            {--format=yaml : The output format. Options are \"yaml\" and \"json\".}';\n\n    protected $description = 'Displays the configuration for the specified node.';\n\n    public function handle(): int\n    {\n        $column = ctype_digit((string) $this->argument('node')) ? 'id' : 'uuid';\n\n        /** @var Node $node */\n        $node = Node::query()->where($column, $this->argument('node'))->firstOr(function () {\n            $this->error('The selected node does not exist.');\n\n            exit(1);\n        });\n\n        $format = $this->option('format');\n        if (!in_array($format, ['yaml', 'yml', 'json'])) {\n            $this->error('Invalid format specified. Valid options are \"yaml\" and \"json\".');\n\n            return 1;\n        }\n\n        if ($format === 'json') {\n            $this->output->write($node->getJsonConfiguration(true));\n        } else {\n            $this->output->write($node->getYamlConfiguration());\n        }\n\n        $this->output->newLine();\n\n        return 0;\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Node/NodeListCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Node;\n\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Console\\Command;\n\nclass NodeListCommand extends Command\n{\n    protected $signature = 'p:node:list {--format=text : The output format: \"text\" or \"json\". }';\n\n    public function handle(): int\n    {\n        $nodes = Node::query()->with('location')->get()->map(function (Node $node) {\n            return [\n                'id' => $node->id,\n                'uuid' => $node->uuid,\n                'name' => $node->name,\n                'location' => $node->location->short,\n                'host' => $node->getConnectionAddress(),\n            ];\n        });\n\n        if ($this->option('format') === 'json') {\n            $this->output->write($nodes->toJson(JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES));\n        } else {\n            $this->table(['ID', 'UUID', 'Name', 'Location', 'Host'], $nodes->toArray());\n        }\n\n        $this->output->newLine();\n\n        return 0;\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Overrides/KeyGenerateCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Overrides;\n\nuse Illuminate\\Foundation\\Console\\KeyGenerateCommand as BaseKeyGenerateCommand;\n\nclass KeyGenerateCommand extends BaseKeyGenerateCommand\n{\n    /**\n     * Override the default Laravel key generation command to throw a warning to the user\n     * if it appears that they have already generated an application encryption key.\n     */\n    public function handle()\n    {\n        if (!empty(config('app.key')) && $this->input->isInteractive()) {\n            $this->output->warning('您似乎已经配置了应用程序加密密钥。如果继续此过程将会覆盖该密钥并导致任何现有已加密数据的损坏。除非您知道自己在做什么，否则请勿继续。');\n            if (!$this->confirm('我了解执行此命令的后果，并承担对加密数据丢失的所有责任。')) {\n                return;\n            }\n\n            if (!$this->confirm('您确定要继续吗？更改应用程序加密密钥将将导致数据丢失。')) {\n                return;\n            }\n        }\n\n        parent::handle();\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Overrides/SeedCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Overrides;\n\nuse Pterodactyl\\Console\\RequiresDatabaseMigrations;\nuse Illuminate\\Database\\Console\\Seeds\\SeedCommand as BaseSeedCommand;\n\nclass SeedCommand extends BaseSeedCommand\n{\n    use RequiresDatabaseMigrations;\n\n    /**\n     * Block someone from running this seed command if they have not completed\n     * the migration process.\n     */\n    public function handle(): int\n    {\n        if (!$this->hasCompletedMigrations()) {\n            $this->showMigrationWarning();\n\n            return 1;\n        }\n\n        return parent::handle();\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Overrides/UpCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Overrides;\n\nuse Pterodactyl\\Console\\RequiresDatabaseMigrations;\nuse Illuminate\\Foundation\\Console\\UpCommand as BaseUpCommand;\n\nclass UpCommand extends BaseUpCommand\n{\n    use RequiresDatabaseMigrations;\n\n    /**\n     * Block someone from running this up command if they have not completed\n     * the migration process.\n     */\n    public function handle(): int\n    {\n        if (!$this->hasCompletedMigrations()) {\n            $this->showMigrationWarning();\n\n            return 1;\n        }\n\n        return parent::handle();\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Schedule/ProcessRunnableCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Schedule;\n\nuse Illuminate\\Console\\Command;\nuse Pterodactyl\\Models\\Schedule;\nuse Illuminate\\Support\\Facades\\Log;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Pterodactyl\\Services\\Schedules\\ProcessScheduleService;\n\nclass ProcessRunnableCommand extends Command\n{\n    protected $signature = 'p:schedule:process';\n\n    protected $description = 'Process schedules in the database and determine which are ready to run.';\n\n    /**\n     * Handle command execution.\n     */\n    public function handle(): int\n    {\n        $schedules = Schedule::query()\n            ->with('tasks')\n            ->whereRelation('server', fn (Builder $builder) => $builder->whereNull('status'))\n            ->where('is_active', true)\n            ->where('is_processing', false)\n            ->whereRaw('next_run_at <= NOW()')\n            ->get();\n\n        if ($schedules->count() < 1) {\n            $this->line('There are no scheduled tasks for servers that need to be run.');\n\n            return 0;\n        }\n\n        $bar = $this->output->createProgressBar(count($schedules));\n        foreach ($schedules as $schedule) {\n            $bar->clear();\n            $this->processSchedule($schedule);\n            $bar->advance();\n            $bar->display();\n        }\n\n        $this->line('');\n\n        return 0;\n    }\n\n    /**\n     * Processes a given schedule and logs and errors encountered the console output. This should\n     * never throw an exception out, otherwise you'll end up killing the entire run group causing\n     * any other schedules to not process correctly.\n     *\n     * @see https://github.com/pterodactyl/panel/issues/2609\n     */\n    protected function processSchedule(Schedule $schedule)\n    {\n        if ($schedule->tasks->isEmpty()) {\n            return;\n        }\n\n        try {\n            $this->getLaravel()->make(ProcessScheduleService::class)->handle($schedule);\n\n            $this->line(trans('command/messages.schedule.output_line', [\n                'schedule' => $schedule->name,\n                'hash' => $schedule->hashid,\n            ]));\n        } catch (\\Throwable $exception) {\n            Log::error($exception, ['schedule_id' => $schedule->id]);\n\n            $this->error(\"处理计划时遇到错误 #$schedule->id: \" . $exception->getMessage());\n        }\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/Server/BulkPowerActionCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\Server;\n\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Console\\Command;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Illuminate\\Validation\\ValidationException;\nuse Illuminate\\Validation\\Factory as ValidatorFactory;\nuse Pterodactyl\\Repositories\\Wings\\DaemonPowerRepository;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass BulkPowerActionCommand extends Command\n{\n    protected $signature = 'p:server:bulk-power\n                            {action : The action to perform (start, stop, restart, kill)}\n                            {--servers= : A comma separated list of servers.}\n                            {--nodes= : A comma separated list of nodes.}';\n\n    protected $description = 'Perform bulk power management on large groupings of servers or nodes at once.';\n\n    /**\n     * BulkPowerActionCommand constructor.\n     */\n    public function __construct(private DaemonPowerRepository $powerRepository, private ValidatorFactory $validator)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Handle the bulk power request.\n     *\n     * @throws ValidationException\n     */\n    public function handle()\n    {\n        $action = $this->argument('action');\n        $nodes = empty($this->option('nodes')) ? [] : explode(',', $this->option('nodes'));\n        $servers = empty($this->option('servers')) ? [] : explode(',', $this->option('servers'));\n\n        $validator = $this->validator->make([\n            'action' => $action,\n            'nodes' => $nodes,\n            'servers' => $servers,\n        ], [\n            'action' => 'string|in:start,stop,kill,restart',\n            'nodes' => 'array',\n            'nodes.*' => 'integer|min:1',\n            'servers' => 'array',\n            'servers.*' => 'integer|min:1',\n        ]);\n\n        if ($validator->fails()) {\n            foreach ($validator->getMessageBag()->all() as $message) {\n                $this->output->error($message);\n            }\n\n            throw new ValidationException($validator);\n        }\n\n        $count = $this->getQueryBuilder($servers, $nodes)->count();\n        if (!$this->confirm(trans('command/messages.server.power.confirm', ['action' => $action, 'count' => $count])) && $this->input->isInteractive()) {\n            return;\n        }\n\n        $bar = $this->output->createProgressBar($count);\n        $powerRepository = $this->powerRepository;\n        $this->getQueryBuilder($servers, $nodes)->each(function (Server $server) use ($action, $powerRepository, &$bar) {\n            $bar->clear();\n\n            try {\n                $powerRepository->setServer($server)->send($action);\n            } catch (DaemonConnectionException $exception) {\n                $this->output->error(trans('command/messages.server.power.action_failed', [\n                    'name' => $server->name,\n                    'id' => $server->id,\n                    'node' => $server->node->name,\n                    'message' => $exception->getMessage(),\n                ]));\n            }\n\n            $bar->advance();\n            $bar->display();\n        });\n\n        $this->line('');\n    }\n\n    /**\n     * Returns the query builder instance that will return the servers that should be affected.\n     */\n    protected function getQueryBuilder(array $servers, array $nodes): Builder\n    {\n        $instance = Server::query()->whereNull('status');\n\n        if (!empty($nodes) && !empty($servers)) {\n            $instance->whereIn('id', $servers)->orWhereIn('node_id', $nodes);\n        } elseif (empty($nodes) && !empty($servers)) {\n            $instance->whereIn('id', $servers);\n        } elseif (!empty($nodes) && empty($servers)) { // @phpstan-ignore empty.variable\n            $instance->whereIn('node_id', $nodes);\n        }\n\n        return $instance->with('node');\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/TelemetryCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands;\n\nuse Illuminate\\Console\\Command;\nuse Symfony\\Component\\VarDumper\\VarDumper;\nuse Pterodactyl\\Services\\Telemetry\\TelemetryCollectionService;\n\nclass TelemetryCommand extends Command\n{\n    protected $description = '如果启用遥测收集，则所有服务数据将通过匿名的方式发送到翼龙官方。';\n\n    protected $signature = 'p:telemetry';\n\n    /**\n     * TelemetryCommand constructor.\n     */\n    public function __construct(private TelemetryCollectionService $telemetryCollectionService)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Handle execution of command.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function handle()\n    {\n        $this->output->info('正在收集遥测数据，这可能需要一段时间......');\n\n        VarDumper::dump($this->telemetryCollectionService->collect());\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/UpgradeCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands;\n\nuse Illuminate\\Console\\Command;\nuse Pterodactyl\\Console\\Kernel;\nuse Symfony\\Component\\Process\\Process;\nuse Symfony\\Component\\Console\\Helper\\ProgressBar;\n\nclass UpgradeCommand extends Command\n{\n    protected const DEFAULT_URL = 'https://github.com/pterodactyl-china/panel/releases/%s/panel.tar.gz';\n\n    protected $signature = 'p:upgrade\n        {--user= : 运行 PHP 的用户。所有文件将归此用户所有。}\n        {--group= : 运行 PHP 所在的组。所有文件都归该组所有。}\n        {--url= : 要下载的特定存档。}\n        {--release= : 要从 GitHub 下载的特定翼龙版本。 留空则下载最新的。}\n        {--skip-download : 如果设置，则不会下载存档。}';\n\n    protected $description = '从 GitHub 下载翼龙中国的新存档，然后执行正常的升级命令。';\n\n    /**\n     * Executes an upgrade command which will run through all of our standard\n     * commands for Pterodactyl and enable users to basically just download\n     * the archive and execute this and be done.\n     *\n     * This places the application in maintenance mode as well while the commands\n     * are being executed.\n     *\n     * @throws \\Exception\n     */\n    public function handle()\n    {\n        $skipDownload = $this->option('skip-download');\n        if (!$skipDownload) {\n            $this->output->warning('该命令不会验证下载资源的完整性。请确保您信任此下载源。如果您不希望下载存档，请使用 --skip-download 参数指明，或对以下问题回答 \"no\"。');\n            $this->output->comment('下载源(使用 --url= 参数进行设置):');\n            $this->line($this->getUrl());\n        }\n\n        if (version_compare(PHP_VERSION, '8.2.0', '<')) {\n            $this->error('无法执行自动升级。所需的最低 PHP 版本是 8.2.0，而你所用的是 [' . PHP_VERSION . '].');\n        }\n\n        $user = 'www-data';\n        $group = 'www-data';\n        if ($this->input->isInteractive()) {\n            if (!$skipDownload) {\n                $skipDownload = !$this->confirm('您想下载并解压最新版本的存档文件吗？', true);\n            }\n\n            if (is_null($this->option('user'))) {\n                $userDetails = posix_getpwuid(fileowner('public'));\n                $user = $userDetails['name'] ?? 'www-data';\n\n                if (!$this->confirm(\"您的 WEB 服务器用户已被检测为 <fg=blue>[{$user}]:</> 是否正确?\", true)) {\n                    $user = $this->anticipate(\n                        '请输入运行您的 WEB 服务器进程的用户名。这因系统而异，但通常是 \"www-data\"、\"nginx\" 或 \"apache\"。',\n                        [\n                            'www-data',\n                            'nginx',\n                            'apache',\n                        ]\n                    );\n                }\n            }\n\n            if (is_null($this->option('group'))) {\n                $groupDetails = posix_getgrgid(filegroup('public'));\n                $group = $groupDetails['name'] ?? 'www-data';\n\n                if (!$this->confirm(\"您的 WEB 服务器组已被检测为 <fg=blue>[{$group}]:</> 是否正确？\", true)) {\n                    $group = $this->anticipate(\n                        '请输入运行您的 WEB 服务器进程组名。通常这与 WEB 服务器进程用户相同。',\n                        [\n                            'www-data',\n                            'nginx',\n                            'apache',\n                        ]\n                    );\n                }\n            }\n\n            if (!$this->confirm('您确定要为您的面板运行升级操作吗？')) {\n                $this->warn('用户终止了升级操作。');\n\n                return;\n            }\n        }\n\n        ini_set('output_buffering', '0');\n        $bar = $this->output->createProgressBar($skipDownload ? 9 : 10);\n        $bar->start();\n\n        if (!$skipDownload) {\n            $this->withProgress($bar, function () {\n                $this->line(\"\\$upgrader> curl -L \\\"{$this->getUrl()}\\\" | tar -xzv\");\n                $process = Process::fromShellCommandline(\"curl -L \\\"{$this->getUrl()}\\\" | tar -xzv\");\n                $process->run(function ($type, $buffer) {\n                    $this->{$type === Process::ERR ? 'error' : 'line'}($buffer);\n                });\n            });\n        }\n\n        $this->withProgress($bar, function () {\n            $this->line('$upgrader> php artisan down');\n            $this->call('down');\n        });\n\n        $this->withProgress($bar, function () {\n            $this->line('$upgrader> chmod -R 755 storage bootstrap/cache');\n            $process = new Process(['chmod', '-R', '755', 'storage', 'bootstrap/cache']);\n            $process->run(function ($type, $buffer) {\n                $this->{$type === Process::ERR ? 'error' : 'line'}($buffer);\n            });\n        });\n\n        $this->withProgress($bar, function () {\n            $command = ['composer', 'install', '--no-ansi'];\n            if (config('app.env') === 'production' && !config('app.debug')) {\n                $command[] = '--optimize-autoloader';\n                $command[] = '--no-dev';\n            }\n\n            $this->line('$upgrader> ' . implode(' ', $command));\n            $process = new Process($command);\n            $process->setTimeout(10 * 60);\n            $process->run(function ($type, $buffer) {\n                $this->line($buffer);\n            });\n        });\n\n        /** @var \\Illuminate\\Foundation\\Application $app */\n        $app = require __DIR__ . '/../../../bootstrap/app.php';\n        /** @var Kernel $kernel */\n        $kernel = $app->make(Kernel::class);\n        $kernel->bootstrap();\n        $this->setLaravel($app);\n\n        $this->withProgress($bar, function () {\n            $this->line('$upgrader> php artisan view:clear');\n            $this->call('view:clear');\n        });\n\n        $this->withProgress($bar, function () {\n            $this->line('$upgrader> php artisan config:clear');\n            $this->call('config:clear');\n        });\n\n        $this->withProgress($bar, function () {\n            $this->line('$upgrader> php artisan migrate --force --seed');\n            $this->call('migrate', ['--force' => true, '--seed' => true]);\n        });\n\n        $this->withProgress($bar, function () use ($user, $group) {\n            $this->line(\"\\$upgrader> chown -R {$user}:{$group} *\");\n            $process = Process::fromShellCommandline(\"chown -R {$user}:{$group} *\", $this->getLaravel()->basePath());\n            $process->setTimeout(10 * 60);\n            $process->run(function ($type, $buffer) {\n                $this->{$type === Process::ERR ? 'error' : 'line'}($buffer);\n            });\n        });\n\n        $this->withProgress($bar, function () {\n            $this->line('$upgrader> php artisan queue:restart');\n            $this->call('queue:restart');\n        });\n\n        $this->withProgress($bar, function () {\n            $this->line('$upgrader> php artisan up');\n            $this->call('up');\n        });\n\n        $this->newLine(2);\n        $this->info('面板已成功升级。请确保您还更新了所有 Wings 的实例：https://pterodactyl.top/wings/1.0/upgrading.html');\n    }\n\n    protected function withProgress(ProgressBar $bar, \\Closure $callback)\n    {\n        $bar->clear();\n        $callback();\n        $bar->advance();\n        $bar->display();\n    }\n\n    protected function getUrl(): string\n    {\n        if ($this->option('url')) {\n            return $this->option('url');\n        }\n\n        return sprintf(self::DEFAULT_URL, $this->option('release') ? 'download/v' . $this->option('release') : 'latest/download');\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/User/DeleteUserCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\User;\n\nuse Pterodactyl\\Models\\User;\nuse Webmozart\\Assert\\Assert;\nuse Illuminate\\Console\\Command;\nuse Pterodactyl\\Services\\Users\\UserDeletionService;\n\nclass DeleteUserCommand extends Command\n{\n    protected $description = 'Deletes a user from the Panel if no servers are attached to their account.';\n\n    protected $signature = 'p:user:delete {--user=}';\n\n    /**\n     * DeleteUserCommand constructor.\n     */\n    public function __construct(private UserDeletionService $deletionService)\n    {\n        parent::__construct();\n    }\n\n    public function handle(): int\n    {\n        $search = $this->option('user') ?? $this->ask(trans('command/messages.user.search_users'));\n        Assert::notEmpty($search, 'Search term should be an email address, got: %s.');\n\n        $results = User::query()\n            ->where('id', 'LIKE', \"$search%\")\n            ->orWhere('username', 'LIKE', \"$search%\")\n            ->orWhere('email', 'LIKE', \"$search%\")\n            ->get();\n\n        if (count($results) < 1) {\n            $this->error(trans('command/messages.user.no_users_found'));\n            if ($this->input->isInteractive()) {\n                return $this->handle();\n            }\n\n            return 1;\n        }\n\n        if ($this->input->isInteractive()) {\n            $tableValues = [];\n            foreach ($results as $user) {\n                $tableValues[] = [$user->id, $user->email, $user->name];\n            }\n\n            $this->table(['User ID', 'Email', 'Name'], $tableValues);\n            if (!$deleteUser = $this->ask(trans('command/messages.user.select_search_user'))) {\n                return $this->handle();\n            }\n        } else {\n            if (count($results) > 1) {\n                $this->error(trans('command/messages.user.multiple_found'));\n\n                return 1;\n            }\n\n            $deleteUser = $results->first();\n        }\n\n        if ($this->confirm(trans('command/messages.user.confirm_delete')) || !$this->input->isInteractive()) {\n            $this->deletionService->handle($deleteUser);\n            $this->info(trans('command/messages.user.deleted'));\n        }\n\n        return 0;\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/User/DisableTwoFactorCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\User;\n\nuse Illuminate\\Console\\Command;\nuse Pterodactyl\\Contracts\\Repository\\UserRepositoryInterface;\n\nclass DisableTwoFactorCommand extends Command\n{\n    protected $description = '在面板中为特定用户禁用动态口令认证。';\n\n    protected $signature = 'p:user:disable2fa {--email= : 要为其禁用动态口令认证的用户邮箱。}';\n\n    /**\n     * DisableTwoFactorCommand constructor.\n     */\n    public function __construct(private UserRepositoryInterface $repository)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Handle command execution process.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function handle()\n    {\n        if ($this->input->isInteractive()) {\n            $this->output->warning(trans('command/messages.user.2fa_help_text'));\n        }\n\n        $email = $this->option('email') ?? $this->ask(trans('command/messages.user.ask_email'));\n        $user = $this->repository->setColumns(['id', 'email'])->findFirstWhere([['email', '=', $email]]);\n\n        $this->repository->withoutFreshModel()->update($user->id, [\n            'use_totp' => false,\n            'totp_secret' => null,\n        ]);\n        $this->info(trans('command/messages.user.2fa_disabled', ['email' => $user->email]));\n    }\n}\n"
  },
  {
    "path": "app/Console/Commands/User/MakeUserCommand.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console\\Commands\\User;\n\nuse Illuminate\\Console\\Command;\nuse Pterodactyl\\Services\\Users\\UserCreationService;\n\nclass MakeUserCommand extends Command\n{\n    protected $description = '通过 CLI 在系统上创建用户。';\n\n    protected $signature = 'p:user:make {--email=} {--username=} {--name-first=} {--name-last=} {--password=} {--admin=} {--no-password}';\n\n    /**\n     * MakeUserCommand constructor.\n     */\n    public function __construct(private UserCreationService $creationService)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Handle command request to create a new user.\n     *\n     * @throws \\Exception\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function handle()\n    {\n        $root_admin = $this->option('admin') ?? $this->confirm(trans('command/messages.user.ask_admin'));\n        $email = $this->option('email') ?? $this->ask(trans('command/messages.user.ask_email'));\n        $username = $this->option('username') ?? $this->ask(trans('command/messages.user.ask_username'));\n        $name_first = $this->option('name-first') ?? $this->ask(trans('command/messages.user.ask_name_first'));\n        $name_last = $this->option('name-last') ?? $this->ask(trans('command/messages.user.ask_name_last'));\n\n        if (is_null($password = $this->option('password')) && !$this->option('no-password')) {\n            $this->warn(trans('command/messages.user.ask_password_help'));\n            $this->line(trans('command/messages.user.ask_password_tip'));\n            $password = $this->secret(trans('command/messages.user.ask_password'));\n        }\n\n        $user = $this->creationService->handle(compact('email', 'username', 'name_first', 'name_last', 'password', 'root_admin'));\n        $this->table(['字段', '值'], [\n            ['UUID', $user->uuid],\n            ['Email', $user->email],\n            ['用户名', $user->username],\n            ['姓名', $user->name],\n            ['管理员', $user->root_admin ? '是' : '否'],\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Console/Kernel.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Pterodactyl\\Models\\ActivityLog;\nuse Illuminate\\Console\\Scheduling\\Schedule;\nuse Illuminate\\Database\\Console\\PruneCommand;\nuse Pterodactyl\\Repositories\\Eloquent\\SettingsRepository;\nuse Illuminate\\Foundation\\Console\\Kernel as ConsoleKernel;\nuse Pterodactyl\\Services\\Telemetry\\TelemetryCollectionService;\nuse Pterodactyl\\Console\\Commands\\Schedule\\ProcessRunnableCommand;\nuse Pterodactyl\\Console\\Commands\\Maintenance\\PruneOrphanedBackupsCommand;\nuse Pterodactyl\\Console\\Commands\\Maintenance\\CleanServiceBackupFilesCommand;\n\nclass Kernel extends ConsoleKernel\n{\n    /**\n     * Register the commands for the application.\n     */\n    protected function commands(): void\n    {\n        $this->load(__DIR__ . '/Commands');\n    }\n\n    /**\n     * Define the application's command schedule.\n     */\n    protected function schedule(Schedule $schedule): void\n    {\n        // https://laravel.com/docs/10.x/upgrade#redis-cache-tags\n        $schedule->command('cache:prune-stale-tags')->hourly();\n\n        // Execute scheduled commands for servers every minute, as if there was a normal cron running.\n        $schedule->command(ProcessRunnableCommand::class)->everyMinute()->withoutOverlapping();\n        $schedule->command(CleanServiceBackupFilesCommand::class)->daily();\n\n        if (config('backups.prune_age')) {\n            // Every 30 minutes, run the backup pruning command so that any abandoned backups can be deleted.\n            $schedule->command(PruneOrphanedBackupsCommand::class)->everyThirtyMinutes();\n        }\n\n        if (config('activity.prune_days')) {\n            $schedule->command(PruneCommand::class, ['--model' => [ActivityLog::class]])->daily();\n        }\n\n        if (config('pterodactyl.telemetry.enabled')) {\n            $this->registerTelemetry($schedule);\n        }\n    }\n\n    /**\n     * I wonder what this does.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Illuminate\\Contracts\\Container\\BindingResolutionException\n     */\n    private function registerTelemetry(Schedule $schedule): void\n    {\n        $settingsRepository = app()->make(SettingsRepository::class);\n\n        $uuid = $settingsRepository->get('app:telemetry:uuid');\n        if (is_null($uuid)) {\n            $uuid = Uuid::uuid4()->toString();\n            $settingsRepository->set('app:telemetry:uuid', $uuid);\n        }\n\n        // Calculate a fixed time to run the data push at, this will be the same time every day.\n        $time = hexdec(str_replace('-', '', substr($uuid, 27))) % 1440;\n        $hour = floor($time / 60);\n        $minute = $time % 60;\n\n        // Run the telemetry collector.\n        $schedule->call(app()->make(TelemetryCollectionService::class))->description('Collect Telemetry')->dailyAt(\"$hour:$minute\");\n    }\n}\n"
  },
  {
    "path": "app/Console/RequiresDatabaseMigrations.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Console;\n\n/**\n * @mixin \\Illuminate\\Console\\Command\n */\ntrait RequiresDatabaseMigrations\n{\n    /**\n     * Checks if the migrations have finished running by comparing the last migration file.\n     */\n    protected function hasCompletedMigrations(): bool\n    {\n        /** @var \\Illuminate\\Database\\Migrations\\Migrator $migrator */\n        $migrator = $this->getLaravel()->make('migrator');\n\n        $files = $migrator->getMigrationFiles(database_path('migrations'));\n\n        if (!$migrator->repositoryExists()) {\n            return false;\n        }\n\n        if (array_diff(array_keys($files), $migrator->getRepository()->getRan())) {\n            return false;\n        }\n\n        return true;\n    }\n\n    /**\n     * Throw a massive error into the console to hopefully catch the users attention and get\n     * them to properly run the migrations rather than ignoring all of the other previous\n     * errors...\n     */\n    protected function showMigrationWarning(): void\n    {\n        $this->getOutput()->writeln('<options=bold>\n| @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ |\n|                                                                              |\n|                             您的数据库未正确迁移！                             |\n|                                                                              |\n| @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ |</>\n\n您必须运行以下命令才能完成数据库迁移：\n\n  <fg=green;options=bold>php artisan migrate --step --force</>\n\n如果您不运行上述命令进行修复数据库你将无法正常使用 Pterodactyl 面板。\n');\n\n        $this->getOutput()->error('在继续之前，您必须更正上述错误。');\n    }\n}\n"
  },
  {
    "path": "app/Contracts/Core/ReceivesEvents.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Core;\n\nuse Pterodactyl\\Events\\Event;\n\ninterface ReceivesEvents\n{\n    /**\n     * Handles receiving an event from the application.\n     */\n    public function handle(Event $notification): void;\n}\n"
  },
  {
    "path": "app/Contracts/Criteria/CriteriaInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Criteria;\n\nuse Illuminate\\Database\\Eloquent\\Model;\nuse Pterodactyl\\Repositories\\Repository;\n\ninterface CriteriaInterface\n{\n    /**\n     * Apply selected criteria to a repository call.\n     */\n    public function apply(Model $model, Repository $repository): mixed;\n}\n"
  },
  {
    "path": "app/Contracts/Extensions/HashidsInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Extensions;\n\nuse Hashids\\HashidsInterface as VendorHashidsInterface;\n\ninterface HashidsInterface extends VendorHashidsInterface\n{\n    /**\n     * Decode an encoded hashid and return the first result.\n     *\n     * @throws \\InvalidArgumentException\n     */\n    public function decodeFirst(string $encoded, ?string $default = null): mixed;\n}\n"
  },
  {
    "path": "app/Contracts/Http/ClientPermissionsRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Http;\n\ninterface ClientPermissionsRequest\n{\n    /**\n     * Returns the permissions string indicating which permission should be used to\n     * validate that the authenticated user has permission to perform this action against\n     * the given resource (server).\n     */\n    public function permission(): string;\n}\n"
  },
  {
    "path": "app/Contracts/Models/Identifiable.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Builder;\n\ninterface Identifiable\n{\n    public function scopeWhereIdentifier(Builder $builder, string $identifier): void;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/AllocationRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Pterodactyl\\Models\\Allocation;\n\ninterface AllocationRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Return all the allocations that exist for a node that are not currently\n     * allocated.\n     */\n    public function getUnassignedAllocationIds(int $node): array;\n\n    /**\n     * Return a single allocation from those meeting the requirements.\n     */\n    public function getRandomAllocation(array $nodes, array $ports, bool $dedicated = false): ?Allocation;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/ApiKeyRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Support\\Collection;\n\ninterface ApiKeyRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Get all the account API keys that exist for a specific user.\n     */\n    public function getAccountKeys(User $user): Collection;\n\n    /**\n     * Delete an account API key from the panel for a specific user.\n     */\n    public function deleteAccountKey(User $user, string $identifier): int;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/ApiPermissionRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\ninterface ApiPermissionRepositoryInterface extends RepositoryInterface\n{\n}\n"
  },
  {
    "path": "app/Contracts/Repository/DatabaseHostRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Illuminate\\Support\\Collection;\n\ninterface DatabaseHostRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Return database hosts with a count of databases and the node\n     * information for which it is attached.\n     */\n    public function getWithViewDetails(): Collection;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/DatabaseRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Contracts\\Pagination\\LengthAwarePaginator;\n\ninterface DatabaseRepositoryInterface extends RepositoryInterface\n{\n    public const DEFAULT_CONNECTION_NAME = 'dynamic';\n\n    /**\n     * Set the connection name to execute statements against.\n     */\n    public function setConnection(string $connection): self;\n\n    /**\n     * Return the connection to execute statements against.\n     */\n    public function getConnection(): string;\n\n    /**\n     * Return all the databases belonging to a server.\n     */\n    public function getDatabasesForServer(int $server): Collection;\n\n    /**\n     * Return all the databases for a given host with the server relationship loaded.\n     */\n    public function getDatabasesForHost(int $host, int $count = 25): LengthAwarePaginator;\n\n    /**\n     * Create a new database on a given connection.\n     */\n    public function createDatabase(string $database): bool;\n\n    /**\n     * Create a new database user on a given connection.\n     */\n    public function createUser(string $username, string $remote, string $password, ?int $max_connections): bool;\n\n    /**\n     * Give a specific user access to a given database.\n     */\n    public function assignUserToDatabase(string $database, string $username, string $remote): bool;\n\n    /**\n     * Flush the privileges for a given connection.\n     */\n    public function flush(): bool;\n\n    /**\n     * Drop a given database on a specific connection.\n     */\n    public function dropDatabase(string $database): bool;\n\n    /**\n     * Drop a given user on a specific connection.\n     */\n    public function dropUser(string $username, string $remote): bool;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/EggRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Pterodactyl\\Models\\Egg;\nuse Illuminate\\Database\\Eloquent\\Collection;\n\ninterface EggRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Return an egg with the variables relation attached.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getWithVariables(int $id): Egg;\n\n    /**\n     * Return all eggs and their relations to be used in the daemon API.\n     */\n    public function getAllWithCopyAttributes(): Collection;\n\n    /**\n     * Return an egg with the scriptFrom and configFrom relations loaded onto the model.\n     */\n    public function getWithCopyAttributes(int|string $value, string $column = 'id'): Egg;\n\n    /**\n     * Return all the data needed to export a service.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getWithExportAttributes(int $id): Egg;\n\n    /**\n     * Confirm a copy script belongs to the same nest as the item trying to use it.\n     */\n    public function isCopyableScript(int $copyFromId, int $service): bool;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/EggVariableRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Illuminate\\Support\\Collection;\n\ninterface EggVariableRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Return editable variables for a given egg. Editable variables must be set to\n     * user viewable in order to be picked up by this function.\n     */\n    public function getEditableVariables(int $egg): Collection;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/LocationRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Pterodactyl\\Models\\Location;\nuse Illuminate\\Support\\Collection;\n\ninterface LocationRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Return locations with a count of nodes and servers attached to it.\n     */\n    public function getAllWithDetails(): Collection;\n\n    /**\n     * Return all the available locations with the nodes as a relationship.\n     */\n    public function getAllWithNodes(): Collection;\n\n    /**\n     * Return all the nodes and their respective count of servers for a location.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getWithNodes(int $id): Location;\n\n    /**\n     * Return a location and the count of nodes in that location.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getWithNodeCount(int $id): Location;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/NestRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Pterodactyl\\Models\\Nest;\nuse Illuminate\\Database\\Eloquent\\Collection;\n\ninterface NestRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Return a nest or all nests with their associated eggs and variables.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getWithEggs(?int $id = null): Collection|Nest;\n\n    /**\n     * Return a nest or all nests and the count of eggs and servers for that nest.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getWithCounts(?int $id = null): Collection|Nest;\n\n    /**\n     * Return a nest along with its associated eggs and the servers relation on those eggs.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getWithEggServers(int $id): Nest;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/NodeRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Support\\Collection;\n\ninterface NodeRepositoryInterface extends RepositoryInterface\n{\n    public const THRESHOLD_PERCENTAGE_LOW = 75;\n    public const THRESHOLD_PERCENTAGE_MEDIUM = 90;\n\n    /**\n     * Return the usage stats for a single node.\n     */\n    public function getUsageStats(Node $node): array;\n\n    /**\n     * Return the usage stats for a single node.\n     */\n    public function getUsageStatsRaw(Node $node): array;\n\n    /**\n     * Return a single node with location and server information.\n     */\n    public function loadLocationAndServerCount(Node $node, bool $refresh = false): Node;\n\n    /**\n     * Attach a paginated set of allocations to a node mode including\n     * any servers that are also attached to those allocations.\n     */\n    public function loadNodeAllocations(Node $node, bool $refresh = false): Node;\n\n    /**\n     * Return a collection of nodes for all locations to use in server creation UI.\n     */\n    public function getNodesForServerCreation(): Collection;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/PermissionRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\ninterface PermissionRepositoryInterface extends RepositoryInterface\n{\n}\n"
  },
  {
    "path": "app/Contracts/Repository/RepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Database\\Eloquent\\Model;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Illuminate\\Contracts\\Pagination\\LengthAwarePaginator;\n\ninterface RepositoryInterface\n{\n    /**\n     * Return an identifier or Model object to be used by the repository.\n     */\n    public function model(): string;\n\n    /**\n     * Return the model being used for this repository instance.\n     */\n    public function getModel(): Model;\n\n    /**\n     * Returns an instance of a query builder.\n     */\n    public function getBuilder(): Builder;\n\n    /**\n     * Returns the columns to be selected or returned by the query.\n     */\n    public function getColumns(): array;\n\n    /**\n     * An array of columns to filter the response by.\n     */\n    public function setColumns(array|string $columns = ['*']): self;\n\n    /**\n     * Stop repository update functions from returning a fresh\n     * model when changes are committed.\n     */\n    public function withoutFreshModel(): self;\n\n    /**\n     * Return a fresh model with a repository updates a model.\n     */\n    public function withFreshModel(): self;\n\n    /**\n     * Set whether the repository should return a fresh model\n     * when changes are committed.\n     */\n    public function setFreshModel(bool $fresh = true): self;\n\n    /**\n     * Create a new model instance and persist it to the database.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function create(array $fields, bool $validate = true, bool $force = false): mixed;\n\n    /**\n     * Find a model that has the specific ID passed.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function find(int $id): mixed;\n\n    /**\n     * Find a model matching an array of where clauses.\n     */\n    public function findWhere(array $fields): Collection;\n\n    /**\n     * Find and return the first matching instance for the given fields.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function findFirstWhere(array $fields): mixed;\n\n    /**\n     * Return a count of records matching the passed arguments.\n     */\n    public function findCountWhere(array $fields): int;\n\n    /**\n     * Delete a given record from the database.\n     */\n    public function delete(int $id): int;\n\n    /**\n     * Delete records matching the given attributes.\n     */\n    public function deleteWhere(array $attributes): int;\n\n    /**\n     * Update a given ID with the passed array of fields.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(int $id, array $fields, bool $validate = true, bool $force = false): mixed;\n\n    /**\n     * Perform a mass update where matching records are updated using whereIn.\n     * This does not perform any model data validation.\n     */\n    public function updateWhereIn(string $column, array $values, array $fields): int;\n\n    /**\n     * Update a record if it exists in the database, otherwise create it.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function updateOrCreate(array $where, array $fields, bool $validate = true, bool $force = false): mixed;\n\n    /**\n     * Return all records associated with the given model.\n     */\n    public function all(): Collection;\n\n    /**\n     * Return a paginated result set using a search term if set on the repository.\n     */\n    public function paginated(int $perPage): LengthAwarePaginator;\n\n    /**\n     * Insert a single or multiple records into the database at once skipping\n     * validation and mass assignment checking.\n     */\n    public function insert(array $data): bool;\n\n    /**\n     * Insert multiple records into the database and ignore duplicates.\n     */\n    public function insertIgnore(array $values): bool;\n\n    /**\n     * Get the amount of entries in the database.\n     */\n    public function count(): int;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/ScheduleRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Pterodactyl\\Models\\Schedule;\nuse Illuminate\\Support\\Collection;\n\ninterface ScheduleRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Return all the schedules for a given server.\n     */\n    public function findServerSchedules(int $server): Collection;\n\n    /**\n     * Return a schedule model with all the associated tasks as a relationship.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getScheduleWithTasks(int $schedule): Schedule;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/ServerRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Contracts\\Pagination\\LengthAwarePaginator;\n\ninterface ServerRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Load the egg relations onto the server model.\n     */\n    public function loadEggRelations(Server $server, bool $refresh = false): Server;\n\n    /**\n     * Return a collection of servers with their associated data for rebuild operations.\n     */\n    public function getDataForRebuild(?int $server = null, ?int $node = null): Collection;\n\n    /**\n     * Return a collection of servers with their associated data for reinstall operations.\n     */\n    public function getDataForReinstall(?int $server = null, ?int $node = null): Collection;\n\n    /**\n     * Return a server model and all variables associated with the server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function findWithVariables(int $id): Server;\n\n    /**\n     * Get the primary allocation for a given server. If a model is passed into\n     * the function, load the allocation relationship onto it. Otherwise, find and\n     * return the server from the database.\n     */\n    public function getPrimaryAllocation(Server $server, bool $refresh = false): Server;\n\n    /**\n     * Return enough data to be used for the creation of a server via the daemon.\n     */\n    public function getDataForCreation(Server $server, bool $refresh = false): Server;\n\n    /**\n     * Load associated databases onto the server model.\n     */\n    public function loadDatabaseRelations(Server $server, bool $refresh = false): Server;\n\n    /**\n     * Get data for use when updating a server on the Daemon. Returns an array of\n     * the egg which is used for build and rebuild. Only loads relations\n     * if they are missing, or refresh is set to true.\n     */\n    public function getDaemonServiceData(Server $server, bool $refresh = false): array;\n\n    /**\n     * Return a server by UUID.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getByUuid(string $uuid): Server;\n\n    /**\n     * Check if a given UUID and UUID-Short string are unique to a server.\n     */\n    public function isUniqueUuidCombo(string $uuid, string $short): bool;\n\n    /**\n     * Returns all the servers that exist for a given node in a paginated response.\n     */\n    public function loadAllServersForNode(int $node, int $limit): LengthAwarePaginator;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/ServerVariableRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\ninterface ServerVariableRepositoryInterface extends RepositoryInterface\n{\n}\n"
  },
  {
    "path": "app/Contracts/Repository/SessionRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Illuminate\\Support\\Collection;\n\ninterface SessionRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Return all the active sessions for a user.\n     */\n    public function getUserSessions(int $user): Collection;\n\n    /**\n     * Delete a session for a given user.\n     */\n    public function deleteUserSession(int $user, string $session): ?int;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/SettingsRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\ninterface SettingsRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Store a new persistent setting in the database.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function set(string $key, ?string $value = null);\n\n    /**\n     * Retrieve a persistent setting from the database.\n     */\n    public function get(string $key, mixed $default): mixed;\n\n    /**\n     * Remove a key from the database cache.\n     */\n    public function forget(string $key);\n}\n"
  },
  {
    "path": "app/Contracts/Repository/SubuserRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Pterodactyl\\Models\\Subuser;\n\ninterface SubuserRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Return a subuser with the associated server relationship.\n     */\n    public function loadServerAndUserRelations(Subuser $subuser, bool $refresh = false): Subuser;\n\n    /**\n     * Return a subuser with the associated permissions relationship.\n     */\n    public function getWithPermissions(Subuser $subuser, bool $refresh = false): Subuser;\n\n    /**\n     * Return a subuser and associated permissions given a user_id and server_id.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getWithPermissionsUsingUserAndServer(int $user, int $server): Subuser;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/TaskRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\nuse Pterodactyl\\Models\\Task;\n\ninterface TaskRepositoryInterface extends RepositoryInterface\n{\n    /**\n     * Get a task and the server relationship for that task.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function getTaskForJobProcess(int $id): Task;\n\n    /**\n     * Returns the next task in a schedule.\n     */\n    public function getNextTask(int $schedule, int $index): ?Task;\n}\n"
  },
  {
    "path": "app/Contracts/Repository/UserRepositoryInterface.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Contracts\\Repository;\n\ninterface UserRepositoryInterface extends RepositoryInterface\n{\n}\n"
  },
  {
    "path": "app/Enum/ResourceLimit.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Enum;\n\nuse Illuminate\\Http\\Request;\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Cache\\RateLimiting\\Limit;\nuse Illuminate\\Support\\Facades\\RateLimiter;\nuse Illuminate\\Routing\\Middleware\\ThrottleRequests;\n\n/**\n * A basic resource throttler for individual servers. This is applied in addition\n * to existing rate limits and allows the code to slow down speedy users that might\n * be creating resources a little too quickly for comfort. This throttle generally\n * only applies to creation flows, and not general view/edit/delete flows.\n */\nenum ResourceLimit\n{\n    case Allocation;\n    case Backup;\n    case Database;\n    case Schedule;\n    case Subuser;\n    case Websocket;\n    case FilePull;\n\n    public function throttleKey(): string\n    {\n        return mb_strtolower(\"api.client:server-resource:{$this->name}\");\n    }\n\n    /**\n     * Returns a middleware that will throttle the specific resource by server. This\n     * throttle applies to any user making changes to that resource on the specific\n     * server, it is NOT per-user.\n     */\n    public function middleware(): string\n    {\n        return ThrottleRequests::using($this->throttleKey());\n    }\n\n    public function limit(): Limit\n    {\n        return match($this) {\n            self::Backup => Limit::perMinutes(15, 3),\n            self::Database => Limit::perMinute(2),\n            self::FilePull => Limit::perMinutes(10, 5),\n            self::Subuser => Limit::perMinutes(15, 10),\n            self::Websocket => Limit::perMinute(5),\n            default => Limit::perMinute(2),\n        };\n    }\n\n    public static function boot(): void\n    {\n        foreach (self::cases() as $case) {\n            RateLimiter::for($case->throttleKey(), function (Request $request) use ($case) {\n                Assert::isInstanceOf($server = $request->route()->parameter('server'), Server::class);\n\n                return $case->limit()->by($server->uuid);\n            });\n        }\n    }\n}\n"
  },
  {
    "path": "app/Events/ActivityLogged.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events;\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\ActivityLog;\nuse Illuminate\\Database\\Eloquent\\Model;\n\nclass ActivityLogged extends Event\n{\n    public function __construct(public ActivityLog $model)\n    {\n    }\n\n    public function is(string $event): bool\n    {\n        return $this->model->event === $event;\n    }\n\n    public function actor(): ?Model\n    {\n        return $this->isSystem() ? null : $this->model->actor;\n    }\n\n    public function isServerEvent(): bool\n    {\n        return Str::startsWith($this->model->event, 'server:');\n    }\n\n    public function isSystem(): bool\n    {\n        return is_null($this->model->actor_id);\n    }\n}\n"
  },
  {
    "path": "app/Events/Auth/DirectLogin.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Auth;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Events\\Event;\n\nclass DirectLogin extends Event\n{\n    public function __construct(public User $user, public bool $remember)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Auth/FailedCaptcha.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Auth;\n\nuse Pterodactyl\\Events\\Event;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass FailedCaptcha extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public string $ip, public string $domain)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Auth/FailedPasswordReset.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Auth;\n\nuse Pterodactyl\\Events\\Event;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass FailedPasswordReset extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public string $ip, public string $email)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Auth/ProvidedAuthenticationToken.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Auth;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Events\\Event;\n\nclass ProvidedAuthenticationToken extends Event\n{\n    public function __construct(public User $user, public bool $recovery = false)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Event.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events;\n\nabstract class Event\n{\n}\n"
  },
  {
    "path": "app/Events/Server/Created.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Server;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Created extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Server $server)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Server/Creating.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Server;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Creating extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Server $server)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Server/Deleted.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Server;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Deleted extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Server $server)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Server/Deleting.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Server;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Deleting extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Server $server)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Server/Installed.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Server;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Installed extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Server $server)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Server/Saved.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Server;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Saved extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Server $server)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Server/Saving.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Server;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Saving extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Server $server)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Server/Updated.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Server;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Updated extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Server $server)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Server/Updating.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Server;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Updating extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Server $server)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Subuser/Created.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Subuser;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Subuser;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Created extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Subuser $subuser)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Subuser/Creating.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Subuser;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Subuser;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Creating extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Subuser $subuser)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Subuser/Deleted.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Subuser;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Subuser;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Deleted extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Subuser $subuser)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/Subuser/Deleting.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\Subuser;\n\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Subuser;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Deleting extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public Subuser $subuser)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/User/Created.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\User;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Events\\Event;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Created extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public User $user)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/User/Creating.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\User;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Events\\Event;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Creating extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public User $user)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/User/Deleted.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\User;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Events\\Event;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Deleted extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public User $user)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/User/Deleting.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\User;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Events\\Event;\nuse Illuminate\\Queue\\SerializesModels;\n\nclass Deleting extends Event\n{\n    use SerializesModels;\n\n    /**\n     * Create a new event instance.\n     */\n    public function __construct(public User $user)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Events/User/PasswordChanged.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Events\\User;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Foundation\\Events\\Dispatchable;\n\nfinal class PasswordChanged\n{\n    use Dispatchable;\n\n    public function __construct(public readonly User $user)\n    {\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/AccountNotFoundException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions;\n\nclass AccountNotFoundException extends \\Exception\n{\n}\n"
  },
  {
    "path": "app/Exceptions/AutoDeploymentException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions;\n\nclass AutoDeploymentException extends \\Exception\n{\n}\n"
  },
  {
    "path": "app/Exceptions/DisplayException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions;\n\nuse Exception;\nuse Illuminate\\Http\\Request;\nuse Psr\\Log\\LoggerInterface;\nuse Illuminate\\Http\\Response;\nuse Illuminate\\Http\\JsonResponse;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpExceptionInterface;\n\nclass DisplayException extends PterodactylException implements HttpExceptionInterface\n{\n    public const LEVEL_DEBUG = 'debug';\n    public const LEVEL_INFO = 'info';\n    public const LEVEL_WARNING = 'warning';\n    public const LEVEL_ERROR = 'error';\n\n    /**\n     * DisplayException constructor.\n     */\n    public function __construct(string $message, ?\\Throwable $previous = null, protected string $level = self::LEVEL_ERROR, int $code = 0)\n    {\n        parent::__construct($message, $code, $previous);\n    }\n\n    public function getErrorLevel(): string\n    {\n        return $this->level;\n    }\n\n    public function getStatusCode(): int\n    {\n        return Response::HTTP_BAD_REQUEST;\n    }\n\n    public function getHeaders(): array\n    {\n        return [];\n    }\n\n    /**\n     * Render the exception to the user by adding a flashed message to the session\n     * and then redirecting them back to the page that they came from. If the\n     * request originated from an API hit, return the error in JSONAPI spec format.\n     */\n    public function render(Request $request): JsonResponse|RedirectResponse\n    {\n        if ($request->expectsJson()) {\n            return response()->json(Handler::toArray($this), $this->getStatusCode(), $this->getHeaders());\n        }\n\n        app(AlertsMessageBag::class)->danger($this->getMessage())->flash();\n\n        return redirect()->back()->withInput();\n    }\n\n    /**\n     * Log the exception to the logs using the defined error level only if the previous\n     * exception is set.\n     *\n     * @throws \\Throwable\n     */\n    public function report()\n    {\n        if (!$this->getPrevious() instanceof \\Exception || !Handler::isReportable($this->getPrevious())) {\n            return null;\n        }\n\n        try {\n            $logger = Container::getInstance()->make(LoggerInterface::class);\n        } catch (\\Exception) {\n            throw $this->getPrevious();\n        }\n\n        return $logger->{$this->getErrorLevel()}($this->getPrevious());\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Handler.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions;\n\nuse Exception;\nuse Illuminate\\Support\\Arr;\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Http\\JsonResponse;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Database\\Connection;\nuse Illuminate\\Http\\RedirectResponse;\nuse Illuminate\\Foundation\\Application;\nuse Illuminate\\Auth\\AuthenticationException;\nuse Illuminate\\Session\\TokenMismatchException;\nuse Illuminate\\Validation\\ValidationException;\nuse Symfony\\Component\\HttpFoundation\\Response;\nuse Illuminate\\Auth\\Access\\AuthorizationException;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpException;\nuse Symfony\\Component\\Mailer\\Exception\\TransportException;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\nuse Illuminate\\Foundation\\Exceptions\\Handler as ExceptionHandler;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpExceptionInterface;\n\nclass Handler extends ExceptionHandler\n{\n    /**\n     * The validation parser in Laravel formats custom rules using the class name\n     * resulting in some weird rule names. This string will be parsed out and\n     * replaced with 'p_' in the response code.\n     */\n    private const PTERODACTYL_RULE_STRING = 'pterodactyl\\_rules\\_';\n\n    /**\n     * A list of the exception types that should not be reported.\n     */\n    protected $dontReport = [\n        AuthenticationException::class,\n        AuthorizationException::class,\n        HttpException::class,\n        ModelNotFoundException::class,\n        RecordNotFoundException::class,\n        TokenMismatchException::class,\n        ValidationException::class,\n    ];\n\n    /**\n     * Maps exceptions to a specific response code. This handles special exception\n     * types that don't have a defined response code.\n     */\n    protected static array $exceptionResponseCodes = [\n        AuthenticationException::class => 401,\n        AuthorizationException::class => 403,\n        ValidationException::class => 422,\n    ];\n\n    /**\n     * A list of the inputs that are never flashed for validation exceptions.\n     */\n    protected $dontFlash = [\n        'token',\n        'secret',\n        'password',\n        'password_confirmation',\n    ];\n\n    /**\n     * Registers the exception handling callbacks for the application. This\n     * will capture specific exception types that we do not want to include\n     * the detailed stack traces for since they could reveal credentials to\n     * whoever can read the logs.\n     *\n     * @noinspection PhpUnusedLocalVariableInspection\n     */\n    public function register(): void\n    {\n        if (config('app.exceptions.report_all', false)) {\n            $this->dontReport = [];\n        }\n\n        $this->reportable(function (\\PDOException $ex) {\n            $ex = $this->generateCleanedExceptionStack($ex);\n        });\n\n        $this->reportable(function (TransportException $ex) {\n            $ex = $this->generateCleanedExceptionStack($ex);\n        });\n    }\n\n    private function generateCleanedExceptionStack(\\Throwable $exception): string\n    {\n        $cleanedStack = '';\n        foreach ($exception->getTrace() as $index => $item) {\n            $cleanedStack .= sprintf(\n                \"#%d %s(%d): %s%s%s\\n\",\n                $index,\n                Arr::get($item, 'file'),\n                Arr::get($item, 'line'),\n                Arr::get($item, 'class'),\n                Arr::get($item, 'type'),\n                Arr::get($item, 'function')\n            );\n        }\n\n        $message = sprintf(\n            '%s: %s in %s:%d',\n            class_basename($exception),\n            $exception->getMessage(),\n            $exception->getFile(),\n            $exception->getLine()\n        );\n\n        return $message . \"\\nStack trace:\\n\" . trim($cleanedStack);\n    }\n\n    /**\n     * Render an exception into an HTTP response.\n     *\n     * @param \\Illuminate\\Http\\Request $request\n     *\n     * @throws \\Throwable\n     */\n    public function render($request, \\Throwable $e): Response\n    {\n        $connections = $this->container->make(Connection::class);\n\n        // If we are currently wrapped up inside a transaction, we will roll all the way\n        // back to the beginning. This needs to happen, otherwise session data does not\n        // get properly persisted.\n        //\n        // This is kind of a hack, and ideally things like this should be handled as\n        // much as possible at the code level, but there are a lot of spots that do a\n        // ton of actions and were written before this bug discovery was made.\n        //\n        // @see https://github.com/pterodactyl/panel/pull/1468\n        if ($connections->transactionLevel()) {\n            $connections->rollBack(0);\n        }\n\n        return parent::render($request, $e);\n    }\n\n    /**\n     * Transform a validation exception into a consistent format to be returned for\n     * calls to the API.\n     *\n     * @param \\Illuminate\\Http\\Request $request\n     */\n    public function invalidJson($request, ValidationException $exception): JsonResponse\n    {\n        $codes = Collection::make($exception->validator->failed())->mapWithKeys(function ($reasons, $field) {\n            $cleaned = [];\n            foreach ($reasons as $reason => $attrs) {\n                $cleaned[] = Str::snake($reason);\n            }\n\n            return [str_replace('.', '_', $field) => $cleaned];\n        })->toArray();\n\n        $errors = Collection::make($exception->errors())->map(function ($errors, $field) use ($codes, $exception) {\n            $response = [];\n            foreach ($errors as $key => $error) {\n                $meta = [\n                    'source_field' => $field,\n                    'rule' => str_replace(self::PTERODACTYL_RULE_STRING, 'p_', Arr::get(\n                        $codes,\n                        str_replace('.', '_', $field) . '.' . $key\n                    )),\n                ];\n\n                $converted = $this->convertExceptionToArray($exception)['errors'][0];\n                $converted['detail'] = $error;\n                $converted['meta'] = array_merge($converted['meta'] ?? [], $meta);\n\n                $response[] = $converted;\n            }\n\n            return $response;\n        })->flatMap(function ($errors) {\n            return $errors;\n        })->toArray();\n\n        return response()->json(['errors' => $errors], $exception->status);\n    }\n\n    /**\n     * Return the exception as a JSONAPI representation for use on API requests.\n     */\n    protected function convertExceptionToArray(\\Throwable $e, array $override = []): array\n    {\n        $match = self::$exceptionResponseCodes[get_class($e)] ?? null;\n\n        $error = [\n            'code' => class_basename($e),\n            'status' => method_exists($e, 'getStatusCode')\n                ? strval($e->getStatusCode())\n                : strval($match ?? '500'),\n            'detail' => $e instanceof HttpExceptionInterface || !is_null($match)\n                ? $e->getMessage()\n                : '处理此请求时遇到意外错误，请再试一次。',\n        ];\n\n        if ($e instanceof ModelNotFoundException || $e->getPrevious() instanceof ModelNotFoundException) {\n            // Show a nicer error message compared to the standard \"No query results for model\"\n            // response that is normally returned. If we are in debug mode this will get overwritten\n            // with a more specific error message to help narrow down things.\n            $error['detail'] = '无法在服务器上找到请求的资源。';\n        }\n\n        if (config('app.debug')) {\n            $error = array_merge($error, [\n                'detail' => $e->getMessage(),\n                'source' => [\n                    'line' => $e->getLine(),\n                    'file' => str_replace(Application::getInstance()->basePath(), '', $e->getFile()),\n                ],\n                'meta' => [\n                    'trace' => Collection::make($e->getTrace())\n                        ->map(fn ($trace) => Arr::except($trace, ['args']))\n                        ->all(),\n                    'previous' => Collection::make($this->extractPrevious($e))\n                        ->map(fn ($exception) => $e->getTrace())\n                        ->map(fn ($trace) => Arr::except($trace, ['args']))\n                        ->all(),\n                ],\n            ]);\n        }\n\n        return ['errors' => [array_merge($error, $override)]];\n    }\n\n    /**\n     * Return an array of exceptions that should not be reported.\n     */\n    public static function isReportable(\\Exception $exception): bool\n    {\n        return (new self(Container::getInstance()))->shouldReport($exception);\n    }\n\n    /**\n     * Convert an authentication exception into an unauthenticated response.\n     *\n     * @param \\Illuminate\\Http\\Request $request\n     */\n    protected function unauthenticated($request, AuthenticationException $exception): JsonResponse|RedirectResponse\n    {\n        if ($request->expectsJson()) {\n            return new JsonResponse($this->convertExceptionToArray($exception), JsonResponse::HTTP_UNAUTHORIZED);\n        }\n\n        return redirect()->guest('/auth/login');\n    }\n\n    /**\n     * Extracts all the previous exceptions that lead to the one passed into this\n     * function being thrown.\n     *\n     * @return \\Throwable[]\n     */\n    protected function extractPrevious(\\Throwable $e): array\n    {\n        $previous = [];\n        while ($value = $e->getPrevious()) {\n            if (!$value instanceof \\Throwable) { // @phpstan-ignore instanceof.alwaysTrue\n                break;\n            }\n            $previous[] = $value;\n            $e = $value;\n        }\n\n        return $previous;\n    }\n\n    /**\n     * Helper method to allow reaching into the handler to convert an exception\n     * into the expected array response type.\n     */\n    public static function toArray(\\Throwable $e): array\n    {\n        return (new self(app()))->convertExceptionToArray($e);\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Http/Base/InvalidPasswordProvidedException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Http\\Base;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass InvalidPasswordProvidedException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Http/Connection/DaemonConnectionException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Http\\Connection;\n\nuse Illuminate\\Http\\Response;\nuse Illuminate\\Support\\Facades\\Log;\nuse GuzzleHttp\\Exception\\GuzzleException;\nuse Pterodactyl\\Exceptions\\DisplayException;\n\n/**\n * @method \\GuzzleHttp\\Exception\\GuzzleException getPrevious()\n */\nclass DaemonConnectionException extends DisplayException\n{\n    private int $statusCode = Response::HTTP_GATEWAY_TIMEOUT;\n\n    /**\n     * Every request to the Wings instance will return a unique X-Request-Id header\n     * which allows for all errors to be efficiently tied to a specific request that\n     * triggered them, and gives users a more direct method of informing hosts when\n     * something goes wrong.\n     */\n    private ?string $requestId;\n\n    /**\n     * Throw a displayable exception caused by a daemon connection error.\n     */\n    public function __construct(GuzzleException $previous, bool $useStatusCode = true)\n    {\n        /** @var \\GuzzleHttp\\Psr7\\Response|null $response */\n        $response = method_exists($previous, 'getResponse') ? $previous->getResponse() : null;\n        $this->requestId = $response?->getHeaderLine('X-Request-Id');\n\n        if ($useStatusCode) {\n            $this->statusCode = is_null($response) ? $this->statusCode : $response->getStatusCode();\n            // There are rare conditions where wings encounters a panic condition and crashes the\n            // request being made after content has already been sent over the wire. In these cases\n            // you can end up with a \"successful\" response code that is actual an error.\n            //\n            // Handle those better here since we shouldn't ever end up in this exception state and\n            // be returning a 2XX level response.\n            if ($this->statusCode < 400) {\n                $this->statusCode = Response::HTTP_BAD_GATEWAY;\n            }\n        }\n\n        if (is_null($response)) {\n            $message = '无法与运行此服务器的主机建立连接。请再试一次。';\n        } else {\n            $message = sprintf('与运行此服务器的主机通信时出错。已记录此错误，请重试。(code: %s) (request_id: %s)', $response->getStatusCode(), $this->requestId ?? '<nil>');\n        }\n\n        // Attempt to pull the actual error message off the response and return that if it is not\n        // a 500 level error.\n        if ($this->statusCode < 500 && !is_null($response)) {\n            $body = json_decode($response->getBody()->__toString(), true);\n            $message = sprintf('远程主机发生错误: %s. (request id: %s)', $body['error'] ?? $message, $this->requestId ?? '<nil>');\n        }\n\n        $level = $this->statusCode >= 500 && $this->statusCode !== 504\n            ? DisplayException::LEVEL_ERROR\n            : DisplayException::LEVEL_WARNING;\n\n        parent::__construct($message, $previous, $level);\n    }\n\n    /**\n     * Override the default reporting method for DisplayException by just logging immediately\n     * here and including the specific X-Request-Id header that was returned by the call.\n     */\n    public function report()\n    {\n        Log::{$this->getErrorLevel()}($this->getPrevious(), [\n            'request_id' => $this->requestId,\n        ]);\n    }\n\n    /**\n     * Return the HTTP status code for this exception.\n     */\n    public function getStatusCode(): int\n    {\n        return $this->statusCode;\n    }\n\n    public function getRequestId(): ?string\n    {\n        return $this->requestId;\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Http/HttpForbiddenException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Http;\n\nuse Illuminate\\Http\\Response;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpException;\n\nclass HttpForbiddenException extends HttpException\n{\n    /**\n     * HttpForbiddenException constructor.\n     */\n    public function __construct(?string $message = null, ?\\Throwable $previous = null)\n    {\n        parent::__construct(Response::HTTP_FORBIDDEN, $message, $previous);\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Http/Server/FileSizeTooLargeException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Http\\Server;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass FileSizeTooLargeException extends DisplayException\n{\n    /**\n     * FileSizeTooLargeException constructor.\n     */\n    public function __construct()\n    {\n        parent::__construct('您试图打开的文件太大，无法在文件编辑器中查看。');\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Http/Server/FileTypeNotEditableException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Http\\Server;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass FileTypeNotEditableException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Http/Server/ServerStateConflictException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Http\\Server;\n\nuse Pterodactyl\\Models\\Server;\nuse Symfony\\Component\\HttpKernel\\Exception\\ConflictHttpException;\n\nclass ServerStateConflictException extends ConflictHttpException\n{\n    /**\n     * Exception thrown when the server is in an unsupported state for API access or\n     * certain operations within the codebase.\n     */\n    public function __construct(Server $server, ?\\Throwable $previous = null)\n    {\n        $message = '此服务器目前处于不受支持的状态，请稍后再试。';\n        if ($server->isSuspended()) {\n            $message = '此服务器已被冻结，请求的功能不可用。';\n        } elseif ($server->node->isUnderMaintenance()) {\n            $message = '此服务器的节点目前正在维护中，请求的功能不可用。';\n        } elseif (!$server->isInstalled()) {\n            $message = '此服务器尚未完成安装过程，请稍后再试。';\n        } elseif ($server->status === Server::STATUS_RESTORING_BACKUP) {\n            $message = '此服务器当前正在从备份中恢复，请稍后再试。';\n        } elseif (!is_null($server->transfer)) {\n            $message = '此服务器目前正在转移到新主机上，请稍后再试。';\n        }\n\n        parent::__construct($message, $previous);\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Http/TwoFactorAuthRequiredException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Http;\n\nuse Illuminate\\Http\\Response;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpException;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpExceptionInterface;\n\nclass TwoFactorAuthRequiredException extends HttpException implements HttpExceptionInterface\n{\n    /**\n     * TwoFactorAuthRequiredException constructor.\n     */\n    public function __construct(?\\Throwable $previous = null)\n    {\n        parent::__construct(Response::HTTP_BAD_REQUEST, '此帐户需要动态口令认证才能访问此端点。', $previous);\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/ManifestDoesNotExistException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions;\n\nuse Spatie\\Ignition\\Contracts\\Solution;\nuse Spatie\\Ignition\\Contracts\\ProvidesSolution;\n\nclass ManifestDoesNotExistException extends \\Exception implements ProvidesSolution\n{\n    public function getSolution(): Solution\n    {\n        return new Solutions\\ManifestDoesNotExistSolution();\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Model/DataValidationException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Model;\n\nuse Illuminate\\Support\\MessageBag;\nuse Illuminate\\Database\\Eloquent\\Model;\nuse Illuminate\\Contracts\\Validation\\Validator;\nuse Pterodactyl\\Exceptions\\PterodactylException;\nuse Illuminate\\Contracts\\Support\\MessageProvider;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpExceptionInterface;\n\nclass DataValidationException extends PterodactylException implements HttpExceptionInterface, MessageProvider\n{\n    /**\n     * DataValidationException constructor.\n     */\n    public function __construct(protected Validator $validator, protected Model $model)\n    {\n        $message = sprintf(\n            '无法保存 %s[%s]: 验证数据失败: %s',\n            get_class($model),\n            $model->getKey(),\n            $validator->errors()->toJson()\n        );\n\n        parent::__construct($message);\n    }\n\n    /**\n     * Return the validator message bag.\n     */\n    public function getMessageBag(): MessageBag\n    {\n        return $this->validator->errors();\n    }\n\n    /**\n     * Return the status code for this request.\n     */\n    public function getStatusCode(): int\n    {\n        return 500;\n    }\n\n    public function getHeaders(): array\n    {\n        return [];\n    }\n\n    public function getValidator(): Validator\n    {\n        return $this->validator;\n    }\n\n    public function getModel(): Model\n    {\n        return $this->model;\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/PterodactylException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions;\n\nclass PterodactylException extends \\Exception\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Repository/Daemon/InvalidPowerSignalException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Repository\\Daemon;\n\nuse Pterodactyl\\Exceptions\\Repository\\RepositoryException;\n\nclass InvalidPowerSignalException extends RepositoryException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Repository/DuplicateDatabaseNameException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Repository;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass DuplicateDatabaseNameException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Repository/RecordNotFoundException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Repository;\n\nuse Illuminate\\Http\\Response;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpExceptionInterface;\n\nclass RecordNotFoundException extends RepositoryException implements HttpExceptionInterface\n{\n    /**\n     * Returns the status code.\n     */\n    public function getStatusCode(): int\n    {\n        return Response::HTTP_NOT_FOUND;\n    }\n\n    /**\n     * Returns response headers.\n     */\n    public function getHeaders(): array\n    {\n        return [];\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Repository/RepositoryException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Repository;\n\nuse Pterodactyl\\Exceptions\\PterodactylException;\n\nclass RepositoryException extends PterodactylException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Allocation/AllocationDoesNotBelongToServerException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Allocation;\n\nuse Pterodactyl\\Exceptions\\PterodactylException;\n\nclass AllocationDoesNotBelongToServerException extends PterodactylException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Allocation/AutoAllocationNotEnabledException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Allocation;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass AutoAllocationNotEnabledException extends DisplayException\n{\n    /**\n     * AutoAllocationNotEnabledException constructor.\n     */\n    public function __construct()\n    {\n        parent::__construct(\n            '此实例未启用服务器自动分配功能。'\n        );\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Allocation/CidrOutOfRangeException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Allocation;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass CidrOutOfRangeException extends DisplayException\n{\n    /**\n     * CidrOutOfRangeException constructor.\n     */\n    public function __construct()\n    {\n        parent::__construct(trans('exceptions.allocations.cidr_out_of_range'));\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Allocation/InvalidPortMappingException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Allocation;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass InvalidPortMappingException extends DisplayException\n{\n    /**\n     * InvalidPortMappingException constructor.\n     */\n    public function __construct(mixed $port)\n    {\n        parent::__construct(trans('exceptions.allocations.invalid_mapping', ['port' => $port]));\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Allocation/NoAutoAllocationSpaceAvailableException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Allocation;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass NoAutoAllocationSpaceAvailableException extends DisplayException\n{\n    /**\n     * NoAutoAllocationSpaceAvailableException constructor.\n     */\n    public function __construct()\n    {\n        parent::__construct(\n            '无法分配更多端口：节点上没有可用空间。'\n        );\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Allocation/PortOutOfRangeException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Allocation;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass PortOutOfRangeException extends DisplayException\n{\n    /**\n     * PortOutOfRangeException constructor.\n     */\n    public function __construct()\n    {\n        parent::__construct(trans('exceptions.allocations.port_out_of_range'));\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Allocation/ServerUsingAllocationException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Allocation;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass ServerUsingAllocationException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Allocation/TooManyPortsInRangeException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Allocation;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass TooManyPortsInRangeException extends DisplayException\n{\n    /**\n     * TooManyPortsInRangeException constructor.\n     */\n    public function __construct()\n    {\n        parent::__construct(trans('exceptions.allocations.too_many_ports'));\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Backup/BackupLockedException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Backup;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass BackupLockedException extends DisplayException\n{\n    /**\n     * TooManyBackupsException constructor.\n     */\n    public function __construct()\n    {\n        parent::__construct('不能删除标记为锁定的备份。');\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Backup/TooManyBackupsException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Backup;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass TooManyBackupsException extends DisplayException\n{\n    /**\n     * TooManyBackupsException constructor.\n     */\n    public function __construct(int $backupLimit)\n    {\n        parent::__construct(\n            sprintf('无法创建新备份，此服务器已达到 %d 个备份的限制。', $backupLimit)\n        );\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Database/DatabaseClientFeatureNotEnabledException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Database;\n\nuse Pterodactyl\\Exceptions\\PterodactylException;\n\nclass DatabaseClientFeatureNotEnabledException extends PterodactylException\n{\n    public function __construct()\n    {\n        parent::__construct('此面板未启用在客户端创建数据库。');\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Database/NoSuitableDatabaseHostException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Database;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass NoSuitableDatabaseHostException extends DisplayException\n{\n    /**\n     * NoSuitableDatabaseHostException constructor.\n     */\n    public function __construct()\n    {\n        parent::__construct('未找到满足此服务器要求的数据库主机。');\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Database/TooManyDatabasesException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Database;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass TooManyDatabasesException extends DisplayException\n{\n    public function __construct()\n    {\n        parent::__construct('操作中止：创建新数据库会使该服务器超出设定的限制。');\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Deployment/NoViableAllocationException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Deployment;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass NoViableAllocationException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Deployment/NoViableNodeException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Deployment;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass NoViableNodeException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Egg/BadJsonFormatException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Egg;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass BadJsonFormatException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Egg/HasChildrenException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Egg;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass HasChildrenException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Egg/InvalidCopyFromException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Egg;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass InvalidCopyFromException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Egg/NoParentConfigurationFoundException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Egg;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass NoParentConfigurationFoundException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Egg/Variable/BadValidationRuleException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Egg\\Variable;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass BadValidationRuleException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Egg/Variable/ReservedVariableNameException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Egg\\Variable;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass ReservedVariableNameException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/HasActiveServersException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass HasActiveServersException extends DisplayException\n{\n    public function getStatusCode(): int\n    {\n        return Response::HTTP_BAD_REQUEST;\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Helper/CdnVersionFetchingException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Helper;\n\nclass CdnVersionFetchingException extends \\Exception\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/InvalidFileUploadException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass InvalidFileUploadException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Location/HasActiveNodesException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Location;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass HasActiveNodesException extends DisplayException\n{\n    public function getStatusCode(): int\n    {\n        return Response::HTTP_BAD_REQUEST;\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Node/ConfigurationNotPersistedException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Node;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass ConfigurationNotPersistedException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Schedule/Task/TaskIntervalTooLongException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Schedule\\Task;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass TaskIntervalTooLongException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Server/RequiredVariableMissingException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Server;\n\nuse Pterodactyl\\Exceptions\\PterodactylException;\n\nclass RequiredVariableMissingException extends PterodactylException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/ServiceLimitExceededException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass ServiceLimitExceededException extends DisplayException\n{\n    /**\n     * Exception thrown when something goes over a defined limit, such as allocated\n     * ports, tasks, databases, etc.\n     */\n    public function __construct(string $message, ?\\Throwable $previous = null)\n    {\n        parent::__construct($message, $previous, self::LEVEL_WARNING);\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Subuser/ServerSubuserExistsException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Subuser;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass ServerSubuserExistsException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/Subuser/UserIsServerOwnerException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\Subuser;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass UserIsServerOwnerException extends DisplayException\n{\n}\n"
  },
  {
    "path": "app/Exceptions/Service/User/TwoFactorAuthenticationTokenInvalid.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Service\\User;\n\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass TwoFactorAuthenticationTokenInvalid extends DisplayException\n{\n    /**\n     * TwoFactorAuthenticationTokenInvalid constructor.\n     */\n    public function __construct()\n    {\n        parent::__construct('提供的动态口令无效。');\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Solutions/ManifestDoesNotExistSolution.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Solutions;\n\nuse Spatie\\Ignition\\Contracts\\Solution;\n\nclass ManifestDoesNotExistSolution implements Solution\n{\n    public function getSolutionTitle(): string\n    {\n        return 'manifest.json 文件尚未生成';\n    }\n\n    public function getSolutionDescription(): string\n    {\n        return '首先运行 yarn run build:production 来构建前端。';\n    }\n\n    public function getDocumentationLinks(): array\n    {\n        return [\n            'Docs' => 'https://github.com/pterodactyl-china/panel/blob/develop/package.json',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Exceptions/Transformer/InvalidTransformerLevelException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Exceptions\\Transformer;\n\nuse Pterodactyl\\Exceptions\\PterodactylException;\n\nclass InvalidTransformerLevelException extends PterodactylException\n{\n}\n"
  },
  {
    "path": "app/Extensions/Backups/BackupManager.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions\\Backups;\n\nuse Closure;\nuse Aws\\S3\\S3Client;\nuse Illuminate\\Support\\Arr;\nuse Illuminate\\Support\\Str;\nuse Webmozart\\Assert\\Assert;\nuse Illuminate\\Foundation\\Application;\nuse League\\Flysystem\\FilesystemAdapter;\nuse Pterodactyl\\Extensions\\Filesystem\\S3Filesystem;\nuse League\\Flysystem\\InMemory\\InMemoryFilesystemAdapter;\nuse Illuminate\\Contracts\\Config\\Repository as ConfigRepository;\n\nclass BackupManager\n{\n    protected ConfigRepository $config;\n\n    /**\n     * The array of resolved backup drivers.\n     */\n    protected array $adapters = [];\n\n    /**\n     * The registered custom driver creators.\n     */\n    protected array $customCreators;\n\n    /**\n     * BackupManager constructor.\n     */\n    public function __construct(protected Application $app)\n    {\n        $this->config = $app->make(ConfigRepository::class);\n    }\n\n    /**\n     * Returns a backup adapter instance.\n     */\n    public function adapter(?string $name = null): FilesystemAdapter\n    {\n        return $this->get($name ?: $this->getDefaultAdapter());\n    }\n\n    /**\n     * Set the given backup adapter instance.\n     */\n    public function set(string $name, FilesystemAdapter $disk): self\n    {\n        $this->adapters[$name] = $disk;\n\n        return $this;\n    }\n\n    /**\n     * Gets a backup adapter.\n     */\n    protected function get(string $name): FilesystemAdapter\n    {\n        return $this->adapters[$name] = $this->resolve($name);\n    }\n\n    /**\n     * Resolve the given backup disk.\n     */\n    protected function resolve(string $name): FilesystemAdapter\n    {\n        $config = $this->getConfig($name);\n\n        if (empty($config['adapter'])) {\n            throw new \\InvalidArgumentException(\"备份磁盘 [$name] 未配置适配器。\");\n        }\n\n        $adapter = $config['adapter'];\n\n        if (isset($this->customCreators[$name])) {\n            return $this->callCustomCreator($config);\n        }\n\n        $adapterMethod = 'create' . Str::studly($adapter) . 'Adapter';\n        if (method_exists($this, $adapterMethod)) {\n            $instance = $this->{$adapterMethod}($config);\n\n            Assert::isInstanceOf($instance, FilesystemAdapter::class);\n\n            return $instance;\n        }\n\n        throw new \\InvalidArgumentException(\"适配器 [$adapter] 不受支持。\");\n    }\n\n    /**\n     * Calls a custom creator for a given adapter type.\n     */\n    protected function callCustomCreator(array $config): mixed\n    {\n        return $this->customCreators[$config['adapter']]($this->app, $config);\n    }\n\n    /**\n     * Creates a new Wings adapter.\n     */\n    public function createWingsAdapter(array $config): FilesystemAdapter\n    {\n        return new InMemoryFilesystemAdapter();\n    }\n\n    /**\n     * Creates a new S3 adapter.\n     */\n    public function createS3Adapter(array $config): FilesystemAdapter\n    {\n        $config['version'] = 'latest';\n\n        if (!empty($config['key']) && !empty($config['secret'])) {\n            $config['credentials'] = Arr::only($config, ['key', 'secret', 'token']);\n        }\n\n        $client = new S3Client($config);\n\n        return new S3Filesystem($client, $config['bucket'], $config['prefix'] ?? '', $config['options'] ?? []);\n    }\n\n    /**\n     * Returns the configuration associated with a given backup type.\n     */\n    protected function getConfig(string $name): array\n    {\n        return $this->config->get(\"backups.disks.$name\") ?: [];\n    }\n\n    /**\n     * Get the default backup driver name.\n     */\n    public function getDefaultAdapter(): string\n    {\n        return $this->config->get('backups.default');\n    }\n\n    /**\n     * Set the default session driver name.\n     */\n    public function setDefaultAdapter(string $name): void\n    {\n        $this->config->set('backups.default', $name);\n    }\n\n    /**\n     * Unset the given adapter instances.\n     *\n     * @param string|string[] $adapter\n     */\n    public function forget(array|string $adapter): self\n    {\n        foreach ((array) $adapter as $adapterName) {\n            unset($this->adapters[$adapterName]);\n        }\n\n        return $this;\n    }\n\n    /**\n     * Register a custom adapter creator closure.\n     */\n    public function extend(string $adapter, \\Closure $callback): self\n    {\n        $this->customCreators[$adapter] = $callback;\n\n        return $this;\n    }\n}\n"
  },
  {
    "path": "app/Extensions/DynamicDatabaseConnection.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions;\n\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Illuminate\\Config\\Repository as ConfigRepository;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseHostRepositoryInterface;\n\nclass DynamicDatabaseConnection\n{\n    public const DB_CHARSET = 'utf8';\n    public const DB_COLLATION = 'utf8_unicode_ci';\n    public const DB_DRIVER = 'mysql';\n\n    /**\n     * DynamicDatabaseConnection constructor.\n     */\n    public function __construct(\n        protected ConfigRepository $config,\n        protected Encrypter $encrypter,\n        protected DatabaseHostRepositoryInterface $repository,\n    ) {\n    }\n\n    /**\n     * Adds a dynamic database connection entry to the runtime config.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function set(string $connection, DatabaseHost|int $host, string $database = 'mysql'): void\n    {\n        if (!$host instanceof DatabaseHost) {\n            $host = $this->repository->find($host);\n        }\n\n        $this->config->set('database.connections.' . $connection, [\n            'driver' => self::DB_DRIVER,\n            'host' => $host->host,\n            'port' => $host->port,\n            'database' => $database,\n            'username' => $host->username,\n            'password' => $this->encrypter->decrypt($host->password),\n            'charset' => self::DB_CHARSET,\n            'collation' => self::DB_COLLATION,\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Extensions/Facades/Theme.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions\\Facades;\n\nuse Illuminate\\Support\\Facades\\Facade;\n\nclass Theme extends Facade\n{\n    protected static function getFacadeAccessor(): string\n    {\n        return 'extensions.themes';\n    }\n}\n"
  },
  {
    "path": "app/Extensions/Filesystem/S3Filesystem.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions\\Filesystem;\n\nuse Aws\\S3\\S3ClientInterface;\nuse League\\Flysystem\\AwsS3V3\\AwsS3V3Adapter;\n\nclass S3Filesystem extends AwsS3V3Adapter\n{\n    public function __construct(\n        private S3ClientInterface $client,\n        private string $bucket,\n        string $prefix = '',\n        array $options = [],\n    ) {\n        parent::__construct(\n            $client,\n            $bucket,\n            $prefix,\n            null,\n            null,\n            $options,\n        );\n    }\n\n    public function getClient(): S3ClientInterface\n    {\n        return $this->client;\n    }\n\n    public function getBucket(): string\n    {\n        return $this->bucket;\n    }\n}\n"
  },
  {
    "path": "app/Extensions/Hashids.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions;\n\nuse Illuminate\\Support\\Arr;\nuse Hashids\\Hashids as VendorHashids;\nuse Pterodactyl\\Contracts\\Extensions\\HashidsInterface;\n\nclass Hashids extends VendorHashids implements HashidsInterface\n{\n    public function decodeFirst(string $encoded, ?string $default = null): mixed\n    {\n        $result = $this->decode($encoded);\n\n        return Arr::first($result, null, $default);\n    }\n}\n"
  },
  {
    "path": "app/Extensions/Illuminate/Database/Eloquent/Builder.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions\\Illuminate\\Database\\Eloquent;\n\nuse Illuminate\\Database\\Eloquent\\Builder as EloquentBuilder;\n\nclass Builder extends EloquentBuilder\n{\n    /**\n     * Do nothing.\n     */\n    public function search(): self\n    {\n        return $this;\n    }\n}\n"
  },
  {
    "path": "app/Extensions/Illuminate/Events/Contracts/SubscribesToEvents.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions\\Illuminate\\Events\\Contracts;\n\nuse Illuminate\\Contracts\\Events\\Dispatcher;\n\ninterface SubscribesToEvents\n{\n    public function subscribe(Dispatcher $events): void;\n}\n"
  },
  {
    "path": "app/Extensions/Laravel/Sanctum/NewAccessToken.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions\\Laravel\\Sanctum;\n\nuse Pterodactyl\\Models\\ApiKey;\nuse Laravel\\Sanctum\\NewAccessToken as SanctumAccessToken;\n\n/**\n * @property ApiKey $accessToken\n */\nclass NewAccessToken extends SanctumAccessToken\n{\n    /**\n     * NewAccessToken constructor.\n     *\n     * @noinspection PhpMissingParentConstructorInspection\n     */\n    public function __construct(ApiKey $accessToken, string $plainTextToken)\n    {\n        $this->accessToken = $accessToken;\n        $this->plainTextToken = $plainTextToken;\n    }\n}\n"
  },
  {
    "path": "app/Extensions/Lcobucci/JWT/Encoding/TimestampDates.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions\\Lcobucci\\JWT\\Encoding;\n\nuse Lcobucci\\JWT\\ClaimsFormatter;\nuse Lcobucci\\JWT\\Token\\RegisteredClaims;\n\nfinal class TimestampDates implements ClaimsFormatter\n{\n    /**\n     * The default time encoder for JWTs using this library is not supported correctly\n     * by Wings and will cause a flood of errors and panic conditions because the times\n     * cannot be parsed correctly. The default is time with microseconds, we just need\n     * to use the normal unix timestamp here.\n     */\n    public function formatClaims(array $claims): array\n    {\n        foreach (RegisteredClaims::DATE_CLAIMS as $claim) {\n            if (!array_key_exists($claim, $claims)) {\n                continue;\n            }\n\n            assert($claims[$claim] instanceof \\DateTimeImmutable);\n            $claims[$claim] = $claims[$claim]->getTimestamp();\n        }\n\n        return $claims;\n    }\n}\n"
  },
  {
    "path": "app/Extensions/League/Fractal/Serializers/PterodactylSerializer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions\\League\\Fractal\\Serializers;\n\nuse League\\Fractal\\Serializer\\ArraySerializer;\n\nclass PterodactylSerializer extends ArraySerializer\n{\n    /**\n     * Serialize an item.\n     */\n    public function item(?string $resourceKey, array $data): array\n    {\n        return [\n            'object' => $resourceKey,\n            'attributes' => $data,\n        ];\n    }\n\n    /**\n     * Serialize a collection.\n     */\n    public function collection(?string $resourceKey, array $data): array\n    {\n        $response = [];\n        foreach ($data as $datum) {\n            $response[] = $this->item($resourceKey, $datum);\n        }\n\n        return [\n            'object' => 'list',\n            'data' => $response,\n        ];\n    }\n\n    /**\n     * Serialize a null resource.\n     */\n    public function null(): ?array\n    {\n        return [\n            'object' => 'null_resource',\n            'attributes' => null,\n        ];\n    }\n\n    /**\n     * Merge the included resources with the parent resource being serialized.\n     */\n    public function mergeIncludes(array $transformedData, array $includedData): array\n    {\n        foreach ($includedData as $key => $datum) {\n            $transformedData['relationships'][$key] = $datum;\n        }\n\n        return $transformedData;\n    }\n}\n"
  },
  {
    "path": "app/Extensions/Spatie/Fractalistic/Fractal.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions\\Spatie\\Fractalistic;\n\nuse League\\Fractal\\Scope;\nuse League\\Fractal\\TransformerAbstract;\nuse Spatie\\Fractal\\Fractal as SpatieFractal;\nuse Illuminate\\Contracts\\Pagination\\LengthAwarePaginator;\nuse League\\Fractal\\Pagination\\IlluminatePaginatorAdapter;\nuse Pterodactyl\\Extensions\\League\\Fractal\\Serializers\\PterodactylSerializer;\n\nclass Fractal extends SpatieFractal\n{\n    /**\n     * Create fractal data.\n     *\n     * @throws \\Spatie\\Fractalistic\\Exceptions\\InvalidTransformation\n     * @throws \\Spatie\\Fractalistic\\Exceptions\\NoTransformerSpecified\n     */\n    public function createData(): Scope\n    {\n        // Set the serializer by default.\n        if (is_null($this->serializer)) {\n            $this->serializer = new PterodactylSerializer();\n        }\n\n        // Automatically set the paginator on the response object if the\n        // data being provided implements a paginator.\n        if (is_null($this->paginator) && $this->data instanceof LengthAwarePaginator) {\n            $this->paginator = new IlluminatePaginatorAdapter($this->data);\n        }\n\n        // If the resource name is not set attempt to pull it off the transformer\n        // itself and set it automatically.\n        if (\n            is_null($this->resourceName)\n            && $this->transformer instanceof TransformerAbstract\n            && method_exists($this->transformer, 'getResourceName')\n        ) {\n            $this->resourceName = $this->transformer->getResourceName();\n        }\n\n        return parent::createData();\n    }\n}\n"
  },
  {
    "path": "app/Extensions/Themes/Theme.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Extensions\\Themes;\n\nclass Theme\n{\n    public function js($path): string\n    {\n        return sprintf('<script src=\"%s\"></script>' . PHP_EOL, $this->getUrl($path));\n    }\n\n    public function css($path): string\n    {\n        return sprintf('<link media=\"all\" type=\"text/css\" rel=\"stylesheet\" href=\"%s\"/>' . PHP_EOL, $this->getUrl($path));\n    }\n\n    protected function getUrl($path): string\n    {\n        return '/themes/pterodactyl/' . ltrim($path, '/');\n    }\n}\n"
  },
  {
    "path": "app/Facades/Activity.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Facades;\n\nuse Illuminate\\Support\\Facades\\Facade;\nuse Pterodactyl\\Services\\Activity\\ActivityLogService;\n\nclass Activity extends Facade\n{\n    protected static function getFacadeAccessor(): string\n    {\n        return ActivityLogService::class;\n    }\n}\n"
  },
  {
    "path": "app/Facades/LogBatch.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Facades;\n\nuse Illuminate\\Support\\Facades\\Facade;\nuse Pterodactyl\\Services\\Activity\\ActivityLogBatchService;\n\nclass LogBatch extends Facade\n{\n    protected static function getFacadeAccessor(): string\n    {\n        return ActivityLogBatchService::class;\n    }\n}\n"
  },
  {
    "path": "app/Facades/LogTarget.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Facades;\n\nuse Illuminate\\Support\\Facades\\Facade;\nuse Pterodactyl\\Services\\Activity\\ActivityLogTargetableService;\n\n/**\n * @mixin \\Pterodactyl\\Services\\Activity\\ActivityLogTargetableService\n */\nclass LogTarget extends Facade\n{\n    protected static function getFacadeAccessor(): string\n    {\n        return ActivityLogTargetableService::class;\n    }\n}\n"
  },
  {
    "path": "app/Helpers/Time.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Helpers;\n\nuse Carbon\\CarbonImmutable;\n\nfinal class Time\n{\n    /**\n     * Gets the time offset from the provided timezone relative to UTC as a number. This\n     * is used in the database configuration since we can't always rely on there being support\n     * for named timezones in MySQL.\n     *\n     * Returns the timezone as a string like +08:00 or -05:00 depending on the app timezone.\n     */\n    public static function getMySQLTimezoneOffset(string $timezone): string\n    {\n        return CarbonImmutable::now($timezone)->getTimezone()->toOffsetName();\n    }\n}\n"
  },
  {
    "path": "app/Helpers/Utilities.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Helpers;\n\nuse Carbon\\Carbon;\nuse Cron\\CronExpression;\nuse Illuminate\\Support\\Facades\\Log;\nuse Illuminate\\Support\\ViewErrorBag;\n\nclass Utilities\n{\n    /**\n     * Generates a random string and injects special characters into it, in addition to\n     * the randomness of the alphanumeric default response.\n     */\n    public static function randomStringWithSpecialCharacters(int $length = 16): string\n    {\n        $string = str_random($length);\n        // Given a random string of characters, randomly loop through the characters and replace some\n        // with special characters to avoid issues with MySQL password requirements on some servers.\n        try {\n            for ($i = 0; $i < random_int(2, 6); ++$i) {\n                $character = ['!', '@', '=', '.', '+', '^'][random_int(0, 5)];\n\n                $string = substr_replace($string, $character, random_int(0, $length - 1), 1);\n            }\n        } catch (\\Exception $exception) {\n            // Just log the error and hope for the best at this point.\n            Log::error($exception);\n        }\n\n        return $string;\n    }\n\n    /**\n     * Converts schedule cron data into a carbon object.\n     *\n     * @throws \\Exception\n     */\n    public static function getScheduleNextRunDate(string $minute, string $hour, string $dayOfMonth, string $month, string $dayOfWeek): Carbon\n    {\n        return Carbon::instance((new CronExpression(\n            sprintf('%s %s %s %s %s', $minute, $hour, $dayOfMonth, $month, $dayOfWeek)\n        ))->getNextRunDate());\n    }\n\n    public static function checked(string $name, mixed $default): string\n    {\n        $errors = session('errors');\n\n        if (isset($errors) && $errors instanceof ViewErrorBag && $errors->any()) {\n            return old($name) ? 'checked' : '';\n        }\n\n        return ($default) ? 'checked' : '';\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/ApiController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\ApiKey;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Api\\KeyCreationService;\nuse Pterodactyl\\Http\\Requests\\Admin\\Api\\StoreApplicationApiKeyRequest;\n\nclass ApiController extends Controller\n{\n    /**\n     * ApiController constructor.\n     */\n    public function __construct(\n        private AlertsMessageBag $alert,\n        private KeyCreationService $keyCreationService,\n    ) {\n    }\n\n    /**\n     * Render view showing all of a user's application API keys.\n     */\n    public function index(Request $request): View\n    {\n        return view('admin.api.index', [\n            'keys' => ApiKey::query()->where('key_type', ApiKey::TYPE_APPLICATION)->get(),\n        ]);\n    }\n\n    /**\n     * Render view allowing an admin to create a new application API key.\n     *\n     * @throws \\ReflectionException\n     */\n    public function create(): View\n    {\n        $resources = AdminAcl::getResourceList();\n        sort($resources);\n\n        return view('admin.api.new', [\n            'resources' => $resources,\n            'permissions' => [\n                'r' => AdminAcl::READ,\n                'rw' => AdminAcl::READ | AdminAcl::WRITE,\n                'n' => AdminAcl::NONE,\n            ],\n        ]);\n    }\n\n    /**\n     * Store the new key and redirect the user back to the application key listing.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function store(StoreApplicationApiKeyRequest $request): RedirectResponse\n    {\n        $this->keyCreationService->setKeyType(ApiKey::TYPE_APPLICATION)->handle([\n            'memo' => $request->input('memo'),\n            'user_id' => $request->user()->id,\n        ], $request->getKeyPermissions());\n\n        $this->alert->success('已为您的帐户生成了一个新的应用程序 API 密钥。')->flash();\n\n        return redirect()->route('admin.api.index');\n    }\n\n    /**\n     * Delete an application API key from the database.\n     */\n    public function delete(Request $request, string $identifier): Response\n    {\n        ApiKey::query()\n            ->where('key_type', ApiKey::TYPE_APPLICATION)\n            ->where('identifier', $identifier)\n            ->delete();\n\n        return response('', 204);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/BaseController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin;\n\nuse Illuminate\\View\\View;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Helpers\\SoftwareVersionService;\n\nclass BaseController extends Controller\n{\n    /**\n     * BaseController constructor.\n     */\n    public function __construct(private SoftwareVersionService $version)\n    {\n    }\n\n    /**\n     * Return the admin index view.\n     */\n    public function index(): View\n    {\n        return view('admin.index', ['version' => $this->version]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/DatabaseController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin;\n\nuse Illuminate\\View\\View;\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Databases\\Hosts\\HostUpdateService;\nuse Pterodactyl\\Http\\Requests\\Admin\\DatabaseHostFormRequest;\nuse Pterodactyl\\Services\\Databases\\Hosts\\HostCreationService;\nuse Pterodactyl\\Services\\Databases\\Hosts\\HostDeletionService;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\LocationRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseHostRepositoryInterface;\n\nclass DatabaseController extends Controller\n{\n    /**\n     * DatabaseController constructor.\n     */\n    public function __construct(\n        private AlertsMessageBag $alert,\n        private DatabaseHostRepositoryInterface $repository,\n        private DatabaseRepositoryInterface $databaseRepository,\n        private HostCreationService $creationService,\n        private HostDeletionService $deletionService,\n        private HostUpdateService $updateService,\n        private LocationRepositoryInterface $locationRepository,\n    ) {\n    }\n\n    /**\n     * Display database host index.\n     */\n    public function index(): View\n    {\n        return view('admin.databases.index', [\n            'locations' => $this->locationRepository->getAllWithNodes(),\n            'hosts' => $this->repository->getWithViewDetails(),\n        ]);\n    }\n\n    /**\n     * Display database host to user.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function view(int $host): View\n    {\n        return view('admin.databases.view', [\n            'locations' => $this->locationRepository->getAllWithNodes(),\n            'host' => $this->repository->find($host),\n            'databases' => $this->databaseRepository->getDatabasesForHost($host),\n        ]);\n    }\n\n    /**\n     * Handle request to create a new database host.\n     *\n     * @throws \\Throwable\n     */\n    public function create(DatabaseHostFormRequest $request): RedirectResponse\n    {\n        try {\n            $host = $this->creationService->handle($request->normalize());\n        } catch (\\Exception $exception) {\n            if ($exception instanceof \\PDOException || $exception->getPrevious() instanceof \\PDOException) {\n                $this->alert->danger(\n                    sprintf('在尝试连接到主机或执行查询的过程中出现错误：\"%s\"', $exception->getMessage())\n                )->flash();\n\n                return redirect()->route('admin.databases')->withInput($request->validated());\n            } else {\n                throw $exception;\n            }\n        }\n\n        $this->alert->success('已成功在系统上创建新的数据库主机。')->flash();\n\n        return redirect()->route('admin.databases.view', $host->id);\n    }\n\n    /**\n     * Handle updating database host.\n     *\n     * @throws \\Throwable\n     */\n    public function update(DatabaseHostFormRequest $request, DatabaseHost $host): RedirectResponse\n    {\n        $redirect = redirect()->route('admin.databases.view', $host->id);\n\n        try {\n            $this->updateService->handle($host->id, $request->normalize());\n            $this->alert->success('Database host was updated successfully.')->flash();\n        } catch (\\Exception $exception) {\n            // Catch any SQL related exceptions and display them back to the user, otherwise just\n            // throw the exception like normal and move on with it.\n            if ($exception instanceof \\PDOException || $exception->getPrevious() instanceof \\PDOException) {\n                $this->alert->danger(\n                    sprintf('在尝试连接到主机或执行查询的过程中出现错误：\"%s\"', $exception->getMessage())\n                )->flash();\n\n                return $redirect->withInput($request->normalize());\n            } else {\n                throw $exception;\n            }\n        }\n\n        return $redirect;\n    }\n\n    /**\n     * Handle request to delete a database host.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\HasActiveServersException\n     */\n    public function delete(int $host): RedirectResponse\n    {\n        $this->deletionService->handle($host);\n        $this->alert->success('已从系统中删除请求的数据库主机。')->flash();\n\n        return redirect()->route('admin.databases');\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/LocationController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin;\n\nuse Illuminate\\View\\View;\nuse Pterodactyl\\Models\\Location;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Illuminate\\View\\Factory as ViewFactory;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Http\\Requests\\Admin\\LocationFormRequest;\nuse Pterodactyl\\Services\\Locations\\LocationUpdateService;\nuse Pterodactyl\\Services\\Locations\\LocationCreationService;\nuse Pterodactyl\\Services\\Locations\\LocationDeletionService;\nuse Pterodactyl\\Contracts\\Repository\\LocationRepositoryInterface;\n\nclass LocationController extends Controller\n{\n    /**\n     * LocationController constructor.\n     */\n    public function __construct(\n        protected AlertsMessageBag $alert,\n        protected LocationCreationService $creationService,\n        protected LocationDeletionService $deletionService,\n        protected LocationRepositoryInterface $repository,\n        protected LocationUpdateService $updateService,\n        protected ViewFactory $view,\n    ) {\n    }\n\n    /**\n     * Return the location overview page.\n     */\n    public function index(): View\n    {\n        return view('admin.locations.index', [\n            'locations' => $this->repository->getAllWithDetails(),\n        ]);\n    }\n\n    /**\n     * Return the location view page.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function view(int $id): View\n    {\n        return view('admin.locations.view', [\n            'location' => $this->repository->getWithNodes($id),\n        ]);\n    }\n\n    /**\n     * Handle request to create new location.\n     *\n     * @throws \\Throwable\n     */\n    public function create(LocationFormRequest $request): RedirectResponse\n    {\n        $location = $this->creationService->handle($request->normalize());\n        $this->alert->success('成功创建地域。')->flash();\n\n        return redirect()->route('admin.locations.view', $location->id);\n    }\n\n    /**\n     * Handle request to update or delete location.\n     *\n     * @throws \\Throwable\n     */\n    public function update(LocationFormRequest $request, Location $location): RedirectResponse\n    {\n        if ($request->input('action') === 'delete') {\n            return $this->delete($location);\n        }\n\n        $this->updateService->handle($location->id, $request->normalize());\n        $this->alert->success('已成功更新地域。')->flash();\n\n        return redirect()->route('admin.locations.view', $location->id);\n    }\n\n    /**\n     * Delete a location from the system.\n     *\n     * @throws \\Exception\n     * @throws DisplayException\n     */\n    public function delete(Location $location): RedirectResponse\n    {\n        try {\n            $this->deletionService->handle($location->id);\n\n            return redirect()->route('admin.locations');\n        } catch (DisplayException $ex) {\n            $this->alert->danger($ex->getMessage())->flash();\n        }\n\n        return redirect()->route('admin.locations.view', $location->id);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/MountController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Nest;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Mount;\nuse Pterodactyl\\Models\\Location;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Illuminate\\View\\Factory as ViewFactory;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Http\\Requests\\Admin\\MountFormRequest;\nuse Pterodactyl\\Repositories\\Eloquent\\MountRepository;\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\LocationRepositoryInterface;\n\nclass MountController extends Controller\n{\n    /**\n     * MountController constructor.\n     */\n    public function __construct(\n        protected AlertsMessageBag $alert,\n        protected NestRepositoryInterface $nestRepository,\n        protected LocationRepositoryInterface $locationRepository,\n        protected MountRepository $repository,\n        protected ViewFactory $view,\n    ) {\n    }\n\n    /**\n     * Return the mount overview page.\n     */\n    public function index(): View\n    {\n        return view('admin.mounts.index', [\n            'mounts' => $this->repository->getAllWithDetails(),\n        ]);\n    }\n\n    /**\n     * Return the mount view page.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function view(string $id): View\n    {\n        $nests = Nest::query()->with('eggs')->get();\n        $locations = Location::query()->with('nodes')->get();\n\n        return view('admin.mounts.view', [\n            'mount' => $this->repository->getWithRelations($id),\n            'nests' => $nests,\n            'locations' => $locations,\n        ]);\n    }\n\n    /**\n     * Handle request to create new mount.\n     *\n     * @throws \\Throwable\n     */\n    public function create(MountFormRequest $request): RedirectResponse\n    {\n        $model = (new Mount())->fill($request->validated());\n        $model->forceFill(['uuid' => Uuid::uuid4()->toString()]);\n\n        $model->saveOrFail();\n        $mount = $model->fresh();\n\n        $this->alert->success('已成功创建挂载。')->flash();\n\n        return redirect()->route('admin.mounts.view', $mount->id);\n    }\n\n    /**\n     * Handle request to update or delete location.\n     *\n     * @throws \\Throwable\n     */\n    public function update(MountFormRequest $request, Mount $mount): RedirectResponse\n    {\n        if ($request->input('action') === 'delete') {\n            return $this->delete($mount);\n        }\n\n        $mount->forceFill($request->validated())->save();\n\n        $this->alert->success('已成功更新挂载。')->flash();\n\n        return redirect()->route('admin.mounts.view', $mount->id);\n    }\n\n    /**\n     * Delete a location from the system.\n     *\n     * @throws \\Exception\n     */\n    public function delete(Mount $mount): RedirectResponse\n    {\n        $mount->delete();\n\n        return redirect()->route('admin.mounts');\n    }\n\n    /**\n     * Adds eggs to the mount's many-to-many relation.\n     */\n    public function addEggs(Request $request, Mount $mount): RedirectResponse\n    {\n        $validatedData = $request->validate([\n            'eggs' => 'required|exists:eggs,id',\n        ]);\n\n        $eggs = $validatedData['eggs'] ?? [];\n        if (count($eggs) > 0) {\n            $mount->eggs()->attach($eggs);\n        }\n\n        $this->alert->success('已成功更新挂载。')->flash();\n\n        return redirect()->route('admin.mounts.view', $mount->id);\n    }\n\n    /**\n     * Adds nodes to the mount's many-to-many relation.\n     */\n    public function addNodes(Request $request, Mount $mount): RedirectResponse\n    {\n        $data = $request->validate(['nodes' => 'required|exists:nodes,id']);\n\n        $nodes = $data['nodes'] ?? [];\n        if (count($nodes) > 0) {\n            $mount->nodes()->attach($nodes);\n        }\n\n        $this->alert->success('已成功更新挂载。')->flash();\n\n        return redirect()->route('admin.mounts.view', $mount->id);\n    }\n\n    /**\n     * Deletes an egg from the mount's many-to-many relation.\n     */\n    public function deleteEgg(Mount $mount, int $egg_id): Response\n    {\n        $mount->eggs()->detach($egg_id);\n\n        return response('', 204);\n    }\n\n    /**\n     * Deletes a node from the mount's many-to-many relation.\n     */\n    public function deleteNode(Mount $mount, int $node_id): Response\n    {\n        $mount->nodes()->detach($node_id);\n\n        return response('', 204);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Nests/EggController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Nests;\n\nuse Illuminate\\View\\View;\nuse Pterodactyl\\Models\\Egg;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Illuminate\\View\\Factory as ViewFactory;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Eggs\\EggUpdateService;\nuse Pterodactyl\\Services\\Eggs\\EggCreationService;\nuse Pterodactyl\\Services\\Eggs\\EggDeletionService;\nuse Pterodactyl\\Http\\Requests\\Admin\\Egg\\EggFormRequest;\nuse Pterodactyl\\Contracts\\Repository\\EggRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\n\nclass EggController extends Controller\n{\n    /**\n     * EggController constructor.\n     */\n    public function __construct(\n        protected AlertsMessageBag $alert,\n        protected EggCreationService $creationService,\n        protected EggDeletionService $deletionService,\n        protected EggRepositoryInterface $repository,\n        protected EggUpdateService $updateService,\n        protected NestRepositoryInterface $nestRepository,\n        protected ViewFactory $view,\n    ) {\n    }\n\n    /**\n     * Handle a request to display the Egg creation page.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function create(): View\n    {\n        $nests = $this->nestRepository->getWithEggs();\n        \\JavaScript::put(['nests' => $nests->keyBy('id')]);\n\n        return view('admin.eggs.new', ['nests' => $nests]);\n    }\n\n    /**\n     * Handle request to store a new Egg.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Egg\\NoParentConfigurationFoundException\n     */\n    public function store(EggFormRequest $request): RedirectResponse\n    {\n        $data = $request->validated();\n        $data['docker_images'] = $this->normalizeDockerImages($data['docker_images'] ?? null);\n\n        $egg = $this->creationService->handle($data);\n        $this->alert->success(trans('admin/nests.eggs.notices.egg_created'))->flash();\n\n        return redirect()->route('admin.nests.egg.view', $egg->id);\n    }\n\n    /**\n     * Handle request to view a single Egg.\n     */\n    public function view(Egg $egg): View\n    {\n        return view('admin.eggs.view', [\n            'egg' => $egg,\n            'images' => array_map(\n                fn ($key, $value) => $key === $value ? $value : \"$key|$value\",\n                array_keys($egg->docker_images),\n                $egg->docker_images,\n            ),\n        ]);\n    }\n\n    /**\n     * Handle request to update an Egg.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Egg\\NoParentConfigurationFoundException\n     */\n    public function update(EggFormRequest $request, Egg $egg): RedirectResponse\n    {\n        $data = $request->validated();\n        $data['docker_images'] = $this->normalizeDockerImages($data['docker_images'] ?? null);\n\n        $this->updateService->handle($egg, $data);\n        $this->alert->success(trans('admin/nests.eggs.notices.updated'))->flash();\n\n        return redirect()->route('admin.nests.egg.view', $egg->id);\n    }\n\n    /**\n     * Handle request to destroy an egg.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Egg\\HasChildrenException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\HasActiveServersException\n     */\n    public function destroy(Egg $egg): RedirectResponse\n    {\n        $this->deletionService->handle($egg->id);\n        $this->alert->success(trans('admin/nests.eggs.notices.deleted'))->flash();\n\n        return redirect()->route('admin.nests.view', $egg->nest_id);\n    }\n\n    /**\n     * Normalizes a string of docker image data into the expected egg format.\n     */\n    protected function normalizeDockerImages(?string $input = null): array\n    {\n        $data = array_map(fn ($value) => trim($value), explode(\"\\n\", $input ?? ''));\n\n        $images = [];\n        // Iterate over the image data provided and convert it into a name => image\n        // pairing that is used to improve the display on the front-end.\n        foreach ($data as $value) {\n            $parts = explode('|', $value, 2);\n            $images[$parts[0]] = empty($parts[1]) ? $parts[0] : $parts[1];\n        }\n\n        return $images;\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Nests/EggScriptController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Nests;\n\nuse Illuminate\\View\\View;\nuse Pterodactyl\\Models\\Egg;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Illuminate\\View\\Factory as ViewFactory;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Eggs\\Scripts\\InstallScriptService;\nuse Pterodactyl\\Contracts\\Repository\\EggRepositoryInterface;\nuse Pterodactyl\\Http\\Requests\\Admin\\Egg\\EggScriptFormRequest;\n\nclass EggScriptController extends Controller\n{\n    /**\n     * EggScriptController constructor.\n     */\n    public function __construct(\n        protected AlertsMessageBag $alert,\n        protected EggRepositoryInterface $repository,\n        protected InstallScriptService $installScriptService,\n        protected ViewFactory $view,\n    ) {\n    }\n\n    /**\n     * Handle requests to render installation script for an Egg.\n     */\n    public function index(int $egg): View\n    {\n        $egg = $this->repository->getWithCopyAttributes($egg);\n        $copy = $this->repository->findWhere([\n            ['copy_script_from', '=', null],\n            ['nest_id', '=', $egg->nest_id],\n            ['id', '!=', $egg],\n        ]);\n\n        $rely = $this->repository->findWhere([\n            ['copy_script_from', '=', $egg->id],\n        ]);\n\n        return view('admin.eggs.scripts', [\n            'copyFromOptions' => $copy,\n            'relyOnScript' => $rely,\n            'egg' => $egg,\n        ]);\n    }\n\n    /**\n     * Handle a request to update the installation script for an Egg.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Egg\\InvalidCopyFromException\n     */\n    public function update(EggScriptFormRequest $request, Egg $egg): RedirectResponse\n    {\n        $this->installScriptService->handle($egg, $request->normalize());\n        $this->alert->success(trans('admin/nests.eggs.notices.script_updated'))->flash();\n\n        return redirect()->route('admin.nests.egg.scripts', $egg);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Nests/EggShareController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Nests;\n\nuse Pterodactyl\\Models\\Egg;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Symfony\\Component\\HttpFoundation\\Response;\nuse Pterodactyl\\Services\\Eggs\\Sharing\\EggExporterService;\nuse Pterodactyl\\Services\\Eggs\\Sharing\\EggImporterService;\nuse Pterodactyl\\Http\\Requests\\Admin\\Egg\\EggImportFormRequest;\nuse Pterodactyl\\Services\\Eggs\\Sharing\\EggUpdateImporterService;\n\nclass EggShareController extends Controller\n{\n    /**\n     * EggShareController constructor.\n     */\n    public function __construct(\n        protected AlertsMessageBag $alert,\n        protected EggExporterService $exporterService,\n        protected EggImporterService $importerService,\n        protected EggUpdateImporterService $updateImporterService,\n    ) {\n    }\n\n    /**\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function export(Egg $egg): Response\n    {\n        $filename = trim(preg_replace('/\\W/', '-', kebab_case($egg->name)), '-');\n\n        return response($this->exporterService->handle($egg->id), 200, [\n            'Content-Transfer-Encoding' => 'binary',\n            'Content-Description' => 'File Transfer',\n            'Content-Disposition' => 'attachment; filename=egg-' . $filename . '.json',\n            'Content-Type' => 'application/json',\n        ]);\n    }\n\n    /**\n     * Import a new service option using an XML file.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Egg\\BadJsonFormatException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\InvalidFileUploadException\n     */\n    public function import(EggImportFormRequest $request): RedirectResponse\n    {\n        $egg = $this->importerService->handle($request->file('import_file'), $request->input('import_to_nest'));\n        $this->alert->success(trans('admin/nests.eggs.notices.imported'))->flash();\n\n        return redirect()->route('admin.nests.egg.view', ['egg' => $egg->id]);\n    }\n\n    /**\n     * Update an existing Egg using a new imported file.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Egg\\BadJsonFormatException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\InvalidFileUploadException\n     */\n    public function update(EggImportFormRequest $request, Egg $egg): RedirectResponse\n    {\n        $this->updateImporterService->handle($egg, $request->file('import_file'));\n        $this->alert->success(trans('admin/nests.eggs.notices.updated_via_import'))->flash();\n\n        return redirect()->route('admin.nests.egg.view', ['egg' => $egg]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Nests/EggVariableController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Nests;\n\nuse Illuminate\\View\\View;\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\EggVariable;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Illuminate\\View\\Factory as ViewFactory;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Contracts\\Repository\\EggRepositoryInterface;\nuse Pterodactyl\\Services\\Eggs\\Variables\\VariableUpdateService;\nuse Pterodactyl\\Http\\Requests\\Admin\\Egg\\EggVariableFormRequest;\nuse Pterodactyl\\Services\\Eggs\\Variables\\VariableCreationService;\nuse Pterodactyl\\Contracts\\Repository\\EggVariableRepositoryInterface;\n\nclass EggVariableController extends Controller\n{\n    /**\n     * EggVariableController constructor.\n     */\n    public function __construct(\n        protected AlertsMessageBag $alert,\n        protected VariableCreationService $creationService,\n        protected VariableUpdateService $updateService,\n        protected EggRepositoryInterface $repository,\n        protected EggVariableRepositoryInterface $variableRepository,\n        protected ViewFactory $view,\n    ) {\n    }\n\n    /**\n     * Handle request to view the variables attached to an Egg.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function view(int $egg): View\n    {\n        $egg = $this->repository->getWithVariables($egg);\n\n        return view('admin.eggs.variables', ['egg' => $egg]);\n    }\n\n    /**\n     * Handle a request to create a new Egg variable.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Egg\\Variable\\BadValidationRuleException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Egg\\Variable\\ReservedVariableNameException\n     */\n    public function store(EggVariableFormRequest $request, Egg $egg): RedirectResponse\n    {\n        $this->creationService->handle($egg->id, $request->normalize());\n        $this->alert->success(trans('admin/nests.variables.notices.variable_created'))->flash();\n\n        return redirect()->route('admin.nests.egg.variables', $egg->id);\n    }\n\n    /**\n     * Handle a request to update an existing Egg variable.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Egg\\Variable\\ReservedVariableNameException\n     */\n    public function update(EggVariableFormRequest $request, Egg $egg, EggVariable $variable): RedirectResponse\n    {\n        $this->updateService->handle($variable, $request->normalize());\n        $this->alert->success(trans('admin/nests.variables.notices.variable_updated', [\n            'variable' => htmlspecialchars($variable->name),\n        ]))->flash();\n\n        return redirect()->route('admin.nests.egg.variables', $egg->id);\n    }\n\n    /**\n     * Handle a request to delete an existing Egg variable from the Panel.\n     */\n    public function destroy(int $egg, EggVariable $variable): RedirectResponse\n    {\n        $this->variableRepository->delete($variable->id);\n        $this->alert->success(trans('admin/nests.variables.notices.variable_deleted', [\n            'variable' => htmlspecialchars($variable->name),\n        ]))->flash();\n\n        return redirect()->route('admin.nests.egg.variables', $egg);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Nests/NestController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Nests;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Illuminate\\View\\Factory as ViewFactory;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Nests\\NestUpdateService;\nuse Pterodactyl\\Services\\Nests\\NestCreationService;\nuse Pterodactyl\\Services\\Nests\\NestDeletionService;\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\nuse Pterodactyl\\Http\\Requests\\Admin\\Nest\\StoreNestFormRequest;\n\nclass NestController extends Controller\n{\n    /**\n     * NestController constructor.\n     */\n    public function __construct(\n        protected AlertsMessageBag $alert,\n        protected NestCreationService $nestCreationService,\n        protected NestDeletionService $nestDeletionService,\n        protected NestRepositoryInterface $repository,\n        protected NestUpdateService $nestUpdateService,\n        protected ViewFactory $view,\n    ) {\n    }\n\n    /**\n     * Render nest listing page.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function index(): View\n    {\n        return view('admin.nests.index', [\n            'nests' => $this->repository->getWithCounts(),\n        ]);\n    }\n\n    /**\n     * Render nest creation page.\n     */\n    public function create(): View\n    {\n        return view('admin.nests.new');\n    }\n\n    /**\n     * Handle the storage of a new nest.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function store(StoreNestFormRequest $request): RedirectResponse\n    {\n        $nest = $this->nestCreationService->handle($request->normalize());\n        $this->alert->success(trans('admin/nests.notices.created', ['name' => htmlspecialchars($nest->name)]))->flash();\n\n        return redirect()->route('admin.nests.view', $nest->id);\n    }\n\n    /**\n     * Return details about a nest including all the eggs and servers per egg.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function view(int $nest): View\n    {\n        return view('admin.nests.view', [\n            'nest' => $this->repository->getWithEggServers($nest),\n        ]);\n    }\n\n    /**\n     * Handle request to update a nest.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(StoreNestFormRequest $request, int $nest): RedirectResponse\n    {\n        $this->nestUpdateService->handle($nest, $request->normalize());\n        $this->alert->success(trans('admin/nests.notices.updated'))->flash();\n\n        return redirect()->route('admin.nests.view', $nest);\n    }\n\n    /**\n     * Handle request to delete a nest.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\HasActiveServersException\n     */\n    public function destroy(int $nest): RedirectResponse\n    {\n        $this->nestDeletionService->handle($nest);\n        $this->alert->success(trans('admin/nests.notices.deleted'))->flash();\n\n        return redirect()->route('admin.nests');\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/NodeAutoDeployController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\ApiKey;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Services\\Api\\KeyCreationService;\n\nclass NodeAutoDeployController extends Controller\n{\n    /**\n     * NodeAutoDeployController constructor.\n     */\n    public function __construct(\n        private Encrypter $encrypter,\n        private KeyCreationService $keyCreationService,\n    ) {\n    }\n\n    /**\n     * Generates a new API key for the logged-in user with only permission to read\n     * nodes, and returns that as the deployment key for a node.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function __invoke(Request $request, Node $node): JsonResponse\n    {\n        $key = ApiKey::query()\n            ->where('user_id', $request->user()->id)\n            ->where('key_type', ApiKey::TYPE_APPLICATION)\n            ->where('r_nodes', 1)\n            ->first();\n\n        // We couldn't find a key that exists for this user with only permission for\n        // reading nodes. Go ahead and create it now.\n        if (!$key) {\n            $key = $this->keyCreationService->setKeyType(ApiKey::TYPE_APPLICATION)->handle([\n                'user_id' => $request->user()->id,\n                'memo' => '自动生成的节点部署密钥。',\n                'allowed_ips' => [],\n            ], ['r_nodes' => 1]);\n        }\n\n        return new JsonResponse([\n            'node' => $node->id,\n            'token' => $key->identifier . $this->encrypter->decrypt($key->token),\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Nodes/NodeController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Nodes;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Node;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Pterodactyl\\Http\\Controllers\\Controller;\n\nclass NodeController extends Controller\n{\n    /**\n     * Returns a listing of nodes on the system.\n     */\n    public function index(Request $request): View\n    {\n        $nodes = QueryBuilder::for(\n            Node::query()->with('location')->withCount('servers')\n        )\n            ->allowedFilters(['uuid', 'name'])\n            ->allowedSorts(['id'])\n            ->paginate(25);\n\n        return view('admin.nodes.index', ['nodes' => $nodes]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Nodes/NodeViewController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Nodes;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Repositories\\Eloquent\\NodeRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerRepository;\nuse Pterodactyl\\Traits\\Controllers\\JavascriptInjection;\nuse Pterodactyl\\Services\\Helpers\\SoftwareVersionService;\nuse Pterodactyl\\Repositories\\Eloquent\\LocationRepository;\n\nclass NodeViewController extends Controller\n{\n    use JavascriptInjection;\n\n    /**\n     * NodeViewController constructor.\n     */\n    public function __construct(\n        private LocationRepository $locationRepository,\n        private NodeRepository $repository,\n        private ServerRepository $serverRepository,\n        private SoftwareVersionService $versionService,\n    ) {\n    }\n\n    /**\n     * Returns index view for a specific node on the system.\n     */\n    public function index(Request $request, Node $node): View\n    {\n        $node = $this->repository->loadLocationAndServerCount($node);\n\n        return view('admin.nodes.view.index', [\n            'node' => $node,\n            'stats' => $this->repository->getUsageStats($node),\n            'version' => $this->versionService,\n        ]);\n    }\n\n    /**\n     * Returns the settings page for a specific node.\n     */\n    public function settings(Request $request, Node $node): View\n    {\n        return view('admin.nodes.view.settings', [\n            'node' => $node,\n            'locations' => $this->locationRepository->all(),\n        ]);\n    }\n\n    /**\n     * Return the node configuration page for a specific node.\n     */\n    public function configuration(Request $request, Node $node): View\n    {\n        return view('admin.nodes.view.configuration', compact('node'));\n    }\n\n    /**\n     * Return the node allocation management page.\n     */\n    public function allocations(Request $request, Node $node): View\n    {\n        $node = $this->repository->loadNodeAllocations($node);\n\n        $this->plainInject(['node' => Collection::make([$node])->only(['id'])]);\n\n        return view('admin.nodes.view.allocation', [\n            'node' => $node,\n            'allocations' => Allocation::query()->where('node_id', $node->id)\n                ->groupBy('ip')\n                ->orderByRaw('INET_ATON(ip) ASC')\n                ->get(['ip']),\n        ]);\n    }\n\n    /**\n     * Return a listing of servers that exist for this specific node.\n     */\n    public function servers(Request $request, Node $node): View\n    {\n        $this->plainInject([\n            'node' => Collection::make([$node->makeVisible(['daemon_token_id', 'daemon_token'])])\n                ->only(['scheme', 'fqdn', 'daemonListen', 'daemon_token_id', 'daemon_token']),\n        ]);\n\n        return view('admin.nodes.view.servers', [\n            'node' => $node,\n            'servers' => $this->serverRepository->loadAllServersForNode($node->id, 25),\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Nodes/SystemInformationController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Nodes;\n\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Repositories\\Wings\\DaemonConfigurationRepository;\n\nclass SystemInformationController extends Controller\n{\n    /**\n     * SystemInformationController constructor.\n     */\n    public function __construct(private DaemonConfigurationRepository $repository)\n    {\n    }\n\n    /**\n     * Returns system information from the Daemon.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException\n     */\n    public function __invoke(Request $request, Node $node): JsonResponse\n    {\n        $data = $this->repository->setNode($node)->getSystemInformation();\n\n        return new JsonResponse([\n            'version' => $data['version'] ?? '',\n            'system' => [\n                'type' => Str::title($data['os'] ?? 'Unknown'),\n                'arch' => $data['architecture'] ?? '--',\n                'release' => $data['kernel_version'] ?? '--',\n                'cpus' => $data['cpu_count'] ?? 0,\n            ],\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/NodesController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Allocation;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Illuminate\\View\\Factory as ViewFactory;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Nodes\\NodeUpdateService;\nuse Illuminate\\Cache\\Repository as CacheRepository;\nuse Pterodactyl\\Services\\Nodes\\NodeCreationService;\nuse Pterodactyl\\Services\\Nodes\\NodeDeletionService;\nuse Pterodactyl\\Services\\Allocations\\AssignmentService;\nuse Pterodactyl\\Services\\Helpers\\SoftwareVersionService;\nuse Pterodactyl\\Http\\Requests\\Admin\\Node\\NodeFormRequest;\nuse Pterodactyl\\Contracts\\Repository\\NodeRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\ServerRepositoryInterface;\nuse Pterodactyl\\Http\\Requests\\Admin\\Node\\AllocationFormRequest;\nuse Pterodactyl\\Services\\Allocations\\AllocationDeletionService;\nuse Pterodactyl\\Contracts\\Repository\\LocationRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\AllocationRepositoryInterface;\nuse Pterodactyl\\Http\\Requests\\Admin\\Node\\AllocationAliasFormRequest;\n\nclass NodesController extends Controller\n{\n    /**\n     * NodesController constructor.\n     */\n    public function __construct(\n        protected AlertsMessageBag $alert,\n        protected AllocationDeletionService $allocationDeletionService,\n        protected AllocationRepositoryInterface $allocationRepository,\n        protected AssignmentService $assignmentService,\n        protected CacheRepository $cache,\n        protected NodeCreationService $creationService,\n        protected NodeDeletionService $deletionService,\n        protected LocationRepositoryInterface $locationRepository,\n        protected NodeRepositoryInterface $repository,\n        protected ServerRepositoryInterface $serverRepository,\n        protected NodeUpdateService $updateService,\n        protected SoftwareVersionService $versionService,\n        protected ViewFactory $view,\n    ) {\n    }\n\n    /**\n     * Displays create new node page.\n     */\n    public function create(): View|RedirectResponse\n    {\n        $locations = $this->locationRepository->all();\n        if (count($locations) < 1) {\n            $this->alert->warning(trans('admin/node.notices.location_required'))->flash();\n\n            return redirect()->route('admin.locations');\n        }\n\n        return view('admin.nodes.new', ['locations' => $locations]);\n    }\n\n    /**\n     * Post controller to create a new node on the system.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function store(NodeFormRequest $request): RedirectResponse\n    {\n        $node = $this->creationService->handle($request->normalize());\n        $this->alert->info(trans('admin/node.notices.node_created'))->flash();\n\n        return redirect()->route('admin.nodes.view.allocation', $node->id);\n    }\n\n    /**\n     * Updates settings for a node.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function updateSettings(NodeFormRequest $request, Node $node): RedirectResponse\n    {\n        $this->updateService->handle($node, $request->normalize(), $request->input('reset_secret') === 'on');\n        $this->alert->success(trans('admin/node.notices.node_updated'))->flash();\n\n        return redirect()->route('admin.nodes.view.settings', $node->id)->withInput();\n    }\n\n    /**\n     * Removes a single allocation from a node.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\ServerUsingAllocationException\n     */\n    public function allocationRemoveSingle(int $node, Allocation $allocation): Response\n    {\n        $this->allocationDeletionService->handle($allocation);\n\n        return response('', 204);\n    }\n\n    /**\n     * Removes multiple individual allocations from a node.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\ServerUsingAllocationException\n     */\n    public function allocationRemoveMultiple(Request $request, int $node): Response\n    {\n        $allocations = $request->input('allocations');\n        foreach ($allocations as $rawAllocation) {\n            $allocation = new Allocation();\n            $allocation->id = $rawAllocation['id'];\n            $this->allocationRemoveSingle($node, $allocation);\n        }\n\n        return response('', 204);\n    }\n\n    /**\n     * Remove all allocations for a specific IP at once on a node.\n     */\n    public function allocationRemoveBlock(Request $request, int $node): RedirectResponse\n    {\n        $this->allocationRepository->deleteWhere([\n            ['node_id', '=', $node],\n            ['server_id', '=', null],\n            ['ip', '=', $request->input('ip')],\n        ]);\n\n        $this->alert->success(trans('admin/node.notices.unallocated_deleted', ['ip' => htmlspecialchars($request->input('ip'))]))\n            ->flash();\n\n        return redirect()->route('admin.nodes.view.allocation', $node);\n    }\n\n    /**\n     * Sets an alias for a specific allocation on a node.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function allocationSetAlias(AllocationAliasFormRequest $request): \\Symfony\\Component\\HttpFoundation\\Response\n    {\n        $this->allocationRepository->update($request->input('allocation_id'), [\n            'ip_alias' => (empty($request->input('alias'))) ? null : $request->input('alias'),\n        ]);\n\n        return response('', 204);\n    }\n\n    /**\n     * Creates new allocations on a node.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\CidrOutOfRangeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\InvalidPortMappingException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\PortOutOfRangeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\TooManyPortsInRangeException\n     */\n    public function createAllocation(AllocationFormRequest $request, Node $node): RedirectResponse\n    {\n        $this->assignmentService->handle($node, $request->normalize());\n        $this->alert->success(trans('admin/node.notices.allocations_added'))->flash();\n\n        return redirect()->route('admin.nodes.view.allocation', $node->id);\n    }\n\n    /**\n     * Deletes a node from the system.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     */\n    public function delete(int|Node $node): RedirectResponse\n    {\n        $this->deletionService->handle($node);\n        $this->alert->success(trans('admin/node.notices.node_deleted'))->flash();\n\n        return redirect()->route('admin.nodes');\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Servers/CreateServerController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Servers;\n\nuse Illuminate\\View\\View;\nuse Pterodactyl\\Models\\Nest;\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\Location;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Repositories\\Eloquent\\NestRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\NodeRepository;\nuse Pterodactyl\\Http\\Requests\\Admin\\ServerFormRequest;\nuse Pterodactyl\\Services\\Servers\\ServerCreationService;\n\nclass CreateServerController extends Controller\n{\n    /**\n     * CreateServerController constructor.\n     */\n    public function __construct(\n        private AlertsMessageBag $alert,\n        private NestRepository $nestRepository,\n        private NodeRepository $nodeRepository,\n        private ServerCreationService $creationService,\n    ) {\n    }\n\n    /**\n     * Displays the create server page.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function index(): View|RedirectResponse\n    {\n        $nodes = Node::all();\n        if (count($nodes) < 1) {\n            $this->alert->warning(trans('admin/server.alerts.node_required'))->flash();\n\n            return redirect()->route('admin.nodes');\n        }\n\n        $nests = $this->nestRepository->getWithEggs();\n\n        \\JavaScript::put([\n            'nodeData' => $this->nodeRepository->getNodesForServerCreation(),\n            'nests' => $nests->map(function (Nest $item) {\n                return array_merge($item->toArray(), [\n                    'eggs' => $item->eggs->keyBy('id')->toArray(),\n                ]);\n            })->keyBy('id'),\n        ]);\n\n        return view('admin.servers.new', [\n            'locations' => Location::all(),\n            'nests' => $nests,\n        ]);\n    }\n\n    /**\n     * Create a new server on the remote system.\n     *\n     * @throws \\Illuminate\\Validation\\ValidationException\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableAllocationException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableNodeException\n     * @throws \\Throwable\n     */\n    public function store(ServerFormRequest $request): RedirectResponse\n    {\n        $data = $request->except(['_token']);\n        if (!empty($data['custom_image'])) {\n            $data['image'] = $data['custom_image'];\n            unset($data['custom_image']);\n        }\n\n        $server = $this->creationService->handle($data);\n\n        $this->alert->success(trans('admin/server.alerts.server_created'))->flash();\n\n        return new RedirectResponse('/admin/servers/view/' . $server->id);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Servers/ServerController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Servers;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Server;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Spatie\\QueryBuilder\\AllowedFilter;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Models\\Filters\\AdminServerFilter;\n\nclass ServerController extends Controller\n{\n    /**\n     * Returns all the servers that exist on the system using a paginated result set. If\n     * a query is passed along in the request it is also passed to the repository function.\n     */\n    public function index(Request $request): View\n    {\n        $servers = QueryBuilder::for(Server::query()->with('node', 'user', 'allocation'))\n            ->allowedFilters([\n                AllowedFilter::exact('owner_id'),\n                AllowedFilter::custom('*', new AdminServerFilter()),\n            ])\n            ->paginate(config()->get('pterodactyl.paginate.admin.servers'));\n\n        return view('admin.servers.index', ['servers' => $servers]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Servers/ServerTransferController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Servers;\n\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Pterodactyl\\Models\\ServerTransfer;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Nodes\\NodeJWTService;\nuse Pterodactyl\\Repositories\\Eloquent\\NodeRepository;\nuse Pterodactyl\\Repositories\\Wings\\DaemonTransferRepository;\nuse Pterodactyl\\Contracts\\Repository\\AllocationRepositoryInterface;\n\nclass ServerTransferController extends Controller\n{\n    /**\n     * ServerTransferController constructor.\n     */\n    public function __construct(\n        private AlertsMessageBag $alert,\n        private AllocationRepositoryInterface $allocationRepository,\n        private ConnectionInterface $connection,\n        private DaemonTransferRepository $daemonTransferRepository,\n        private NodeJWTService $nodeJWTService,\n        private NodeRepository $nodeRepository,\n    ) {\n    }\n\n    /**\n     * Starts a transfer of a server to a new node.\n     *\n     * @throws \\Throwable\n     */\n    public function transfer(Request $request, Server $server): RedirectResponse\n    {\n        $validatedData = $request->validate([\n            'node_id' => 'required|exists:nodes,id',\n            'allocation_id' => 'required|bail|unique:servers|exists:allocations,id',\n            'allocation_additional' => 'nullable',\n        ]);\n\n        $node_id = $validatedData['node_id'];\n        $allocation_id = intval($validatedData['allocation_id']);\n        $additional_allocations = array_map('intval', $validatedData['allocation_additional'] ?? []);\n\n        // Check if the node is viable for the transfer.\n        $node = $this->nodeRepository->getNodeWithResourceUsage($node_id);\n        if (!$node->isViable($server->memory, $server->disk)) {\n            $this->alert->danger(trans('admin/server.alerts.transfer_not_viable'))->flash();\n\n            return redirect()->route('admin.servers.view.manage', $server->id);\n        }\n\n        $server->validateTransferState();\n\n        $this->connection->transaction(function () use ($server, $node_id, $allocation_id, $additional_allocations) {\n            // Create a new ServerTransfer entry.\n            $transfer = new ServerTransfer();\n\n            $transfer->server_id = $server->id;\n            $transfer->old_node = $server->node_id;\n            $transfer->new_node = $node_id;\n            $transfer->old_allocation = $server->allocation_id;\n            $transfer->new_allocation = $allocation_id;\n            $transfer->old_additional_allocations = $server->allocations->where('id', '!=', $server->allocation_id)->pluck('id')->values()->toArray();\n            $transfer->new_additional_allocations = $additional_allocations;\n\n            $transfer->save();\n\n            // Add the allocations to the server, so they cannot be automatically assigned while the transfer is in progress.\n            $this->assignAllocationsToServer($server, $node_id, $allocation_id, $additional_allocations);\n\n            // Generate a token for the destination node that the source node can use to authenticate with.\n            $token = $this->nodeJWTService\n                ->setExpiresAt(CarbonImmutable::now()->addMinutes(15))\n                ->setSubject($server->uuid)\n                ->handle($transfer->newNode, $server->uuid, 'sha256');\n\n            // Notify the source node of the pending outgoing transfer.\n            $this->daemonTransferRepository->setServer($server)->notify($transfer->newNode, $token);\n\n            return $transfer;\n        });\n\n        $this->alert->success(trans('admin/server.alerts.transfer_started'))->flash();\n\n        return redirect()->route('admin.servers.view.manage', $server->id);\n    }\n\n    /**\n     * Assigns the specified allocations to the specified server.\n     */\n    private function assignAllocationsToServer(Server $server, int $node_id, int $allocation_id, array $additional_allocations)\n    {\n        $allocations = $additional_allocations;\n        $allocations[] = $allocation_id;\n\n        $unassigned = $this->allocationRepository->getUnassignedAllocationIds($node_id);\n\n        $updateIds = [];\n        foreach ($allocations as $allocation) {\n            if (!in_array($allocation, $unassigned)) {\n                continue;\n            }\n\n            $updateIds[] = $allocation;\n        }\n\n        if (!empty($updateIds)) {\n            $this->allocationRepository->updateWhereIn('id', $updateIds, ['server_id' => $server->id]);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Servers/ServerViewController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Servers;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Nest;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Servers\\EnvironmentService;\nuse Pterodactyl\\Repositories\\Eloquent\\NestRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\NodeRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\MountRepository;\nuse Pterodactyl\\Traits\\Controllers\\JavascriptInjection;\nuse Pterodactyl\\Repositories\\Eloquent\\LocationRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\DatabaseHostRepository;\n\nclass ServerViewController extends Controller\n{\n    use JavascriptInjection;\n\n    /**\n     * ServerViewController constructor.\n     */\n    public function __construct(\n        private DatabaseHostRepository $databaseHostRepository,\n        private LocationRepository $locationRepository,\n        private MountRepository $mountRepository,\n        private NestRepository $nestRepository,\n        private NodeRepository $nodeRepository,\n        private EnvironmentService $environmentService,\n    ) {\n    }\n\n    /**\n     * Returns the index view for a server.\n     */\n    public function index(Request $request, Server $server): View\n    {\n        return view('admin.servers.view.index', compact('server'));\n    }\n\n    /**\n     * Returns the server details page.\n     */\n    public function details(Request $request, Server $server): View\n    {\n        return view('admin.servers.view.details', compact('server'));\n    }\n\n    /**\n     * Returns a view of server build settings.\n     */\n    public function build(Request $request, Server $server): View\n    {\n        $allocations = $server->node->allocations->toBase();\n\n        return view('admin.servers.view.build', [\n            'server' => $server,\n            'assigned' => $allocations->where('server_id', $server->id)->sortBy('port')->sortBy('ip'),\n            'unassigned' => $allocations->where('server_id', null)->sortBy('port')->sortBy('ip'),\n        ]);\n    }\n\n    /**\n     * Returns the server startup management page.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function startup(Request $request, Server $server): View\n    {\n        $nests = $this->nestRepository->getWithEggs();\n        $variables = $this->environmentService->handle($server);\n\n        $this->plainInject([\n            'server' => $server,\n            'server_variables' => $variables,\n            'nests' => $nests->map(function (Nest $item) {\n                return array_merge($item->toArray(), [\n                    'eggs' => $item->eggs->keyBy('id')->toArray(),\n                ]);\n            })->keyBy('id'),\n        ]);\n\n        return view('admin.servers.view.startup', compact('server', 'nests'));\n    }\n\n    /**\n     * Returns all the databases that exist for the server.\n     */\n    public function database(Request $request, Server $server): View\n    {\n        return view('admin.servers.view.database', [\n            'hosts' => $this->databaseHostRepository->all(),\n            'server' => $server,\n        ]);\n    }\n\n    /**\n     * Returns all the mounts that exist for the server.\n     */\n    public function mounts(Request $request, Server $server): View\n    {\n        $server->load('mounts');\n\n        return view('admin.servers.view.mounts', [\n            'mounts' => $this->mountRepository->getMountListForServer($server),\n            'server' => $server,\n        ]);\n    }\n\n    /**\n     * Returns the base server management page, or an exception if the server\n     * is in a state that cannot be recovered from.\n     *\n     * @throws DisplayException\n     */\n    public function manage(Request $request, Server $server): View\n    {\n        if ($server->status === Server::STATUS_INSTALL_FAILED) {\n            throw new DisplayException('此服务器处于安装失败状态并且无法恢复。请删除服务器并重新创建。');\n        }\n\n        // Check if the panel doesn't have at least 2 nodes configured.\n        $nodes = $this->nodeRepository->all();\n        $canTransfer = false;\n        if (count($nodes) >= 2) {\n            $canTransfer = true;\n        }\n\n        \\JavaScript::put([\n            'nodeData' => $this->nodeRepository->getNodesForServerCreation(),\n        ]);\n\n        return view('admin.servers.view.manage', [\n            'server' => $server,\n            'locations' => $this->locationRepository->all(),\n            'canTransfer' => $canTransfer,\n        ]);\n    }\n\n    /**\n     * Returns the server deletion page.\n     */\n    public function delete(Request $request, Server $server): View\n    {\n        return view('admin.servers.view.delete', compact('server'));\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/ServersController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Mount;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\MountServer;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Illuminate\\Validation\\ValidationException;\nuse Pterodactyl\\Services\\Servers\\SuspensionService;\nuse Pterodactyl\\Repositories\\Eloquent\\MountRepository;\nuse Pterodactyl\\Services\\Servers\\ServerDeletionService;\nuse Pterodactyl\\Services\\Servers\\ReinstallServerService;\nuse Pterodactyl\\Exceptions\\Model\\DataValidationException;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Services\\Servers\\BuildModificationService;\nuse Pterodactyl\\Services\\Databases\\DatabasePasswordService;\nuse Pterodactyl\\Services\\Servers\\DetailsModificationService;\nuse Pterodactyl\\Services\\Servers\\StartupModificationService;\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\nuse Pterodactyl\\Repositories\\Eloquent\\DatabaseHostRepository;\nuse Pterodactyl\\Services\\Databases\\DatabaseManagementService;\nuse Illuminate\\Contracts\\Config\\Repository as ConfigRepository;\nuse Pterodactyl\\Contracts\\Repository\\ServerRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\AllocationRepositoryInterface;\nuse Pterodactyl\\Services\\Servers\\ServerConfigurationStructureService;\nuse Pterodactyl\\Http\\Requests\\Admin\\Servers\\Databases\\StoreServerDatabaseRequest;\n\nclass ServersController extends Controller\n{\n    /**\n     * ServersController constructor.\n     */\n    public function __construct(\n        protected AlertsMessageBag $alert,\n        protected AllocationRepositoryInterface $allocationRepository,\n        protected BuildModificationService $buildModificationService,\n        protected ConfigRepository $config,\n        protected DaemonServerRepository $daemonServerRepository,\n        protected DatabaseManagementService $databaseManagementService,\n        protected DatabasePasswordService $databasePasswordService,\n        protected DatabaseRepositoryInterface $databaseRepository,\n        protected DatabaseHostRepository $databaseHostRepository,\n        protected ServerDeletionService $deletionService,\n        protected DetailsModificationService $detailsModificationService,\n        protected ReinstallServerService $reinstallService,\n        protected ServerRepositoryInterface $repository,\n        protected MountRepository $mountRepository,\n        protected NestRepositoryInterface $nestRepository,\n        protected ServerConfigurationStructureService $serverConfigurationStructureService,\n        protected StartupModificationService $startupModificationService,\n        protected SuspensionService $suspensionService,\n    ) {\n    }\n\n    /**\n     * Update the details for a server.\n     *\n     * @throws DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function setDetails(Request $request, Server $server): RedirectResponse\n    {\n        $this->detailsModificationService->handle($server, $request->only([\n            'owner_id', 'external_id', 'name', 'description',\n        ]));\n\n        $this->alert->success(trans('admin/server.alerts.details_updated'))->flash();\n\n        return redirect()->route('admin.servers.view.details', $server->id);\n    }\n\n    /**\n     * Toggles the installation status for a server.\n     *\n     * @throws DisplayException\n     * @throws DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function toggleInstall(Server $server): RedirectResponse\n    {\n        if ($server->status === Server::STATUS_INSTALL_FAILED) {\n            throw new DisplayException(trans('admin/server.exceptions.marked_as_failed'));\n        }\n\n        $this->repository->update($server->id, [\n            'status' => $server->isInstalled() ? Server::STATUS_INSTALLING : null,\n        ], true, true);\n\n        $this->alert->success(trans('admin/server.alerts.install_toggled'))->flash();\n\n        return redirect()->route('admin.servers.view.manage', $server->id);\n    }\n\n    /**\n     * Reinstalls the server with the currently assigned service.\n     *\n     * @throws DisplayException\n     * @throws DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function reinstallServer(Server $server): RedirectResponse\n    {\n        $this->reinstallService->handle($server);\n        $this->alert->success(trans('admin/server.alerts.server_reinstalled'))->flash();\n\n        return redirect()->route('admin.servers.view.manage', $server->id);\n    }\n\n    /**\n     * Manage the suspension status for a server.\n     *\n     * @throws DisplayException\n     * @throws DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function manageSuspension(Request $request, Server $server): RedirectResponse\n    {\n        $this->suspensionService->toggle($server, $request->input('action'));\n        $this->alert->success(trans('admin/server.alerts.suspension_toggled', [\n            'status' => $request->input('action') . 'ed',\n        ]))->flash();\n\n        return redirect()->route('admin.servers.view.manage', $server->id);\n    }\n\n    /**\n     * Update the build configuration for a server.\n     *\n     * @throws DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws ValidationException\n     */\n    public function updateBuild(Request $request, Server $server): RedirectResponse\n    {\n        try {\n            $this->buildModificationService->handle($server, $request->only([\n                'allocation_id', 'add_allocations', 'remove_allocations',\n                'memory', 'swap', 'io', 'cpu', 'threads', 'disk',\n                'database_limit', 'allocation_limit', 'backup_limit', 'oom_disabled',\n            ]));\n        } catch (DataValidationException $exception) {\n            throw new ValidationException($exception->getValidator());\n        }\n\n        $this->alert->success(trans('admin/server.alerts.build_updated'))->flash();\n\n        return redirect()->route('admin.servers.view.build', $server->id);\n    }\n\n    /**\n     * Start the server deletion process.\n     *\n     * @throws DisplayException\n     * @throws \\Throwable\n     */\n    public function delete(Request $request, Server $server): RedirectResponse\n    {\n        $this->deletionService->withForce($request->filled('force_delete'))->handle($server);\n        $this->alert->success(trans('admin/server.alerts.server_deleted'))->flash();\n\n        return redirect()->route('admin.servers');\n    }\n\n    /**\n     * Update the startup command as well as variables.\n     *\n     * @throws ValidationException\n     */\n    public function saveStartup(Request $request, Server $server): RedirectResponse\n    {\n        $data = $request->except('_token');\n        if (!empty($data['custom_docker_image'])) {\n            $data['docker_image'] = $data['custom_docker_image'];\n            unset($data['custom_docker_image']);\n        }\n\n        try {\n            $this->startupModificationService\n                ->setUserLevel(User::USER_LEVEL_ADMIN)\n                ->handle($server, $data);\n        } catch (DataValidationException $exception) {\n            throw new ValidationException($exception->getValidator());\n        }\n\n        $this->alert->success(trans('admin/server.alerts.startup_changed'))->flash();\n\n        return redirect()->route('admin.servers.view.startup', $server->id);\n    }\n\n    /**\n     * Creates a new database assigned to a specific server.\n     *\n     * @throws \\Throwable\n     */\n    public function newDatabase(StoreServerDatabaseRequest $request, Server $server): RedirectResponse\n    {\n        $this->databaseManagementService->create($server, [\n            'database' => DatabaseManagementService::generateUniqueDatabaseName($request->input('database'), $server->id),\n            'remote' => $request->input('remote'),\n            'database_host_id' => $request->input('database_host_id'),\n            'max_connections' => $request->input('max_connections'),\n        ]);\n\n        return redirect()->route('admin.servers.view.database', $server->id)->withInput();\n    }\n\n    /**\n     * Resets the database password for a specific database on this server.\n     *\n     * @throws \\Throwable\n     */\n    public function resetDatabasePassword(Request $request, Server $server): Response\n    {\n        /** @var Database $database */\n        $database = $server->databases()->findOrFail($request->input('database'));\n\n        $this->databasePasswordService->handle($database);\n\n        return response('', 204);\n    }\n\n    /**\n     * Deletes a database from a server.\n     *\n     * @throws \\Exception\n     */\n    public function deleteDatabase(Server $server, Database $database): Response\n    {\n        $this->databaseManagementService->delete($database);\n\n        return response('', 204);\n    }\n\n    /**\n     * Add a mount to a server.\n     *\n     * @throws \\Throwable\n     */\n    public function addMount(Request $request, Server $server): RedirectResponse\n    {\n        $mountServer = (new MountServer())->forceFill([\n            'mount_id' => $request->input('mount_id'),\n            'server_id' => $server->id,\n        ]);\n\n        $mountServer->saveOrFail();\n\n        $this->alert->success('已成功添加挂载。')->flash();\n\n        return redirect()->route('admin.servers.view.mounts', $server->id);\n    }\n\n    /**\n     * Remove a mount from a server.\n     */\n    public function deleteMount(Server $server, Mount $mount): RedirectResponse\n    {\n        MountServer::where('mount_id', $mount->id)->where('server_id', $server->id)->delete();\n\n        $this->alert->success('已成功移除挂载。')->flash();\n\n        return redirect()->route('admin.servers.view.mounts', $server->id);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Settings/AdvancedController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Settings;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Illuminate\\Contracts\\Console\\Kernel;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Illuminate\\Contracts\\Config\\Repository as ConfigRepository;\nuse Pterodactyl\\Contracts\\Repository\\SettingsRepositoryInterface;\nuse Pterodactyl\\Http\\Requests\\Admin\\Settings\\AdvancedSettingsFormRequest;\n\nclass AdvancedController extends Controller\n{\n    /**\n     * AdvancedController constructor.\n     */\n    public function __construct(\n        private AlertsMessageBag $alert,\n        private ConfigRepository $config,\n        private Kernel $kernel,\n        private SettingsRepositoryInterface $settings,\n    ) {\n    }\n\n    /**\n     * Render advanced Panel settings UI.\n     */\n    public function index(): View\n    {\n        $showRecaptchaWarning = false;\n        if (\n            $this->config->get('recaptcha._shipped_secret_key') === $this->config->get('recaptcha.secret_key')\n            || $this->config->get('recaptcha._shipped_website_key') === $this->config->get('recaptcha.website_key')\n        ) {\n            $showRecaptchaWarning = true;\n        }\n\n        return view('admin.settings.advanced', [\n            'showRecaptchaWarning' => $showRecaptchaWarning,\n        ]);\n    }\n\n    /**\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(AdvancedSettingsFormRequest $request): RedirectResponse\n    {\n        foreach ($request->normalize() as $key => $value) {\n            $this->settings->set('settings::' . $key, $value);\n        }\n\n        $this->kernel->call('queue:restart');\n        $this->alert->success('高级设置已成功更新，工作队列已重新启动以应用这些更改。')->flash();\n\n        return redirect()->route('admin.settings.advanced');\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Settings/IndexController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Settings;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Illuminate\\Contracts\\Console\\Kernel;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Traits\\Helpers\\AvailableLanguages;\nuse Pterodactyl\\Services\\Helpers\\SoftwareVersionService;\nuse Pterodactyl\\Contracts\\Repository\\SettingsRepositoryInterface;\nuse Pterodactyl\\Http\\Requests\\Admin\\Settings\\BaseSettingsFormRequest;\n\nclass IndexController extends Controller\n{\n    use AvailableLanguages;\n\n    /**\n     * IndexController constructor.\n     */\n    public function __construct(\n        private AlertsMessageBag $alert,\n        private Kernel $kernel,\n        private SettingsRepositoryInterface $settings,\n        private SoftwareVersionService $versionService,\n    ) {\n    }\n\n    /**\n     * Render the UI for basic Panel settings.\n     */\n    public function index(): View\n    {\n        return view('admin.settings.index', [\n            'version' => $this->versionService,\n            'languages' => $this->getAvailableLanguages(true),\n        ]);\n    }\n\n    /**\n     * Handle settings update.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(BaseSettingsFormRequest $request): RedirectResponse\n    {\n        foreach ($request->normalize() as $key => $value) {\n            $this->settings->set('settings::' . $key, $value);\n        }\n\n        $this->kernel->call('queue:restart');\n        $this->alert->success('面板设置已成功更新，工作队列已重新启动以应用这些更改。')->flash();\n\n        return redirect()->route('admin.settings');\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/Settings/MailController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin\\Settings;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Http\\Response;\nuse Illuminate\\Contracts\\Console\\Kernel;\nuse Pterodactyl\\Notifications\\MailTested;\nuse Illuminate\\Support\\Facades\\Notification;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Providers\\SettingsServiceProvider;\nuse Illuminate\\Contracts\\Config\\Repository as ConfigRepository;\nuse Pterodactyl\\Contracts\\Repository\\SettingsRepositoryInterface;\nuse Pterodactyl\\Http\\Requests\\Admin\\Settings\\MailSettingsFormRequest;\n\nclass MailController extends Controller\n{\n    /**\n     * MailController constructor.\n     */\n    public function __construct(\n        private ConfigRepository $config,\n        private Encrypter $encrypter,\n        private Kernel $kernel,\n        private SettingsRepositoryInterface $settings,\n    ) {\n    }\n\n    /**\n     * Render UI for editing mail settings. This UI should only display if\n     * the server is configured to send mail using SMTP.\n     */\n    public function index(): View\n    {\n        return view('admin.settings.mail', [\n            'disabled' => $this->config->get('mail.default') !== 'smtp',\n        ]);\n    }\n\n    /**\n     * Handle request to update SMTP mail settings.\n     *\n     * @throws DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(MailSettingsFormRequest $request): Response\n    {\n        if ($this->config->get('mail.default') !== 'smtp') {\n            throw new DisplayException('功能仅在 SMTP 是面板选定的电子邮件驱动程序时才可用。');\n        }\n\n        $values = $request->normalize();\n        if (array_get($values, 'mail:mailers:smtp:password') === '!e') {\n            $values['mail:mailers:smtp:password'] = '';\n        }\n\n        foreach ($values as $key => $value) {\n            if (in_array($key, SettingsServiceProvider::getEncryptedKeys()) && !empty($value)) {\n                $value = $this->encrypter->encrypt($value);\n            }\n\n            $this->settings->set('settings::' . $key, $value);\n        }\n\n        $this->kernel->call('queue:restart');\n\n        return response('', 204);\n    }\n\n    /**\n     * Submit a request to send a test mail message.\n     */\n    public function test(Request $request): Response\n    {\n        try {\n            Notification::route('mail', $request->user()->email)\n                ->notify(new MailTested($request->user()));\n        } catch (\\Exception $exception) {\n            return response($exception->getMessage(), 500);\n        }\n\n        return response('', 204);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Admin/UserController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Admin;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Model;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Http\\RedirectResponse;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Illuminate\\View\\Factory as ViewFactory;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Illuminate\\Contracts\\Translation\\Translator;\nuse Pterodactyl\\Services\\Users\\UserUpdateService;\nuse Pterodactyl\\Traits\\Helpers\\AvailableLanguages;\nuse Pterodactyl\\Services\\Users\\UserCreationService;\nuse Pterodactyl\\Services\\Users\\UserDeletionService;\nuse Pterodactyl\\Http\\Requests\\Admin\\UserFormRequest;\nuse Pterodactyl\\Http\\Requests\\Admin\\NewUserFormRequest;\nuse Pterodactyl\\Contracts\\Repository\\UserRepositoryInterface;\n\nclass UserController extends Controller\n{\n    use AvailableLanguages;\n\n    /**\n     * UserController constructor.\n     */\n    public function __construct(\n        protected AlertsMessageBag $alert,\n        protected UserCreationService $creationService,\n        protected UserDeletionService $deletionService,\n        protected Translator $translator,\n        protected UserUpdateService $updateService,\n        protected UserRepositoryInterface $repository,\n        protected ViewFactory $view,\n    ) {\n    }\n\n    /**\n     * Display user index page.\n     */\n    public function index(Request $request): View\n    {\n        $users = QueryBuilder::for(\n            User::query()->select('users.*')\n                ->selectRaw('COUNT(DISTINCT(subusers.id)) as subuser_of_count')\n                ->selectRaw('COUNT(DISTINCT(servers.id)) as servers_count')\n                ->leftJoin('subusers', 'subusers.user_id', '=', 'users.id')\n                ->leftJoin('servers', 'servers.owner_id', '=', 'users.id')\n                ->groupBy('users.id')\n        )\n            ->allowedFilters(['username', 'email', 'uuid'])\n            ->defaultSort('-root_admin')\n            ->allowedSorts(['id', 'uuid'])\n            ->paginate(50);\n\n        return view('admin.users.index', ['users' => $users]);\n    }\n\n    /**\n     * Display new user page.\n     */\n    public function create(): View\n    {\n        return view('admin.users.new', [\n            'languages' => $this->getAvailableLanguages(true),\n        ]);\n    }\n\n    /**\n     * Display user view page.\n     */\n    public function view(User $user): View\n    {\n        return view('admin.users.view', [\n            'user' => $user,\n            'languages' => $this->getAvailableLanguages(true),\n        ]);\n    }\n\n    /**\n     * Delete a user from the system.\n     *\n     * @throws \\Exception\n     * @throws DisplayException\n     */\n    public function delete(Request $request, User $user): RedirectResponse\n    {\n        if ($request->user()->is($user)) {\n            throw new DisplayException(__('admin/user.exceptions.delete_self'));\n        }\n\n        $this->deletionService->handle($user);\n\n        return redirect()->route('admin.users');\n    }\n\n    /**\n     * Create a user.\n     *\n     * @throws \\Exception\n     * @throws \\Throwable\n     */\n    public function store(NewUserFormRequest $request): RedirectResponse\n    {\n        $user = $this->creationService->handle($request->normalize());\n        $this->alert->success($this->translator->get('admin/user.notices.account_created'))->flash();\n\n        return redirect()->route('admin.users.view', $user->id);\n    }\n\n    /**\n     * Update a user on the system.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(UserFormRequest $request, User $user): RedirectResponse\n    {\n        $this->updateService\n            ->setUserLevel(User::USER_LEVEL_ADMIN)\n            ->handle($user, $request->normalize());\n\n        $this->alert->success(trans('admin/user.notices.account_updated'))->flash();\n\n        return redirect()->route('admin.users.view', $user->id);\n    }\n\n    /**\n     * Get a JSON response of users on the system.\n     */\n    public function json(Request $request): Model|Collection\n    {\n        $users = QueryBuilder::for(User::query())->allowedFilters(['email'])->paginate(25);\n\n        // Handle single user requests.\n        if ($request->query('user_id')) {\n            $user = User::query()->findOrFail($request->input('user_id'));\n            // @phpstan-ignore-next-line property.notFound\n            $user->md5 = md5(strtolower($user->email));\n\n            return $user;\n        }\n\n        return $users->map(function ($item) {\n            // @phpstan-ignore-next-line property.notFound\n            $item->md5 = md5(strtolower($item->email));\n\n            return $item;\n        });\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/ApplicationApiController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application;\n\nuse Illuminate\\Http\\Request;\nuse Webmozart\\Assert\\Assert;\nuse Illuminate\\Http\\Response;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Container\\Container;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Extensions\\Spatie\\Fractalistic\\Fractal;\nuse Pterodactyl\\Transformers\\Api\\Application\\BaseTransformer;\n\nabstract class ApplicationApiController extends Controller\n{\n    protected Request $request;\n\n    protected Fractal $fractal;\n\n    /**\n     * ApplicationApiController constructor.\n     */\n    public function __construct()\n    {\n        Container::getInstance()->call([$this, 'loadDependencies']);\n\n        // Parse all the includes to use on this request.\n        $input = $this->request->input('include', []);\n        $input = is_array($input) ? $input : explode(',', $input);\n\n        $includes = (new Collection($input))->map(function ($value) {\n            return trim($value);\n        })->filter()->toArray();\n\n        $this->fractal->parseIncludes($includes);\n        $this->fractal->limitRecursion(2);\n    }\n\n    /**\n     * Perform dependency injection of certain classes needed for core functionality\n     * without littering the constructors of classes that extend this abstract.\n     */\n    public function loadDependencies(Fractal $fractal, Request $request)\n    {\n        $this->fractal = $fractal;\n        $this->request = $request;\n    }\n\n    /**\n     * Return an instance of an application transformer.\n     *\n     * @template T of \\Pterodactyl\\Transformers\\Api\\Application\\BaseTransformer\n     *\n     * @param class-string<T> $abstract\n     *\n     * @return T\n     *\n     * @noinspection PhpDocSignatureInspection\n     */\n    public function getTransformer(string $abstract)\n    {\n        Assert::subclassOf($abstract, BaseTransformer::class); // @phpstan-ignore staticMethod.alreadyNarrowedType\n\n        return $abstract::fromRequest($this->request);\n    }\n\n    /**\n     * Return an HTTP/204 response for the API.\n     */\n    protected function returnNoContent(): Response\n    {\n        return new Response('', Response::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Locations/LocationController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Locations;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Location;\nuse Illuminate\\Http\\JsonResponse;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Pterodactyl\\Services\\Locations\\LocationUpdateService;\nuse Pterodactyl\\Services\\Locations\\LocationCreationService;\nuse Pterodactyl\\Services\\Locations\\LocationDeletionService;\nuse Pterodactyl\\Transformers\\Api\\Application\\LocationTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Locations\\GetLocationRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Locations\\GetLocationsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Locations\\StoreLocationRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Locations\\DeleteLocationRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Locations\\UpdateLocationRequest;\n\nclass LocationController extends ApplicationApiController\n{\n    /**\n     * LocationController constructor.\n     */\n    public function __construct(\n        private LocationCreationService $creationService,\n        private LocationDeletionService $deletionService,\n        private LocationUpdateService $updateService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Return all the locations currently registered on the Panel.\n     */\n    public function index(GetLocationsRequest $request): array\n    {\n        $locations = QueryBuilder::for(Location::query())\n            ->allowedFilters(['short', 'long'])\n            ->allowedSorts(['id'])\n            ->paginate($request->query('per_page') ?? 50);\n\n        return $this->fractal->collection($locations)\n            ->transformWith($this->getTransformer(LocationTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Return a single location.\n     */\n    public function view(GetLocationRequest $request, Location $location): array\n    {\n        return $this->fractal->item($location)\n            ->transformWith($this->getTransformer(LocationTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Store a new location on the Panel and return an HTTP/201 response code with the\n     * new location attached.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function store(StoreLocationRequest $request): JsonResponse\n    {\n        $location = $this->creationService->handle($request->validated());\n\n        return $this->fractal->item($location)\n            ->transformWith($this->getTransformer(LocationTransformer::class))\n            ->addMeta([\n                'resource' => route('api.application.locations.view', [\n                    'location' => $location->id,\n                ]),\n            ])\n            ->respond(201);\n    }\n\n    /**\n     * Update a location on the Panel and return the updated record to the user.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(UpdateLocationRequest $request, Location $location): array\n    {\n        $location = $this->updateService->handle($location, $request->validated());\n\n        return $this->fractal->item($location)\n            ->transformWith($this->getTransformer(LocationTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Delete a location from the Panel.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Location\\HasActiveNodesException\n     */\n    public function delete(DeleteLocationRequest $request, Location $location): Response\n    {\n        $this->deletionService->handle($location);\n\n        return response('', 204);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Nests/EggController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Nests;\n\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\Nest;\nuse Pterodactyl\\Transformers\\Api\\Application\\EggTransformer;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Nests\\Eggs\\GetEggRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Nests\\Eggs\\GetEggsRequest;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\n\nclass EggController extends ApplicationApiController\n{\n    /**\n     * Return all eggs that exist for a given nest.\n     */\n    public function index(GetEggsRequest $request, Nest $nest): array\n    {\n        return $this->fractal->collection($nest->eggs)\n            ->transformWith($this->getTransformer(EggTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Return a single egg that exists on the specified nest.\n     */\n    public function view(GetEggRequest $request, Nest $nest, Egg $egg): array\n    {\n        return $this->fractal->item($egg)\n            ->transformWith($this->getTransformer(EggTransformer::class))\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Nests/NestController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Nests;\n\nuse Pterodactyl\\Models\\Nest;\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\nuse Pterodactyl\\Transformers\\Api\\Application\\NestTransformer;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Nests\\GetNestsRequest;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\n\nclass NestController extends ApplicationApiController\n{\n    /**\n     * NestController constructor.\n     */\n    public function __construct(private NestRepositoryInterface $repository)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Return all Nests that exist on the Panel.\n     */\n    public function index(GetNestsRequest $request): array\n    {\n        $nests = $this->repository->paginated($request->query('per_page') ?? 50);\n\n        return $this->fractal->collection($nests)\n            ->transformWith($this->getTransformer(NestTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Return information about a single Nest model.\n     */\n    public function view(GetNestsRequest $request, Nest $nest): array\n    {\n        return $this->fractal->item($nest)\n            ->transformWith($this->getTransformer(NestTransformer::class))\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Nodes/AllocationController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes;\n\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Models\\Allocation;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Spatie\\QueryBuilder\\AllowedFilter;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Pterodactyl\\Services\\Allocations\\AssignmentService;\nuse Pterodactyl\\Services\\Allocations\\AllocationDeletionService;\nuse Pterodactyl\\Transformers\\Api\\Application\\AllocationTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Allocations\\GetAllocationsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Allocations\\StoreAllocationRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Allocations\\DeleteAllocationRequest;\n\nclass AllocationController extends ApplicationApiController\n{\n    /**\n     * AllocationController constructor.\n     */\n    public function __construct(\n        private AssignmentService $assignmentService,\n        private AllocationDeletionService $deletionService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Return all the allocations that exist for a given node.\n     */\n    public function index(GetAllocationsRequest $request, Node $node): array\n    {\n        $allocations = QueryBuilder::for($node->allocations())\n            ->allowedFilters([\n                AllowedFilter::exact('ip'),\n                AllowedFilter::exact('port'),\n                'ip_alias',\n                AllowedFilter::callback('server_id', function (Builder $builder, $value) {\n                    if (empty($value) || is_bool($value) || !ctype_digit((string) $value)) {\n                        return $builder->whereNull('server_id');\n                    }\n\n                    return $builder->where('server_id', $value);\n                }),\n            ])\n            ->paginate($request->query('per_page') ?? 50);\n\n        return $this->fractal->collection($allocations)\n            ->transformWith($this->getTransformer(AllocationTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Store new allocations for a given node.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\CidrOutOfRangeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\InvalidPortMappingException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\PortOutOfRangeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\TooManyPortsInRangeException\n     */\n    public function store(StoreAllocationRequest $request, Node $node): JsonResponse\n    {\n        $this->assignmentService->handle($node, $request->validated());\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Delete a specific allocation from the Panel.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\ServerUsingAllocationException\n     */\n    public function delete(DeleteAllocationRequest $request, Node $node, Allocation $allocation): JsonResponse\n    {\n        $this->deletionService->handle($allocation);\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Nodes/NodeConfigurationController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes;\n\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes\\GetNodeRequest;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\n\nclass NodeConfigurationController extends ApplicationApiController\n{\n    /**\n     * Returns the configuration information for a node. This allows for automated deployments\n     * to remote machines so long as an API key is provided to the machine to make the request\n     * with, and the node is known.\n     */\n    public function __invoke(GetNodeRequest $request, Node $node): JsonResponse\n    {\n        return new JsonResponse($node->getConfiguration());\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Nodes/NodeController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes;\n\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Http\\JsonResponse;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Pterodactyl\\Services\\Nodes\\NodeUpdateService;\nuse Pterodactyl\\Services\\Nodes\\NodeCreationService;\nuse Pterodactyl\\Services\\Nodes\\NodeDeletionService;\nuse Pterodactyl\\Transformers\\Api\\Application\\NodeTransformer;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes\\GetNodeRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes\\GetNodesRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes\\StoreNodeRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes\\DeleteNodeRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes\\UpdateNodeRequest;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\n\nclass NodeController extends ApplicationApiController\n{\n    /**\n     * NodeController constructor.\n     */\n    public function __construct(\n        private NodeCreationService $creationService,\n        private NodeDeletionService $deletionService,\n        private NodeUpdateService $updateService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Return all the nodes currently available on the Panel.\n     */\n    public function index(GetNodesRequest $request): array\n    {\n        $nodes = QueryBuilder::for(Node::query())\n            ->allowedFilters(['uuid', 'name', 'fqdn', 'daemon_token_id'])\n            ->allowedSorts(['id', 'uuid', 'memory', 'disk'])\n            ->paginate($request->query('per_page') ?? 50);\n\n        return $this->fractal->collection($nodes)\n            ->transformWith($this->getTransformer(NodeTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Return data for a single instance of a node.\n     */\n    public function view(GetNodeRequest $request, Node $node): array\n    {\n        return $this->fractal->item($node)\n            ->transformWith($this->getTransformer(NodeTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Create a new node on the Panel. Returns the created node and an HTTP/201\n     * status response on success.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function store(StoreNodeRequest $request): JsonResponse\n    {\n        $node = $this->creationService->handle($request->validated());\n\n        return $this->fractal->item($node)\n            ->transformWith($this->getTransformer(NodeTransformer::class))\n            ->addMeta([\n                'resource' => route('api.application.nodes.view', [\n                    'node' => $node->id,\n                ]),\n            ])\n            ->respond(201);\n    }\n\n    /**\n     * Update an existing node on the Panel.\n     *\n     * @throws \\Throwable\n     */\n    public function update(UpdateNodeRequest $request, Node $node): array\n    {\n        $node = $this->updateService->handle(\n            $node,\n            $request->validated(),\n            $request->input('reset_secret') === true\n        );\n\n        return $this->fractal->item($node)\n            ->transformWith($this->getTransformer(NodeTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Deletes a given node from the Panel as long as there are no servers\n     * currently attached to it.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\HasActiveServersException\n     */\n    public function delete(DeleteNodeRequest $request, Node $node): JsonResponse\n    {\n        $this->deletionService->handle($node);\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Nodes/NodeDeploymentController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes;\n\nuse Pterodactyl\\Services\\Deployment\\FindViableNodesService;\nuse Pterodactyl\\Transformers\\Api\\Application\\NodeTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes\\GetDeployableNodesRequest;\n\nclass NodeDeploymentController extends ApplicationApiController\n{\n    /**\n     * NodeDeploymentController constructor.\n     */\n    public function __construct(private FindViableNodesService $viableNodesService)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Finds any nodes that are available using the given deployment criteria. This works\n     * similarly to the server creation process, but allows you to pass the deployment object\n     * to this endpoint and get back a list of all Nodes satisfying the requirements.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableNodeException\n     */\n    public function __invoke(GetDeployableNodesRequest $request): array\n    {\n        $data = $request->validated();\n        $nodes = $this->viableNodesService->setLocations($data['location_ids'] ?? [])\n            ->setMemory($data['memory'])\n            ->setDisk($data['disk'])\n            ->handle($request->query('per_page'), $request->query('page'));\n\n        return $this->fractal->collection($nodes)\n            ->transformWith($this->getTransformer(NodeTransformer::class))\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Servers/DatabaseController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Database;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Services\\Databases\\DatabasePasswordService;\nuse Pterodactyl\\Services\\Databases\\DatabaseManagementService;\nuse Pterodactyl\\Transformers\\Api\\Application\\ServerDatabaseTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\Databases\\GetServerDatabaseRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\Databases\\GetServerDatabasesRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\Databases\\ServerDatabaseWriteRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\Databases\\StoreServerDatabaseRequest;\n\nclass DatabaseController extends ApplicationApiController\n{\n    /**\n     * DatabaseController constructor.\n     */\n    public function __construct(\n        private DatabaseManagementService $databaseManagementService,\n        private DatabasePasswordService $databasePasswordService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Return a listing of all databases currently available to a single\n     * server.\n     */\n    public function index(GetServerDatabasesRequest $request, Server $server): array\n    {\n        return $this->fractal->collection($server->databases)\n            ->transformWith($this->getTransformer(ServerDatabaseTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Return a single server database.\n     */\n    public function view(GetServerDatabaseRequest $request, Server $server, Database $database): array\n    {\n        return $this->fractal->item($database)\n            ->transformWith($this->getTransformer(ServerDatabaseTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Reset the password for a specific server database.\n     *\n     * @throws \\Throwable\n     */\n    public function resetPassword(ServerDatabaseWriteRequest $request, Server $server, Database $database): JsonResponse\n    {\n        $this->databasePasswordService->handle($database);\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Create a new database on the Panel for a given server.\n     *\n     * @throws \\Throwable\n     */\n    public function store(StoreServerDatabaseRequest $request, Server $server): JsonResponse\n    {\n        $database = $this->databaseManagementService->create($server, array_merge($request->validated(), [\n            'database' => $request->databaseName(),\n        ]));\n\n        return $this->fractal->item($database)\n            ->transformWith($this->getTransformer(ServerDatabaseTransformer::class))\n            ->addMeta([\n                'resource' => route('api.application.servers.databases.view', [\n                    'server' => $server->id,\n                    'database' => $database->id,\n                ]),\n            ])\n            ->respond(Response::HTTP_CREATED);\n    }\n\n    /**\n     * Handle a request to delete a specific server database from the Panel.\n     */\n    public function delete(ServerDatabaseWriteRequest $request, Server $server, Database $database): Response\n    {\n        $this->databaseManagementService->delete($database);\n\n        return response('', 204);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Servers/ExternalServerController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Transformers\\Api\\Application\\ServerTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\GetExternalServerRequest;\n\nclass ExternalServerController extends ApplicationApiController\n{\n    /**\n     * Retrieve a specific server from the database using its external ID.\n     */\n    public function index(GetExternalServerRequest $request, string $external_id): array\n    {\n        $server = Server::query()->where('external_id', $external_id)->firstOrFail();\n\n        return $this->fractal->item($server)\n            ->transformWith($this->getTransformer(ServerTransformer::class))\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Servers/ServerController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Pterodactyl\\Services\\Servers\\ServerCreationService;\nuse Pterodactyl\\Services\\Servers\\ServerDeletionService;\nuse Pterodactyl\\Transformers\\Api\\Application\\ServerTransformer;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\GetServerRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\GetServersRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\ServerWriteRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\StoreServerRequest;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\n\nclass ServerController extends ApplicationApiController\n{\n    /**\n     * ServerController constructor.\n     */\n    public function __construct(\n        private ServerCreationService $creationService,\n        private ServerDeletionService $deletionService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Return all the servers that currently exist on the Panel.\n     */\n    public function index(GetServersRequest $request): array\n    {\n        $servers = QueryBuilder::for(Server::query())\n            ->allowedFilters(['uuid', 'uuidShort', 'name', 'description', 'image', 'external_id'])\n            ->allowedSorts(['id', 'uuid'])\n            ->paginate($request->query('per_page') ?? 50);\n\n        return $this->fractal->collection($servers)\n            ->transformWith($this->getTransformer(ServerTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Create a new server on the system.\n     *\n     * @throws \\Throwable\n     * @throws \\Illuminate\\Validation\\ValidationException\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableAllocationException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableNodeException\n     */\n    public function store(StoreServerRequest $request): JsonResponse\n    {\n        $server = $this->creationService->handle($request->validated(), $request->getDeploymentObject());\n\n        return $this->fractal->item($server)\n            ->transformWith($this->getTransformer(ServerTransformer::class))\n            ->respond(201);\n    }\n\n    /**\n     * Show a single server transformed for the application API.\n     */\n    public function view(GetServerRequest $request, Server $server): array\n    {\n        return $this->fractal->item($server)\n            ->transformWith($this->getTransformer(ServerTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Deletes a server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     */\n    public function delete(ServerWriteRequest $request, Server $server, string $force = ''): Response\n    {\n        $this->deletionService->withForce($force === 'force')->handle($server);\n\n        return $this->returnNoContent();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Servers/ServerDetailsController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Services\\Servers\\BuildModificationService;\nuse Pterodactyl\\Services\\Servers\\DetailsModificationService;\nuse Pterodactyl\\Transformers\\Api\\Application\\ServerTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\UpdateServerDetailsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\UpdateServerBuildConfigurationRequest;\n\nclass ServerDetailsController extends ApplicationApiController\n{\n    /**\n     * ServerDetailsController constructor.\n     */\n    public function __construct(\n        private BuildModificationService $buildModificationService,\n        private DetailsModificationService $detailsModificationService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Update the details for a specific server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function details(UpdateServerDetailsRequest $request, Server $server): array\n    {\n        $updated = $this->detailsModificationService->returnUpdatedModel()->handle(\n            $server,\n            $request->validated()\n        );\n\n        return $this->fractal->item($updated)\n            ->transformWith($this->getTransformer(ServerTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Update the build details for a specific server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function build(UpdateServerBuildConfigurationRequest $request, Server $server): array\n    {\n        $server = $this->buildModificationService->handle($server, $request->validated());\n\n        return $this->fractal->item($server)\n            ->transformWith($this->getTransformer(ServerTransformer::class))\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Servers/ServerManagementController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Services\\Servers\\SuspensionService;\nuse Pterodactyl\\Services\\Servers\\ReinstallServerService;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\ServerWriteRequest;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\n\nclass ServerManagementController extends ApplicationApiController\n{\n    /**\n     * ServerManagementController constructor.\n     */\n    public function __construct(\n        private ReinstallServerService $reinstallServerService,\n        private SuspensionService $suspensionService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Suspend a server on the Panel.\n     *\n     * @throws \\Throwable\n     */\n    public function suspend(ServerWriteRequest $request, Server $server): Response\n    {\n        $this->suspensionService->toggle($server);\n\n        return $this->returnNoContent();\n    }\n\n    /**\n     * Unsuspend a server on the Panel.\n     *\n     * @throws \\Throwable\n     */\n    public function unsuspend(ServerWriteRequest $request, Server $server): Response\n    {\n        $this->suspensionService->toggle($server, SuspensionService::ACTION_UNSUSPEND);\n\n        return $this->returnNoContent();\n    }\n\n    /**\n     * Mark a server as needing to be reinstalled.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function reinstall(ServerWriteRequest $request, Server $server): Response\n    {\n        $this->reinstallServerService->handle($server);\n\n        return $this->returnNoContent();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Servers/StartupController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Services\\Servers\\StartupModificationService;\nuse Pterodactyl\\Transformers\\Api\\Application\\ServerTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\UpdateServerStartupRequest;\n\nclass StartupController extends ApplicationApiController\n{\n    /**\n     * StartupController constructor.\n     */\n    public function __construct(private StartupModificationService $modificationService)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Update the startup and environment settings for a specific server.\n     *\n     * @throws \\Illuminate\\Validation\\ValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function index(UpdateServerStartupRequest $request, Server $server): array\n    {\n        $server = $this->modificationService\n            ->setUserLevel(User::USER_LEVEL_ADMIN)\n            ->handle($server, $request->validated());\n\n        return $this->fractal->item($server)\n            ->transformWith($this->getTransformer(ServerTransformer::class))\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Users/ExternalUserController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Users;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Transformers\\Api\\Application\\UserTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Users\\GetExternalUserRequest;\n\nclass ExternalUserController extends ApplicationApiController\n{\n    /**\n     * Retrieve a specific user from the database using their external ID.\n     */\n    public function index(GetExternalUserRequest $request, string $external_id): array\n    {\n        $user = User::query()->where('external_id', $external_id)->firstOrFail();\n\n        return $this->fractal->item($user)\n            ->transformWith($this->getTransformer(UserTransformer::class))\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Application/Users/UserController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Application\\Users;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\JsonResponse;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Pterodactyl\\Services\\Users\\UserUpdateService;\nuse Pterodactyl\\Services\\Users\\UserCreationService;\nuse Pterodactyl\\Services\\Users\\UserDeletionService;\nuse Pterodactyl\\Transformers\\Api\\Application\\UserTransformer;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Users\\GetUsersRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Users\\StoreUserRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Users\\DeleteUserRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\Users\\UpdateUserRequest;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\n\nclass UserController extends ApplicationApiController\n{\n    /**\n     * UserController constructor.\n     */\n    public function __construct(\n        private UserCreationService $creationService,\n        private UserDeletionService $deletionService,\n        private UserUpdateService $updateService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Handle request to list all users on the panel. Returns a JSON-API representation\n     * of a collection of users including any defined relations passed in\n     * the request.\n     */\n    public function index(GetUsersRequest $request): array\n    {\n        $users = QueryBuilder::for(User::query())\n            ->allowedFilters(['email', 'uuid', 'username', 'external_id'])\n            ->allowedSorts(['id', 'uuid'])\n            ->paginate($request->query('per_page') ?? 50);\n\n        return $this->fractal->collection($users)\n            ->transformWith($this->getTransformer(UserTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Handle a request to view a single user. Includes any relations that\n     * were defined in the request.\n     */\n    public function view(GetUsersRequest $request, User $user): array\n    {\n        return $this->fractal->item($user)\n            ->transformWith($this->getTransformer(UserTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Update an existing user on the system and return the response. Returns the\n     * updated user model response on success. Supports handling of token revocation\n     * errors when switching a user from an admin to a normal user.\n     *\n     * Revocation errors are returned under the 'revocation_errors' key in the response\n     * meta. If there are no errors this is an empty array.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(UpdateUserRequest $request, User $user): array\n    {\n        $this->updateService->setUserLevel(User::USER_LEVEL_ADMIN);\n        $user = $this->updateService->handle($user, $request->validated());\n\n        $response = $this->fractal->item($user)\n            ->transformWith($this->getTransformer(UserTransformer::class));\n\n        return $response->toArray();\n    }\n\n    /**\n     * Store a new user on the system. Returns the created user and an HTTP/201\n     * header on successful creation.\n     *\n     * @throws \\Exception\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function store(StoreUserRequest $request): JsonResponse\n    {\n        $user = $this->creationService->handle($request->validated());\n\n        return $this->fractal->item($user)\n            ->transformWith($this->getTransformer(UserTransformer::class))\n            ->addMeta([\n                'resource' => route('api.application.users.view', [\n                    'user' => $user->id,\n                ]),\n            ])\n            ->respond(201);\n    }\n\n    /**\n     * Handle a request to delete a user from the Panel. Returns a HTTP/204 response\n     * on successful deletion.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     */\n    public function delete(DeleteUserRequest $request, User $user): JsonResponse\n    {\n        $this->deletionService->handle($user);\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/AccountController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client;\n\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Http\\Response;\nuse Illuminate\\Auth\\AuthManager;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Illuminate\\Support\\Facades\\RateLimiter;\nuse Pterodactyl\\Services\\Users\\UserUpdateService;\nuse Pterodactyl\\Transformers\\Api\\Client\\AccountTransformer;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Account\\UpdateEmailRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Account\\UpdatePasswordRequest;\nuse Symfony\\Component\\HttpKernel\\Exception\\TooManyRequestsHttpException;\n\nclass AccountController extends ClientApiController\n{\n    /**\n     * The number of seconds that must elapse before the email change throttle resets.\n     */\n    private const EMAIL_UPDATE_THROTTLE = 60 * 60 * 24;\n\n    /**\n     * AccountController constructor.\n     */\n    public function __construct(private AuthManager $manager, private UserUpdateService $updateService)\n    {\n        parent::__construct();\n    }\n\n    public function index(Request $request): array\n    {\n        return $this->fractal->item($request->user())\n            ->transformWith($this->getTransformer(AccountTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Update the authenticated user's email address.\n     */\n    public function updateEmail(UpdateEmailRequest $request): JsonResponse\n    {\n        $user = $request->user();\n        // Only allow a user to change their email three times in the span\n        // of 24 hours. This prevents malicious users from trying to find\n        // existing accounts in the system by constantly changing their email.\n        if (RateLimiter::tooManyAttempts($key = \"user:update-email:{$user->uuid}\", 3)) {\n            throw new TooManyRequestsHttpException(message: 'Your email address has been changed too many times today. Please try again later.');\n        }\n\n        $original = $user->email;\n        if (mb_strtolower($original) !== mb_strtolower($request->validated('email'))) {\n            RateLimiter::hit($key, self::EMAIL_UPDATE_THROTTLE);\n\n            $this->updateService->handle($user, $request->validated());\n\n            Activity::event('user:account.email-changed')\n                ->property(['old' => $original, 'new' => $request->validated('email')])\n                ->log();\n        }\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Update the authenticated user's password. All existing sessions will be logged\n     * out immediately.\n     *\n     * @throws \\Throwable\n     */\n    public function updatePassword(UpdatePasswordRequest $request): JsonResponse\n    {\n        $user = Activity::event('user:account.password-changed')->transaction(function () use ($request) {\n            return $this->updateService->handle($request->user(), $request->validated());\n        });\n\n        $guard = $this->manager->guard();\n        // If you do not update the user in the session you'll end up working with a\n        // cached copy of the user that does not include the updated password. Do this\n        // to correctly store the new user details in the guard and allow the logout\n        // other devices functionality to work.\n        $guard->setUser($user);\n\n        // This method doesn't exist in the stateless Sanctum world.\n        if (method_exists($guard, 'logoutOtherDevices')) { // @phpstan-ignore function.alreadyNarrowedType\n            $guard->logoutOtherDevices($request->input('password'));\n        }\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/ActivityLogController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client;\n\nuse Pterodactyl\\Models\\ActivityLog;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Spatie\\QueryBuilder\\AllowedFilter;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Pterodactyl\\Transformers\\Api\\Client\\ActivityLogTransformer;\n\nclass ActivityLogController extends ClientApiController\n{\n    /**\n     * Returns a paginated set of the user's activity logs.\n     */\n    public function __invoke(ClientApiRequest $request): array\n    {\n        $activity = QueryBuilder::for($request->user()->activity())\n            ->with('actor')\n            ->allowedFilters([AllowedFilter::partial('event')])\n            ->allowedSorts(['timestamp'])\n            ->whereNotIn('activity_logs.event', ActivityLog::DISABLED_EVENTS)\n            ->paginate(min($request->query('per_page', 25), 100))\n            ->appends($request->query());\n\n        return $this->fractal->collection($activity)\n            ->transformWith($this->getTransformer(ActivityLogTransformer::class))\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/ApiKeyController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client;\n\nuse Pterodactyl\\Models\\ApiKey;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Pterodactyl\\Transformers\\Api\\Client\\ApiKeyTransformer;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Account\\StoreApiKeyRequest;\n\nclass ApiKeyController extends ClientApiController\n{\n    /**\n     * Returns all the API keys that exist for the given client.\n     */\n    public function index(ClientApiRequest $request): array\n    {\n        return $this->fractal->collection($request->user()->apiKeys)\n            ->transformWith($this->getTransformer(ApiKeyTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Store a new API key for a user's account.\n     *\n     * @throws DisplayException\n     */\n    public function store(StoreApiKeyRequest $request): array\n    {\n        if ($request->user()->apiKeys->count() >= 25) {\n            throw new DisplayException('您的帐户已达到 API 密钥数量限制。');\n        }\n\n        $token = $request->user()->createToken(\n            $request->input('description'),\n            $request->input('allowed_ips')\n        );\n\n        Activity::event('user:api-key.create')\n            ->subject($token->accessToken)\n            ->property('identifier', $token->accessToken->identifier)\n            ->log();\n\n        return $this->fractal->item($token->accessToken)\n            ->transformWith($this->getTransformer(ApiKeyTransformer::class))\n            ->addMeta(['secret_token' => $token->plainTextToken])\n            ->toArray();\n    }\n\n    /**\n     * Deletes a given API key.\n     */\n    public function delete(ClientApiRequest $request, string $identifier): JsonResponse\n    {\n        /** @var ApiKey $key */\n        $key = $request->user()->apiKeys()\n            ->where('key_type', ApiKey::TYPE_ACCOUNT)\n            ->where('identifier', $identifier)\n            ->firstOrFail();\n\n        Activity::event('user:api-key.delete')\n            ->property('identifier', $key->identifier)\n            ->log();\n\n        $key->delete();\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/ClientApiController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Transformers\\Api\\Client\\BaseClientTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application\\ApplicationApiController;\n\nabstract class ClientApiController extends ApplicationApiController\n{\n    /**\n     * Returns only the includes which are valid for the given transformer.\n     */\n    protected function getIncludesForTransformer(BaseClientTransformer $transformer, array $merge = []): array\n    {\n        $filtered = array_filter($this->parseIncludes(), function ($datum) use ($transformer) {\n            return in_array($datum, $transformer->getAvailableIncludes());\n        });\n\n        return array_merge($filtered, $merge);\n    }\n\n    /**\n     * Returns the parsed includes for this request.\n     */\n    protected function parseIncludes(): array\n    {\n        $includes = $this->request->query('include') ?? [];\n\n        if (!is_string($includes)) {\n            return $includes;\n        }\n\n        return array_map(function ($item) {\n            return trim($item);\n        }, explode(',', $includes));\n    }\n\n    /**\n     * Return an instance of an application transformer.\n     *\n     * @template T of \\Pterodactyl\\Transformers\\Api\\Client\\BaseClientTransformer\n     *\n     * @param class-string<T> $abstract\n     *\n     * @return T\n     *\n     * @noinspection PhpDocSignatureInspection\n     */\n    public function getTransformer(string $abstract)\n    {\n        Assert::subclassOf($abstract, BaseClientTransformer::class); // @phpstan-ignore staticMethod.alreadyNarrowedType\n\n        return $abstract::fromRequest($this->request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/ClientController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Permission;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Spatie\\QueryBuilder\\AllowedFilter;\nuse Pterodactyl\\Models\\Filters\\MultiFieldServerFilter;\nuse Pterodactyl\\Transformers\\Api\\Client\\ServerTransformer;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\GetServersRequest;\n\nclass ClientController extends ClientApiController\n{\n    /**\n     * ClientController constructor.\n     */\n    public function __construct()\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Return all the servers available to the client making the API\n     * request, including servers the user has access to as a subuser.\n     */\n    public function index(GetServersRequest $request): array\n    {\n        $user = $request->user();\n        $transformer = $this->getTransformer(ServerTransformer::class);\n\n        // Start the query builder and ensure we eager load any requested relationships from the request.\n        $builder = QueryBuilder::for(\n            Server::query()->with($this->getIncludesForTransformer($transformer, ['node']))\n        )->allowedFilters([\n            'uuid',\n            'name',\n            'description',\n            'external_id',\n            AllowedFilter::custom('*', new MultiFieldServerFilter()),\n        ]);\n\n        $type = $request->input('type');\n        // Either return all the servers the user has access to because they are an admin `?type=admin` or\n        // just return all the servers the user has access to because they are the owner or a subuser of the\n        // server. If ?type=admin-all is passed all servers on the system will be returned to the user, rather\n        // than only servers they can see because they are an admin.\n        if (in_array($type, ['admin', 'admin-all'])) {\n            // If they aren't an admin but want all the admin servers don't fail the request, just\n            // make it a query that will never return any results back.\n            if (!$user->root_admin) {\n                $builder->whereRaw('1 = 2');\n            } else {\n                $builder = $type === 'admin-all'\n                    ? $builder\n                    : $builder->whereNotIn('servers.id', $user->accessibleServers()->pluck('id')->all());\n            }\n        } elseif ($type === 'owner') {\n            $builder = $builder->where('servers.owner_id', $user->id);\n        } else {\n            $builder = $builder->whereIn('servers.id', $user->accessibleServers()->pluck('id')->all());\n        }\n\n        $servers = $builder->paginate(min($request->query('per_page', 50), 100))->appends($request->query());\n\n        return $this->fractal->transformWith($transformer)->collection($servers)->toArray();\n    }\n\n    /**\n     * Returns all the subuser permissions available on the system.\n     */\n    public function permissions(): array\n    {\n        return [\n            'object' => 'system_permissions',\n            'attributes' => [\n                'permissions' => Permission::permissions(),\n            ],\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/SSHKeyController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client;\n\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Pterodactyl\\Transformers\\Api\\Client\\UserSSHKeyTransformer;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Account\\StoreSSHKeyRequest;\n\nclass SSHKeyController extends ClientApiController\n{\n    /**\n     * Returns all the SSH keys that have been configured for the logged-in\n     * user account.\n     */\n    public function index(ClientApiRequest $request): array\n    {\n        return $this->fractal->collection($request->user()->sshKeys)\n            ->transformWith($this->getTransformer(UserSSHKeyTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Stores a new SSH key for the authenticated user's account.\n     */\n    public function store(StoreSSHKeyRequest $request): array\n    {\n        $model = $request->user()->sshKeys()->create([\n            'name' => $request->input('name'),\n            'public_key' => $request->getPublicKey(),\n            'fingerprint' => $request->getKeyFingerprint(),\n        ]);\n\n        Activity::event('user:ssh-key.create')\n            ->subject($model)\n            ->property('fingerprint', $request->getKeyFingerprint())\n            ->log();\n\n        return $this->fractal->item($model)\n            ->transformWith($this->getTransformer(UserSSHKeyTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Deletes an SSH key from the user's account.\n     */\n    public function delete(ClientApiRequest $request): JsonResponse\n    {\n        $this->validate($request, ['fingerprint' => ['required', 'string']]);\n\n        $key = $request->user()->sshKeys()\n            ->where('fingerprint', $request->input('fingerprint'))\n            ->first();\n\n        if (!is_null($key)) {\n            $key->delete();\n\n            Activity::event('user:ssh-key.delete')\n                ->subject($key)\n                ->property('fingerprint', $key->fingerprint)\n                ->log();\n        }\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/ActivityLogController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Models\\ActivityLog;\nuse Spatie\\QueryBuilder\\QueryBuilder;\nuse Spatie\\QueryBuilder\\AllowedFilter;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Illuminate\\Database\\Query\\JoinClause;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Pterodactyl\\Transformers\\Api\\Client\\ActivityLogTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\n\nclass ActivityLogController extends ClientApiController\n{\n    /**\n     * Returns the activity logs for a server.\n     */\n    public function __invoke(ClientApiRequest $request, Server $server): array\n    {\n        $this->authorize(Permission::ACTION_ACTIVITY_READ, $server);\n\n        $activity = QueryBuilder::for($server->activity())\n            ->with('actor')\n            ->allowedSorts(['timestamp'])\n            ->allowedFilters([AllowedFilter::partial('event')])\n            ->whereNotIn('activity_logs.event', ActivityLog::DISABLED_EVENTS)\n            ->when(config('activity.hide_admin_activity'), function (Builder $builder) use ($server) {\n                // We could do this with a query and a lot of joins, but that gets pretty\n                // painful so for now we'll execute a simpler query.\n                $subusers = $server->subusers()->pluck('user_id')->merge($server->owner_id);\n\n                $builder->select('activity_logs.*')\n                    ->leftJoin('users', function (JoinClause $join) {\n                        $join->on('users.id', 'activity_logs.actor_id')\n                            ->where('activity_logs.actor_type', (new User())->getMorphClass());\n                    })\n                    ->where(function (Builder $builder) use ($subusers) {\n                        $builder->whereNull('users.id')\n                            ->orWhere('users.root_admin', 0)\n                            ->orWhereIn('users.id', $subusers);\n                    });\n            })\n            ->paginate(min($request->query('per_page', 25), 100))\n            ->appends($request->query());\n\n        return $this->fractal->collection($activity)\n            ->transformWith($this->getTransformer(ActivityLogTransformer::class))\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/BackupController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Backup;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Auth\\Access\\AuthorizationException;\nuse Pterodactyl\\Services\\Backups\\DeleteBackupService;\nuse Pterodactyl\\Services\\Backups\\DownloadLinkService;\nuse Pterodactyl\\Repositories\\Eloquent\\BackupRepository;\nuse Pterodactyl\\Services\\Backups\\InitiateBackupService;\nuse Pterodactyl\\Repositories\\Wings\\DaemonBackupRepository;\nuse Pterodactyl\\Transformers\\Api\\Client\\BackupTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Symfony\\Component\\HttpKernel\\Exception\\BadRequestHttpException;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Backups\\StoreBackupRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Backups\\RestoreBackupRequest;\n\nclass BackupController extends ClientApiController\n{\n    /**\n     * BackupController constructor.\n     */\n    public function __construct(\n        private DaemonBackupRepository $daemonRepository,\n        private DeleteBackupService $deleteBackupService,\n        private InitiateBackupService $initiateBackupService,\n        private DownloadLinkService $downloadLinkService,\n        private BackupRepository $repository,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Returns all the backups for a given server instance in a paginated\n     * result set.\n     *\n     * @throws AuthorizationException\n     */\n    public function index(Request $request, Server $server): array\n    {\n        if (!$request->user()->can(Permission::ACTION_BACKUP_READ, $server)) {\n            throw new AuthorizationException();\n        }\n\n        $limit = min($request->query('per_page') ?? 20, 50);\n\n        return $this->fractal->collection($server->backups()->paginate($limit))\n            ->transformWith($this->getTransformer(BackupTransformer::class))\n            ->addMeta([\n                'backup_count' => $this->repository->getNonFailedBackups($server)->count(),\n            ])\n            ->toArray();\n    }\n\n    /**\n     * Starts the backup process for a server.\n     *\n     * @throws \\Spatie\\Fractalistic\\Exceptions\\InvalidTransformation\n     * @throws \\Spatie\\Fractalistic\\Exceptions\\NoTransformerSpecified\n     * @throws \\Throwable\n     */\n    public function store(StoreBackupRequest $request, Server $server): array\n    {\n        $action = $this->initiateBackupService\n            ->setIgnoredFiles(explode(PHP_EOL, $request->input('ignored') ?? ''));\n\n        // Only set the lock status if the user even has permission to delete backups,\n        // otherwise ignore this status. This gets a little funky since it isn't clear\n        // how best to allow a user to create a backup that is locked without also preventing\n        // them from just filling up a server with backups that can never be deleted?\n        if ($request->user()->can(Permission::ACTION_BACKUP_DELETE, $server)) {\n            $action->setIsLocked($request->boolean('is_locked'));\n        }\n\n        $backup = Activity::event('server:backup.start')->transaction(function ($log) use ($action, $server, $request) {\n            $server->backups()->lockForUpdate()->count();\n\n            $backup = $action->handle($server, $request->input('name'));\n\n            $log->subject($backup)->property([\n                'name' => $backup->name,\n                'locked' => $request->boolean('is_locked'),\n            ]);\n\n            return $backup;\n        });\n\n        return $this->fractal->item($backup)\n            ->transformWith($this->getTransformer(BackupTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Toggles the lock status of a given backup for a server.\n     *\n     * @throws \\Throwable\n     * @throws AuthorizationException\n     */\n    public function toggleLock(Request $request, Server $server, Backup $backup): array\n    {\n        if (!$request->user()->can(Permission::ACTION_BACKUP_DELETE, $server)) {\n            throw new AuthorizationException();\n        }\n\n        $action = $backup->is_locked ? 'server:backup.unlock' : 'server:backup.lock';\n\n        $backup->update(['is_locked' => !$backup->is_locked]);\n\n        Activity::event($action)->subject($backup)->property('name', $backup->name)->log();\n\n        return $this->fractal->item($backup)\n            ->transformWith($this->getTransformer(BackupTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Returns information about a single backup.\n     *\n     * @throws AuthorizationException\n     */\n    public function view(Request $request, Server $server, Backup $backup): array\n    {\n        if (!$request->user()->can(Permission::ACTION_BACKUP_READ, $server)) {\n            throw new AuthorizationException();\n        }\n\n        return $this->fractal->item($backup)\n            ->transformWith($this->getTransformer(BackupTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Deletes a backup from the panel as well as the remote source where it is currently\n     * being stored.\n     *\n     * @throws \\Throwable\n     */\n    public function delete(Request $request, Server $server, Backup $backup): JsonResponse\n    {\n        if (!$request->user()->can(Permission::ACTION_BACKUP_DELETE, $server)) {\n            throw new AuthorizationException();\n        }\n\n        $this->deleteBackupService->handle($backup);\n\n        Activity::event('server:backup.delete')\n            ->subject($backup)\n            ->property(['name' => $backup->name, 'failed' => !$backup->is_successful])\n            ->log();\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Download the backup for a given server instance. For daemon local files, the file\n     * will be streamed back through the Panel. For AWS S3 files, a signed URL will be generated\n     * which the user is redirected to.\n     *\n     * @throws \\Throwable\n     * @throws AuthorizationException\n     */\n    public function download(Request $request, Server $server, Backup $backup): JsonResponse\n    {\n        if (!$request->user()->can(Permission::ACTION_BACKUP_DOWNLOAD, $server)) {\n            throw new AuthorizationException();\n        }\n\n        if ($backup->disk !== Backup::ADAPTER_AWS_S3 && $backup->disk !== Backup::ADAPTER_WINGS) {\n            throw new BadRequestHttpException('请求的备份引用了未知的磁盘驱动程序类型，因此无法下载。');\n        }\n\n        $url = $this->downloadLinkService->handle($backup, $request->user());\n\n        Activity::event('server:backup.download')->subject($backup)->property('name', $backup->name)->log();\n\n        return new JsonResponse([\n            'object' => 'signed_url',\n            'attributes' => ['url' => $url],\n        ]);\n    }\n\n    /**\n     * Handles restoring a backup by making a request to the Wings instance telling it\n     * to begin the process of finding (or downloading) the backup and unpacking it\n     * over the server files.\n     *\n     * If the \"truncate\" flag is passed through in this request then all the\n     * files that currently exist on the server will be deleted before restoring.\n     * Otherwise, the archive will simply be unpacked over the existing files.\n     *\n     * @throws \\Throwable\n     */\n    public function restore(RestoreBackupRequest $request, Server $server, Backup $backup): JsonResponse\n    {\n        // Cannot restore a backup unless a server is fully installed and not currently\n        // processing a different backup restoration request.\n        if (!is_null($server->status)) {\n            throw new BadRequestHttpException('此服务器处于不允许还原备份的状态。');\n        }\n\n        if (!$backup->is_successful && is_null($backup->completed_at)) {\n            throw new BadRequestHttpException('此时无法还原该备份：未完成或失败。');\n        }\n\n        $log = Activity::event('server:backup.restore')\n            ->subject($backup)\n            ->property(['name' => $backup->name, 'truncate' => $request->input('truncate')]);\n\n        $log->transaction(function () use ($backup, $server, $request) {\n            // If the backup is for an S3 file we need to generate a unique Download link for\n            // it that will allow Wings to actually access the file.\n            if ($backup->disk === Backup::ADAPTER_AWS_S3) {\n                $url = $this->downloadLinkService->handle($backup, $request->user());\n            }\n\n            // Update the status right away for the server so that we know not to allow certain\n            // actions against it via the Panel API.\n            $server->update(['status' => Server::STATUS_RESTORING_BACKUP]);\n\n            $this->daemonRepository->setServer($server)->restore($backup, $url ?? null, $request->input('truncate'));\n        });\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/CommandController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Facades\\Activity;\nuse GuzzleHttp\\Exception\\BadResponseException;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpException;\nuse Pterodactyl\\Repositories\\Wings\\DaemonCommandRepository;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\SendCommandRequest;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass CommandController extends ClientApiController\n{\n    /**\n     * CommandController constructor.\n     */\n    public function __construct(private DaemonCommandRepository $repository)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Send a command to a running server.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function index(SendCommandRequest $request, Server $server): Response\n    {\n        try {\n            $this->repository->setServer($server)->send($request->input('command'));\n        } catch (DaemonConnectionException $exception) {\n            $previous = $exception->getPrevious();\n\n            if ($previous instanceof BadResponseException) {\n                if ($previous->getResponse()->getStatusCode() === Response::HTTP_BAD_GATEWAY) {\n                    throw new HttpException(Response::HTTP_BAD_GATEWAY, '服务器必须在线才能发送命令。', $exception);\n                }\n            }\n\n            throw $exception;\n        }\n\n        Activity::event('server:console.command')->property('command', $request->input('command'))->log();\n\n        return $this->returnNoContent();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/DatabaseController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Services\\Databases\\DatabasePasswordService;\nuse Pterodactyl\\Transformers\\Api\\Client\\DatabaseTransformer;\nuse Pterodactyl\\Services\\Databases\\DatabaseManagementService;\nuse Pterodactyl\\Services\\Databases\\DeployServerDatabaseService;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Databases\\GetDatabasesRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Databases\\StoreDatabaseRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Databases\\DeleteDatabaseRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Databases\\RotatePasswordRequest;\n\nclass DatabaseController extends ClientApiController\n{\n    /**\n     * DatabaseController constructor.\n     */\n    public function __construct(\n        private DeployServerDatabaseService $deployDatabaseService,\n        private DatabaseManagementService $managementService,\n        private DatabasePasswordService $passwordService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Return all the databases that belong to the given server.\n     */\n    public function index(GetDatabasesRequest $request, Server $server): array\n    {\n        return $this->fractal->collection($server->databases)\n            ->transformWith($this->getTransformer(DatabaseTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Create a new database for the given server and return it.\n     *\n     * @throws \\Throwable\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Database\\TooManyDatabasesException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Database\\DatabaseClientFeatureNotEnabledException\n     */\n    public function store(StoreDatabaseRequest $request, Server $server): array\n    {\n        $database = Activity::event('server:database.create')->transaction(function ($log) use ($request, $server) {\n            if ($server->databases()->lockForUpdate()->count() >= $server->database_limit) {\n                throw new DisplayException('Cannot create additional databases on this server: limit has been reached.');\n            }\n\n            $database = $this->deployDatabaseService->handle($server, $request->validated());\n\n            $log->subject($database)->property('name', $database->database);\n\n            return $database;\n        });\n\n        return $this->fractal->item($database)\n            ->parseIncludes(['password'])\n            ->transformWith($this->getTransformer(DatabaseTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Rotates the password for the given server model and returns a fresh instance to\n     * the caller.\n     *\n     * @throws \\Throwable\n     */\n    public function rotatePassword(RotatePasswordRequest $request, Server $server, Database $database): array\n    {\n        Activity::event('server:database.rotate-password')\n            ->subject($database)\n            ->property('name', $database->database)\n            ->transaction(fn () => $this->passwordService->handle($database));\n\n        return $this->fractal->item($database->refresh())\n            ->parseIncludes(['password'])\n            ->transformWith($this->getTransformer(DatabaseTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Removes a database from the server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function delete(DeleteDatabaseRequest $request, Server $server, Database $database): Response\n    {\n        $this->managementService->delete($database);\n\n        Activity::event('server:database.delete')\n            ->subject($database)\n            ->property('name', $database->database)\n            ->log();\n\n        return new Response('', Response::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/FileController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Services\\Nodes\\NodeJWTService;\nuse Pterodactyl\\Repositories\\Wings\\DaemonFileRepository;\nuse Pterodactyl\\Transformers\\Api\\Client\\FileObjectTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\CopyFileRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\PullFileRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\ListFilesRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\ChmodFilesRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\DeleteFileRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\RenameFileRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\CreateFolderRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\CompressFilesRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\DecompressFilesRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\GetFileContentsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\WriteFileContentRequest;\n\nclass FileController extends ClientApiController\n{\n    /**\n     * FileController constructor.\n     */\n    public function __construct(\n        private NodeJWTService $jwtService,\n        private DaemonFileRepository $fileRepository,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Returns a listing of files in a given directory.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException\n     */\n    public function directory(ListFilesRequest $request, Server $server): array\n    {\n        $contents = $this->fileRepository\n            ->setServer($server)\n            ->getDirectory($request->get('directory') ?? '/');\n\n        return $this->fractal->collection($contents)\n            ->transformWith($this->getTransformer(FileObjectTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Return the contents of a specified file for the user.\n     *\n     * @throws \\Throwable\n     */\n    public function contents(GetFileContentsRequest $request, Server $server): Response\n    {\n        $response = $this->fileRepository->setServer($server)->getContent(\n            $request->get('file'),\n            config('pterodactyl.files.max_edit_size')\n        );\n\n        Activity::event('server:file.read')->property('file', $request->get('file'))->log();\n\n        return new Response($response, Response::HTTP_OK, ['Content-Type' => 'text/plain']);\n    }\n\n    /**\n     * Generates a one-time token with a link that the user can use to\n     * download a given file.\n     *\n     * @throws \\Throwable\n     */\n    public function download(GetFileContentsRequest $request, Server $server): array\n    {\n        $token = $this->jwtService\n            ->setExpiresAt(CarbonImmutable::now()->addMinutes(15))\n            ->setUser($request->user())\n            ->setClaims([\n                'file_path' => rawurldecode($request->get('file')),\n                'server_uuid' => $server->uuid,\n            ])\n            ->handle($server->node, $request->user()->id . $server->uuid);\n\n        Activity::event('server:file.download')->property('file', $request->get('file'))->log();\n\n        return [\n            'object' => 'signed_url',\n            'attributes' => [\n                'url' => sprintf(\n                    '%s/download/file?token=%s',\n                    $server->node->getConnectionAddress(),\n                    $token->toString()\n                ),\n            ],\n        ];\n    }\n\n    /**\n     * Writes the contents of the specified file to the server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException\n     */\n    public function write(WriteFileContentRequest $request, Server $server): JsonResponse\n    {\n        $this->fileRepository->setServer($server)->putContent($request->get('file'), $request->getContent());\n\n        Activity::event('server:file.write')->property('file', $request->get('file'))->log();\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Creates a new folder on the server.\n     *\n     * @throws \\Throwable\n     */\n    public function create(CreateFolderRequest $request, Server $server): JsonResponse\n    {\n        $this->fileRepository\n            ->setServer($server)\n            ->createDirectory($request->input('name'), $request->input('root', '/'));\n\n        Activity::event('server:file.create-directory')\n            ->property('name', $request->input('name'))\n            ->property('directory', $request->input('root'))\n            ->log();\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Renames a file on the remote machine.\n     *\n     * @throws \\Throwable\n     */\n    public function rename(RenameFileRequest $request, Server $server): JsonResponse\n    {\n        $this->fileRepository\n            ->setServer($server)\n            ->renameFiles($request->input('root'), $request->input('files'));\n\n        Activity::event('server:file.rename')\n            ->property('directory', $request->input('root'))\n            ->property('files', $request->input('files'))\n            ->log();\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Copies a file on the server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException\n     */\n    public function copy(CopyFileRequest $request, Server $server): JsonResponse\n    {\n        $this->fileRepository\n            ->setServer($server)\n            ->copyFile($request->input('location'));\n\n        Activity::event('server:file.copy')->property('file', $request->input('location'))->log();\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * @throws \\Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException\n     */\n    public function compress(CompressFilesRequest $request, Server $server): array\n    {\n        $file = $this->fileRepository->setServer($server)->compressFiles(\n            $request->input('root'),\n            $request->input('files')\n        );\n\n        Activity::event('server:file.compress')\n            ->property('directory', $request->input('root'))\n            ->property('files', $request->input('files'))\n            ->log();\n\n        return $this->fractal->item($file)\n            ->transformWith($this->getTransformer(FileObjectTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * @throws \\Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException\n     */\n    public function decompress(DecompressFilesRequest $request, Server $server): JsonResponse\n    {\n        set_time_limit(10);\n\n        $this->fileRepository->setServer($server)->decompressFile(\n            $request->input('root'),\n            $request->input('file')\n        );\n\n        Activity::event('server:file.decompress')\n            ->property('directory', $request->input('root'))\n            ->property('files', $request->input('file'))\n            ->log();\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Deletes files or folders for the server in the given root directory.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException\n     */\n    public function delete(DeleteFileRequest $request, Server $server): JsonResponse\n    {\n        $this->fileRepository->setServer($server)->deleteFiles(\n            $request->input('root'),\n            $request->input('files')\n        );\n\n        Activity::event('server:file.delete')\n            ->property('directory', $request->input('root'))\n            ->property('files', $request->input('files'))\n            ->log();\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Updates file permissions for file(s) in the given root directory.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException\n     */\n    public function chmod(ChmodFilesRequest $request, Server $server): JsonResponse\n    {\n        $this->fileRepository->setServer($server)->chmodFiles(\n            $request->input('root'),\n            $request->input('files')\n        );\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Requests that a file be downloaded from a remote location by Wings.\n     *\n     * @throws \\Throwable\n     */\n    public function pull(PullFileRequest $request, Server $server): JsonResponse\n    {\n        $this->fileRepository->setServer($server)->pull(\n            $request->input('url'),\n            $request->input('directory'),\n            $request->safe(['filename', 'use_header', 'foreground'])\n        );\n\n        Activity::event('server:file.pull')\n            ->property('directory', $request->input('directory'))\n            ->property('url', $request->input('url'))\n            ->log();\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/FileUploadController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Carbon\\CarbonImmutable;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Services\\Nodes\\NodeJWTService;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files\\UploadFileRequest;\n\nclass FileUploadController extends ClientApiController\n{\n    /**\n     * FileUploadController constructor.\n     */\n    public function __construct(\n        private NodeJWTService $jwtService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Returns an url where files can be uploaded to.\n     */\n    public function __invoke(UploadFileRequest $request, Server $server): JsonResponse\n    {\n        return new JsonResponse([\n            'object' => 'signed_url',\n            'attributes' => [\n                'url' => $this->getUploadUrl($server, $request->user()),\n            ],\n        ]);\n    }\n\n    /**\n     * Returns an url where files can be uploaded to.\n     */\n    protected function getUploadUrl(Server $server, User $user): string\n    {\n        $token = $this->jwtService\n            ->setExpiresAt(CarbonImmutable::now()->addMinutes(15))\n            ->setUser($user)\n            ->setClaims(['server_uuid' => $server->uuid])\n            ->handle($server->node, $user->id . $server->uuid);\n\n        return sprintf(\n            '%s/upload/file?token=%s',\n            $server->node->getConnectionAddress(),\n            $token->toString()\n        );\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/NetworkAllocationController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Models\\Allocation;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerRepository;\nuse Pterodactyl\\Transformers\\Api\\Client\\AllocationTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Pterodactyl\\Services\\Allocations\\FindAssignableAllocationService;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Network\\GetNetworkRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Network\\NewAllocationRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Network\\DeleteAllocationRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Network\\UpdateAllocationRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Network\\SetPrimaryAllocationRequest;\n\nclass NetworkAllocationController extends ClientApiController\n{\n    /**\n     * NetworkAllocationController constructor.\n     */\n    public function __construct(\n        protected readonly ConnectionInterface $connection,\n        private FindAssignableAllocationService $assignableAllocationService,\n        private ServerRepository $serverRepository,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Lists all the allocations available to a server and whether\n     * they are currently assigned as the primary for this server.\n     */\n    public function index(GetNetworkRequest $request, Server $server): array\n    {\n        return $this->fractal->collection($server->allocations)\n            ->transformWith($this->getTransformer(AllocationTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Set the primary allocation for a server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(UpdateAllocationRequest $request, Server $server, Allocation $allocation): array\n    {\n        $original = $allocation->notes;\n\n        $allocation->forceFill(['notes' => $request->input('notes')])->save();\n\n        if ($original !== $allocation->notes) {\n            Activity::event('server:allocation.notes')\n                ->subject($allocation)\n                ->property(['allocation' => $allocation->toString(), 'old' => $original, 'new' => $allocation->notes])\n                ->log();\n        }\n\n        return $this->fractal->item($allocation)\n            ->transformWith($this->getTransformer(AllocationTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Set the primary allocation for a server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function setPrimary(SetPrimaryAllocationRequest $request, Server $server, Allocation $allocation): array\n    {\n        $this->serverRepository->update($server->id, ['allocation_id' => $allocation->id]);\n\n        Activity::event('server:allocation.primary')\n            ->subject($allocation)\n            ->property('allocation', $allocation->toString())\n            ->log();\n\n        return $this->fractal->item($allocation)\n            ->transformWith($this->getTransformer(AllocationTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Set the notes for the allocation for a server.\n     *s.\n     *\n     * @throws DisplayException\n     */\n    public function store(NewAllocationRequest $request, Server $server): array\n    {\n        $count = (int) $request->input('count', 1);\n        $consecutiveEnabled = (bool) config('pterodactyl.client_features.allocations.consecutive_enabled', false);\n\n        if ($count > 1 && $consecutiveEnabled) {\n            $allocations = Activity::event('server:allocation.create')->transaction(function ($log) use ($server, $count) {\n                if ($server->allocations()->lockForUpdate()->count() + $count > $server->allocation_limit) {\n                    throw new DisplayException('无法为此服务器分配更多端口：已达到分配限制。');\n                }\n\n                $allocations = $this->assignableAllocationService->handleConsecutive($server, $count);\n\n                $ports = implode(', ', array_map(fn ($a) => $a->toString(), $allocations));\n                $log->property('allocation', $ports);\n\n                return $allocations;\n            });\n\n            return $this->fractal->collection($allocations)\n                ->transformWith($this->getTransformer(AllocationTransformer::class))\n                ->toArray();\n        }\n\n        $allocation = Activity::event('server:allocation.create')->transaction(function ($log) use ($server) {\n            if ($server->allocations()->lockForUpdate()->count() >= $server->allocation_limit) {\n                throw new DisplayException('无法为此服务器分配更多端口：已达到分配限制。');\n            }\n\n            $allocation = $this->assignableAllocationService->handle($server);\n\n            $log->subject($allocation)->property('allocation', $allocation->toString());\n\n            return $allocation;\n        });\n\n        return $this->fractal->item($allocation)\n            ->transformWith($this->getTransformer(AllocationTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Delete an allocation from a server.\n     *\n     * @throws DisplayException\n     */\n    public function delete(DeleteAllocationRequest $request, Server $server, Allocation $allocation): JsonResponse\n    {\n        // Don't allow the deletion of allocations if the server does not have an\n        // allocation limit set.\n        if (empty($server->allocation_limit)) {\n            throw new DisplayException('您无法删除此服务器的网络分配：未设置分配限制。');\n        }\n\n        if ($allocation->id === $server->allocation_id) {\n            throw new DisplayException('您不能删除此服务器的首选分配。');\n        }\n\n        Allocation::query()->where('id', $allocation->id)->update([\n            'notes' => null,\n            'server_id' => null,\n        ]);\n\n        Activity::event('server:allocation.delete')\n            ->subject($allocation)\n            ->property('allocation', $allocation->toString())\n            ->log();\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/PowerController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Repositories\\Wings\\DaemonPowerRepository;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\SendPowerRequest;\n\nclass PowerController extends ClientApiController\n{\n    /**\n     * PowerController constructor.\n     */\n    public function __construct(private DaemonPowerRepository $repository)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Send a power action to a server.\n     */\n    public function index(SendPowerRequest $request, Server $server): Response\n    {\n        $this->repository->setServer($server)->send(\n            $request->input('signal')\n        );\n\n        Activity::event(strtolower(\"server:power.{$request->input('signal')}\"))->log();\n\n        return $this->returnNoContent();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/ResourceUtilizationController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Carbon\\Carbon;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Cache\\Repository;\nuse Pterodactyl\\Transformers\\Api\\Client\\StatsTransformer;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\GetServerRequest;\n\nclass ResourceUtilizationController extends ClientApiController\n{\n    /**\n     * ResourceUtilizationController constructor.\n     */\n    public function __construct(private Repository $cache, private DaemonServerRepository $repository)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Return the current resource utilization for a server. This value is cached for up to\n     * 20 seconds at a time to ensure that repeated requests to this endpoint do not cause\n     * a flood of unnecessary API calls.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException\n     */\n    public function __invoke(GetServerRequest $request, Server $server): array\n    {\n        $key = \"resources:$server->uuid\";\n        $stats = $this->cache->remember($key, Carbon::now()->addSeconds(20), function () use ($server) {\n            return $this->repository->setServer($server)->getDetails();\n        });\n\n        return $this->fractal->item($stats)\n            ->transformWith($this->getTransformer(StatsTransformer::class))\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/ScheduleController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Carbon\\Carbon;\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Schedule;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Helpers\\Utilities;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Repositories\\Eloquent\\ScheduleRepository;\nuse Pterodactyl\\Services\\Schedules\\ProcessScheduleService;\nuse Pterodactyl\\Transformers\\Api\\Client\\ScheduleTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Symfony\\Component\\HttpKernel\\Exception\\NotFoundHttpException;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules\\ViewScheduleRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules\\StoreScheduleRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules\\DeleteScheduleRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules\\UpdateScheduleRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules\\TriggerScheduleRequest;\n\nclass ScheduleController extends ClientApiController\n{\n    /**\n     * ScheduleController constructor.\n     */\n    public function __construct(private ScheduleRepository $repository, private ProcessScheduleService $service)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Returns all the schedules belonging to a given server.\n     */\n    public function index(ViewScheduleRequest $request, Server $server): array\n    {\n        $schedules = $server->schedules->loadMissing('tasks');\n\n        return $this->fractal->collection($schedules)\n            ->transformWith($this->getTransformer(ScheduleTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Store a new schedule for a server.\n     *\n     * @throws DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function store(StoreScheduleRequest $request, Server $server): array\n    {\n        /** @var Schedule $model */\n        $model = $this->repository->create([\n            'server_id' => $server->id,\n            'name' => $request->input('name'),\n            'cron_day_of_week' => $request->input('day_of_week'),\n            'cron_month' => $request->input('month'),\n            'cron_day_of_month' => $request->input('day_of_month'),\n            'cron_hour' => $request->input('hour'),\n            'cron_minute' => $request->input('minute'),\n            'is_active' => (bool) $request->input('is_active'),\n            'only_when_online' => (bool) $request->input('only_when_online'),\n            'next_run_at' => $this->getNextRunAt($request),\n        ]);\n\n        Activity::event('server:schedule.create')\n            ->subject($model)\n            ->property('name', $model->name)\n            ->log();\n\n        return $this->fractal->item($model)\n            ->transformWith($this->getTransformer(ScheduleTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Returns a specific schedule for the server.\n     */\n    public function view(ViewScheduleRequest $request, Server $server, Schedule $schedule): array\n    {\n        if ($schedule->server_id !== $server->id) {\n            throw new NotFoundHttpException();\n        }\n\n        $schedule->loadMissing('tasks');\n\n        return $this->fractal->item($schedule)\n            ->transformWith($this->getTransformer(ScheduleTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Updates a given schedule with the new data provided.\n     *\n     * @throws DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(UpdateScheduleRequest $request, Server $server, Schedule $schedule): array\n    {\n        $active = (bool) $request->input('is_active');\n\n        $data = [\n            'name' => $request->input('name'),\n            'cron_day_of_week' => $request->input('day_of_week'),\n            'cron_month' => $request->input('month'),\n            'cron_day_of_month' => $request->input('day_of_month'),\n            'cron_hour' => $request->input('hour'),\n            'cron_minute' => $request->input('minute'),\n            'is_active' => $active,\n            'only_when_online' => (bool) $request->input('only_when_online'),\n            'next_run_at' => $this->getNextRunAt($request),\n        ];\n\n        // Toggle the processing state of the scheduled task when it is enabled or disabled so that an\n        // invalid state can be reset without manual database intervention.\n        //\n        // @see https://github.com/pterodactyl/panel/issues/2425\n        if ($schedule->is_active !== $active) {\n            $data['is_processing'] = false;\n        }\n\n        $this->repository->update($schedule->id, $data);\n\n        Activity::event('server:schedule.update')\n            ->subject($schedule)\n            ->property(['name' => $schedule->name, 'active' => $active])\n            ->log();\n\n        return $this->fractal->item($schedule->refresh())\n            ->transformWith($this->getTransformer(ScheduleTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Executes a given schedule immediately rather than waiting on it's normally scheduled time\n     * to pass. This does not care about the schedule state.\n     *\n     * @throws \\Throwable\n     */\n    public function execute(TriggerScheduleRequest $request, Server $server, Schedule $schedule): JsonResponse\n    {\n        $this->service->handle($schedule, true);\n\n        Activity::event('server:schedule.execute')->subject($schedule)->property('name', $schedule->name)->log();\n\n        return new JsonResponse([], JsonResponse::HTTP_ACCEPTED);\n    }\n\n    /**\n     * Deletes a schedule and it's associated tasks.\n     */\n    public function delete(DeleteScheduleRequest $request, Server $server, Schedule $schedule): JsonResponse\n    {\n        $this->repository->delete($schedule->id);\n\n        Activity::event('server:schedule.delete')->subject($schedule)->property('name', $schedule->name)->log();\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Get the next run timestamp based on the cron data provided.\n     *\n     * @throws DisplayException\n     */\n    protected function getNextRunAt(Request $request): Carbon\n    {\n        try {\n            return Utilities::getScheduleNextRunDate(\n                $request->input('minute'),\n                $request->input('hour'),\n                $request->input('day_of_month'),\n                $request->input('month'),\n                $request->input('day_of_week')\n            );\n        } catch (\\Exception $exception) {\n            throw new DisplayException('提供的 cron 数据不是有效的表达式。');\n        }\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/ScheduleTaskController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Pterodactyl\\Models\\Task;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Schedule;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Repositories\\Eloquent\\TaskRepository;\nuse Pterodactyl\\Exceptions\\Http\\HttpForbiddenException;\nuse Pterodactyl\\Transformers\\Api\\Client\\TaskTransformer;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Pterodactyl\\Exceptions\\Service\\ServiceLimitExceededException;\nuse Symfony\\Component\\HttpKernel\\Exception\\NotFoundHttpException;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules\\StoreTaskRequest;\n\nclass ScheduleTaskController extends ClientApiController\n{\n    /**\n     * ScheduleTaskController constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private TaskRepository $repository,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Create a new task for a given schedule and store it in the database.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws ServiceLimitExceededException\n     */\n    public function store(StoreTaskRequest $request, Server $server, Schedule $schedule): array\n    {\n        $limit = config('pterodactyl.client_features.schedules.per_schedule_task_limit', 10);\n        if ($schedule->tasks()->count() >= $limit) {\n            throw new ServiceLimitExceededException(\"Schedules may not have more than $limit tasks associated with them. Creating this task would put this schedule over the limit.\");\n        }\n\n        if ($server->backup_limit === 0 && $request->action === 'backup') {\n            throw new HttpForbiddenException('当服务器的备份限制设置为 0 时，则不能创建备份任务。');\n        }\n\n        /** @var Task|null $lastTask */\n        $lastTask = $schedule->tasks()->orderByDesc('sequence_id')->first();\n\n        /** @var Task $task */\n        $task = $this->connection->transaction(function () use ($request, $schedule, $lastTask) {\n            $sequenceId = ($lastTask->sequence_id ?? 0) + 1;\n            $requestSequenceId = $request->integer('sequence_id', $sequenceId);\n\n            // Ensure that the sequence id is at least 1.\n            if ($requestSequenceId < 1) {\n                $requestSequenceId = 1;\n            }\n\n            // If the sequence id from the request is greater than or equal to the next available\n            // sequence id, we don't need to do anything special.  Otherwise, we need to update\n            // the sequence id of all tasks that are greater than or equal to the request sequence\n            // id to be one greater than the current value.\n            if ($requestSequenceId < $sequenceId) {\n                $schedule->tasks()\n                    ->where('sequence_id', '>=', $requestSequenceId)\n                    ->increment('sequence_id');\n                $sequenceId = $requestSequenceId;\n            }\n\n            return $this->repository->create([\n                'schedule_id' => $schedule->id,\n                'sequence_id' => $sequenceId,\n                'action' => $request->input('action'),\n                'payload' => $request->input('payload') ?? '',\n                'time_offset' => $request->input('time_offset'),\n                'continue_on_failure' => $request->boolean('continue_on_failure'),\n            ]);\n        });\n\n        Activity::event('server:task.create')\n            ->subject($schedule, $task)\n            ->property(['name' => $schedule->name, 'action' => $task->action, 'payload' => $task->payload])\n            ->log();\n\n        return $this->fractal->item($task)\n            ->transformWith($this->getTransformer(TaskTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Updates a given task for a server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(StoreTaskRequest $request, Server $server, Schedule $schedule, Task $task): array\n    {\n        if ($schedule->id !== $task->schedule_id || $server->id !== $schedule->server_id) {\n            throw new NotFoundHttpException();\n        }\n\n        if ($server->backup_limit === 0 && $request->action === 'backup') {\n            throw new HttpForbiddenException('当服务器的备份限制设置为 0 时，则不能创建备份任务。');\n        }\n\n        $this->connection->transaction(function () use ($request, $schedule, $task) {\n            $sequenceId = $request->integer('sequence_id', $task->sequence_id);\n            // Ensure that the sequence id is at least 1.\n            if ($sequenceId < 1) {\n                $sequenceId = 1;\n            }\n\n            // Shift all other tasks in the schedule up or down to make room for the new task.\n            if ($sequenceId < $task->sequence_id) {\n                $schedule->tasks()\n                    ->where('sequence_id', '>=', $sequenceId)\n                    ->where('sequence_id', '<', $task->sequence_id)\n                    ->increment('sequence_id');\n            } elseif ($sequenceId > $task->sequence_id) {\n                $schedule->tasks()\n                    ->where('sequence_id', '>', $task->sequence_id)\n                    ->where('sequence_id', '<=', $sequenceId)\n                    ->decrement('sequence_id');\n            }\n\n            $this->repository->update($task->id, [\n                'sequence_id' => $sequenceId,\n                'action' => $request->input('action'),\n                'payload' => $request->input('payload') ?? '',\n                'time_offset' => $request->input('time_offset'),\n                'continue_on_failure' => $request->boolean('continue_on_failure'),\n            ]);\n        });\n\n        Activity::event('server:task.update')\n            ->subject($schedule, $task)\n            ->property(['name' => $schedule->name, 'action' => $task->action, 'payload' => $task->payload])\n            ->log();\n\n        return $this->fractal->item($task->refresh())\n            ->transformWith($this->getTransformer(TaskTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Delete a given task for a schedule. If there are subsequent tasks stored in the database\n     * for this schedule their sequence IDs are decremented properly.\n     *\n     * @throws \\Exception\n     */\n    public function delete(ClientApiRequest $request, Server $server, Schedule $schedule, Task $task): JsonResponse\n    {\n        if ($task->schedule_id !== $schedule->id || $schedule->server_id !== $server->id) {\n            throw new NotFoundHttpException();\n        }\n\n        if (!$request->user()->can(Permission::ACTION_SCHEDULE_UPDATE, $server)) {\n            throw new HttpForbiddenException('您无权执行此操作。');\n        }\n\n        $schedule->tasks()\n            ->where('sequence_id', '>', $task->sequence_id)\n            ->decrement('sequence_id');\n        $task->delete();\n\n        Activity::event('server:task.delete')->subject($schedule, $task)->property('name', $schedule->name)->log();\n\n        return new JsonResponse(null, Response::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/ServerController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Transformers\\Api\\Client\\ServerTransformer;\nuse Pterodactyl\\Services\\Servers\\GetUserPermissionsService;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\GetServerRequest;\n\nclass ServerController extends ClientApiController\n{\n    /**\n     * ServerController constructor.\n     */\n    public function __construct(private GetUserPermissionsService $permissionsService)\n    {\n        parent::__construct();\n    }\n\n    /**\n     * Transform an individual server into a response that can be consumed by a\n     * client using the API.\n     */\n    public function index(GetServerRequest $request, Server $server): array\n    {\n        return $this->fractal->item($server)\n            ->transformWith($this->getTransformer(ServerTransformer::class))\n            ->addMeta([\n                'is_server_owner' => $request->user()->id === $server->owner_id,\n                'user_permissions' => $this->permissionsService->handle($server, $request->user()),\n            ])\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/SettingsController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerRepository;\nuse Pterodactyl\\Services\\Servers\\ReinstallServerService;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Symfony\\Component\\HttpKernel\\Exception\\BadRequestHttpException;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Settings\\RenameServerRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Settings\\SetDockerImageRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Settings\\ReinstallServerRequest;\n\nclass SettingsController extends ClientApiController\n{\n    /**\n     * SettingsController constructor.\n     */\n    public function __construct(\n        private ServerRepository $repository,\n        private ReinstallServerService $reinstallServerService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Renames a server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function rename(RenameServerRequest $request, Server $server): JsonResponse\n    {\n        $name = $request->input('name');\n        $description = $request->has('description') ? (string) $request->input('description') : $server->description;\n        $this->repository->update($server->id, [\n            'name' => $name,\n            'description' => $description,\n        ]);\n\n        if ($server->name !== $name) {\n            Activity::event('server:settings.rename')\n                ->property(['old' => $server->name, 'new' => $name])\n                ->log();\n        }\n\n        if ($server->description !== $description) {\n            Activity::event('server:settings.description')\n                ->property(['old' => $server->description, 'new' => $description])\n                ->log();\n        }\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Reinstalls the server on the daemon.\n     *\n     * @throws \\Throwable\n     */\n    public function reinstall(ReinstallServerRequest $request, Server $server): JsonResponse\n    {\n        $this->reinstallServerService->handle($server);\n\n        Activity::event('server:reinstall')->log();\n\n        return new JsonResponse([], Response::HTTP_ACCEPTED);\n    }\n\n    /**\n     * Changes the Docker image in use by the server.\n     *\n     * @throws \\Throwable\n     */\n    public function dockerImage(SetDockerImageRequest $request, Server $server): JsonResponse\n    {\n        if (!in_array($server->image, array_values($server->egg->docker_images))) {\n            throw new BadRequestHttpException('此服务器的 Docker 镜像已由管理员手动设置，无法更新。');\n        }\n\n        $original = $server->image;\n        $server->forceFill(['image' => $request->input('docker_image')])->saveOrFail();\n\n        if ($original !== $server->image) {\n            Activity::event('server:startup.image')\n                ->property(['old' => $original, 'new' => $request->input('docker_image')])\n                ->log();\n        }\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/StartupController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\Nest;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Services\\Servers\\StartupCommandService;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerVariableRepository;\nuse Pterodactyl\\Transformers\\Api\\Client\\EggVariableTransformer;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Symfony\\Component\\HttpKernel\\Exception\\BadRequestHttpException;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Startup\\UpdateEggRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Startup\\GetStartupRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Startup\\UpdateStartupVariableRequest;\n\nclass StartupController extends ClientApiController\n{\n    /**\n     * StartupController constructor.\n     */\n    public function __construct(\n        private StartupCommandService $startupCommandService,\n        private ServerVariableRepository $repository,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Returns the startup information for the server including all the variables.\n     */\n    public function index(GetStartupRequest $request, Server $server): array\n    {\n        $startup = $this->startupCommandService->handle($server);\n\n        $meta = [\n            'startup_command' => $startup,\n            'docker_images' => $server->egg->docker_images,\n            'raw_startup_command' => $server->startup,\n        ];\n\n        // Include nests and eggs for switching if the global feature is enabled\n        // and the user has the egg-change permission.\n        $eggChangeMode = config('pterodactyl.client_features.egg_change.mode', 'disabled');\n        if (\n            $eggChangeMode !== 'disabled'\n            && $request->user()->can('startup.egg-change', $server)\n        ) {\n            $meta['egg_change_mode'] = $eggChangeMode;\n            $meta['nests'] = $this->buildNestsList();\n            $meta['current_egg_id'] = $server->egg_id;\n            $meta['current_nest_id'] = $server->nest_id;\n        }\n\n        return $this->fractal->collection(\n            $server->variables()->where('user_viewable', true)->get()\n        )\n            ->transformWith($this->getTransformer(EggVariableTransformer::class))\n            ->addMeta($meta)\n            ->toArray();\n    }\n\n    /**\n     * Updates a single variable for a server.\n     *\n     * @throws \\Illuminate\\Validation\\ValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(UpdateStartupVariableRequest $request, Server $server): array\n    {\n        $variable = $server->variables()->where('env_variable', $request->input('key'))->first();\n\n        if (is_null($variable) || !$variable->user_viewable) {\n            throw new BadRequestHttpException('您试图编辑不存在的环境变量。');\n        } elseif (!$variable->user_editable) {\n            throw new BadRequestHttpException('您试图编辑的环境变量是只读的。');\n        }\n\n        $original = $variable->server_value;\n\n        // Revalidate the variable value using the egg variable specific validation rules for it.\n        $this->validate($request, ['value' => $variable->rules]);\n\n        $this->repository->updateOrCreate([\n            'server_id' => $server->id,\n            'variable_id' => $variable->id,\n        ], [\n            'variable_value' => $request->input('value') ?? '',\n        ]);\n\n        $variable = $variable->refresh();\n        $variable->server_value = $request->input('value');\n\n        $startup = $this->startupCommandService->handle($server);\n\n        if ($original !== $request->input('value')) {\n            Activity::event('server:startup.edit')\n                ->subject($variable)\n                ->property([\n                    'variable' => $variable->env_variable,\n                    'old' => $original,\n                    'new' => $request->input('value') ?? '',\n                ])\n                ->log();\n        }\n\n        return $this->fractal->item($variable)\n            ->transformWith($this->getTransformer(EggVariableTransformer::class))\n            ->addMeta([\n                'startup_command' => $startup,\n                'raw_startup_command' => $server->startup,\n            ])\n            ->toArray();\n    }\n\n    /**\n     * Changes the egg (preset) for a server.\n     *\n     * @throws \\Throwable\n     */\n    public function updateEgg(UpdateEggRequest $request, Server $server): array\n    {\n        if (config('pterodactyl.client_features.egg_change.mode', 'disabled') === 'disabled') {\n            throw new BadRequestHttpException('此面板未启用前台切换预设功能。');\n        }\n\n        /** @var Egg $egg */\n        $egg = Egg::query()->findOrFail($request->input('egg_id'));\n\n        $originalEggId = $server->egg_id;\n        $server->loadMissing('egg');\n        $originalEggName = $server->egg?->name ?? (string) $originalEggId;\n\n        $server->forceFill([\n            'egg_id' => $egg->id,\n            'nest_id' => $egg->nest_id,\n            'startup' => $egg->startup,\n        ])->saveOrFail();\n\n        if ($originalEggId !== $egg->id) {\n            Activity::event('server:startup.egg-change')\n                ->property(['old' => $originalEggName, 'new' => $egg->name])\n                ->log();\n        }\n\n        // Reload the egg relationship after updating\n        $server->load('egg');\n\n        $startup = $this->startupCommandService->handle($server);\n\n        return $this->fractal->collection(\n            $server->variables()->where('user_viewable', true)->get()\n        )\n            ->transformWith($this->getTransformer(EggVariableTransformer::class))\n            ->addMeta([\n                'startup_command' => $startup,\n                'docker_images' => $server->egg->docker_images,\n                'raw_startup_command' => $server->startup,\n                'egg_change_mode' => config('pterodactyl.client_features.egg_change.mode', 'disabled'),\n                'nests' => $this->buildNestsList(),\n                'current_egg_id' => $server->egg_id,\n                'current_nest_id' => $server->nest_id,\n            ])\n            ->toArray();\n    }\n\n    /**\n     * Build the list of nests and their eggs for the egg-change feature.\n     */\n    private function buildNestsList(): array\n    {\n        return Nest::query()->with('eggs:id,nest_id,name')->get(['id', 'name'])\n            ->map(function (Nest $nest) {\n                return [\n                    'id' => $nest->id,\n                    'name' => $nest->name,\n                    'eggs' => $nest->eggs->map(function (Egg $egg) {\n                        return ['id' => $egg->id, 'name' => $egg->name];\n                    })->values()->toArray(),\n                ];\n            })->values()->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/SubuserController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Jobs\\RevokeSftpAccessJob;\nuse Pterodactyl\\Repositories\\Eloquent\\SubuserRepository;\nuse Pterodactyl\\Services\\Subusers\\SubuserCreationService;\nuse Pterodactyl\\Transformers\\Api\\Client\\SubuserTransformer;\nuse Pterodactyl\\Repositories\\Wings\\DaemonRevocationRepository;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Subusers\\GetSubuserRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Subusers\\StoreSubuserRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Subusers\\DeleteSubuserRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Subusers\\UpdateSubuserRequest;\n\nclass SubuserController extends ClientApiController\n{\n    /**\n     * SubuserController constructor.\n     */\n    public function __construct(\n        private SubuserRepository $repository,\n        private SubuserCreationService $creationService,\n        private DaemonRevocationRepository $revocationRepository,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Return the users associated with this server instance.\n     */\n    public function index(GetSubuserRequest $request, Server $server): array\n    {\n        return $this->fractal->collection($server->subusers)\n            ->transformWith($this->getTransformer(SubuserTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Returns a single subuser associated with this server instance.\n     */\n    public function view(GetSubuserRequest $request): array\n    {\n        $subuser = $request->attributes->get('subuser');\n\n        return $this->fractal->item($subuser)\n            ->transformWith($this->getTransformer(SubuserTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Create a new subuser for the given server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Subuser\\ServerSubuserExistsException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Subuser\\UserIsServerOwnerException\n     * @throws \\Throwable\n     */\n    public function store(StoreSubuserRequest $request, Server $server): array\n    {\n        $response = $this->creationService->handle(\n            $server,\n            $request->input('email'),\n            $this->getDefaultPermissions($request)\n        );\n\n        Activity::event('server:subuser.create')\n            ->subject($response->user)\n            ->property(['email' => $request->input('email'), 'permissions' => $this->getDefaultPermissions($request)])\n            ->log();\n\n        return $this->fractal->item($response)\n            ->transformWith($this->getTransformer(SubuserTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Update a given subuser in the system for the server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function update(UpdateSubuserRequest $request, Server $server): array\n    {\n        /** @var \\Pterodactyl\\Models\\Subuser $subuser */\n        $subuser = $request->attributes->get('subuser');\n\n        $permissions = $this->getDefaultPermissions($request);\n        $current = $subuser->permissions;\n\n        sort($permissions);\n        sort($current);\n\n        $log = Activity::event('server:subuser.update')\n            ->subject($subuser->user)\n            ->property([\n                'email' => $subuser->user->email,\n                'old' => $current,\n                'new' => $permissions,\n                'revoked' => true,\n            ]);\n\n        // Only update the database and hit up the Wings instance to invalidate JTI's if the permissions\n        // have actually changed for the user.\n        if ($permissions !== $current) {\n            $log->transaction(function () use ($request, $subuser, $server) {\n                $this->repository->update($subuser->id, [\n                    'permissions' => $this->getDefaultPermissions($request),\n                ]);\n\n                RevokeSftpAccessJob::dispatch($subuser->user->uuid, $server);\n            });\n        }\n\n        $log->reset();\n\n        return $this->fractal->item($subuser->refresh())\n            ->transformWith($this->getTransformer(SubuserTransformer::class))\n            ->toArray();\n    }\n\n    /**\n     * Removes a subusers from a server's assignment.\n     */\n    public function delete(DeleteSubuserRequest $request, Server $server): JsonResponse\n    {\n        /** @var \\Pterodactyl\\Models\\Subuser $subuser */\n        $subuser = $request->attributes->get('subuser');\n\n        $log = Activity::event('server:subuser.delete')\n            ->subject($subuser->user)\n            ->property('email', $subuser->user->email)\n            ->property('revoked', true);\n\n        $log->transaction(function () use ($server, $subuser) {\n            $subuser->delete();\n\n            RevokeSftpAccessJob::dispatch($subuser->user->uuid, $server);\n        });\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Returns the default permissions for subusers and parses out any permissions\n     * that were passed that do not also exist in the internally tracked list of\n     * permissions.\n     */\n    protected function getDefaultPermissions(Request $request): array\n    {\n        $allowed = Permission::permissions()\n            ->map(function ($value, $prefix) {\n                return array_map(function ($value) use ($prefix) {\n                    return \"$prefix.$value\";\n                }, array_keys($value['keys']));\n            })\n            ->flatten()\n            ->all();\n\n        $cleaned = array_intersect($request->input('permissions') ?? [], $allowed);\n\n        return array_unique(array_merge($cleaned, [Permission::ACTION_WEBSOCKET_CONNECT]));\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/Servers/WebsocketController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers;\n\nuse Carbon\\CarbonImmutable;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Services\\Nodes\\NodeJWTService;\nuse Pterodactyl\\Exceptions\\Http\\HttpForbiddenException;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Pterodactyl\\Services\\Servers\\GetUserPermissionsService;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientApiController;\n\nclass WebsocketController extends ClientApiController\n{\n    /**\n     * WebsocketController constructor.\n     */\n    public function __construct(\n        private NodeJWTService $jwtService,\n        private GetUserPermissionsService $permissionsService,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Generates a one-time token that is sent along in every websocket call to the Daemon.\n     * This is a signed JWT that the Daemon then uses to verify the user's identity, and\n     * allows us to continually renew this token and avoid users maintaining sessions wrongly,\n     * as well as ensure that user's only perform actions they're allowed to.\n     */\n    public function __invoke(ClientApiRequest $request, Server $server): JsonResponse\n    {\n        $user = $request->user();\n        if ($user->cannot(Permission::ACTION_WEBSOCKET_CONNECT, $server)) {\n            throw new HttpForbiddenException('您无权连接到此服务器的 websocket。');\n        }\n\n        $permissions = $this->permissionsService->handle($server, $user);\n\n        $node = $server->node;\n        if (!is_null($server->transfer)) {\n            // Check if the user has permissions to receive transfer logs.\n            if (!in_array('admin.websocket.transfer', $permissions)) {\n                throw new HttpForbiddenException('您无权查看服务器传输日志。');\n            }\n\n            // Redirect the websocket request to the new node if the server has been archived.\n            if ($server->transfer->archived) {\n                $node = $server->transfer->newNode;\n            }\n        }\n\n        $token = $this->jwtService\n            ->setExpiresAt(CarbonImmutable::now()->addMinutes(10))\n            ->setUser($request->user())\n            ->setClaims([\n                'server_uuid' => $server->uuid,\n                'permissions' => $permissions,\n            ])\n            ->handle($node, $user->id . $server->uuid);\n\n        $socket = str_replace(['https://', 'http://'], ['wss://', 'ws://'], $node->getConnectionAddress());\n\n        return new JsonResponse([\n            'data' => [\n                'token' => $token->toString(),\n                'socket' => $socket . sprintf('/api/servers/%s/ws', $server->uuid),\n            ],\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Client/TwoFactorController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Client;\n\nuse Carbon\\Carbon;\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Http\\Response;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Services\\Users\\TwoFactorSetupService;\nuse Pterodactyl\\Services\\Users\\ToggleTwoFactorService;\nuse Illuminate\\Contracts\\Validation\\Factory as ValidationFactory;\nuse Symfony\\Component\\HttpKernel\\Exception\\BadRequestHttpException;\n\nclass TwoFactorController extends ClientApiController\n{\n    /**\n     * TwoFactorController constructor.\n     */\n    public function __construct(\n        private ToggleTwoFactorService $toggleTwoFactorService,\n        private TwoFactorSetupService $setupService,\n        private ValidationFactory $validation,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Returns two-factor token credentials that allow a user to configure\n     * it on their account. If two-factor is already enabled this endpoint\n     * will return a 400 error.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function index(Request $request): JsonResponse\n    {\n        if ($request->user()->use_totp) {\n            throw new BadRequestHttpException('此帐户已启用动态口令认证。');\n        }\n\n        return new JsonResponse([\n            'data' => $this->setupService->handle($request->user()),\n        ]);\n    }\n\n    /**\n     * Updates a user's account to have two-factor enabled.\n     *\n     * @throws \\Throwable\n     * @throws \\Illuminate\\Validation\\ValidationException\n     */\n    public function store(Request $request): JsonResponse\n    {\n        $validator = $this->validation->make($request->all(), [\n            'code' => ['required', 'string', 'size:6'],\n            'password' => ['required', 'string'],\n        ]);\n\n        $data = $validator->validate();\n        if (!password_verify($data['password'], $request->user()->password)) {\n            throw new BadRequestHttpException('提供的密码无效。');\n        }\n\n        $tokens = $this->toggleTwoFactorService->handle($request->user(), $data['code'], true);\n\n        Activity::event('user:two-factor.create')->log();\n\n        return new JsonResponse([\n            'object' => 'recovery_tokens',\n            'attributes' => [\n                'tokens' => $tokens,\n            ],\n        ]);\n    }\n\n    /**\n     * Disables two-factor authentication on an account if the password provided\n     * is valid.\n     *\n     * @throws \\Throwable\n     */\n    public function delete(Request $request): JsonResponse\n    {\n        if (!password_verify($request->input('password') ?? '', $request->user()->password)) {\n            throw new BadRequestHttpException('提供的密码无效。');\n        }\n\n        /** @var \\Pterodactyl\\Models\\User $user */\n        $user = $request->user();\n\n        $user->update([\n            'totp_authenticated_at' => Carbon::now(),\n            'use_totp' => false,\n        ]);\n\n        Activity::event('user:two-factor.delete')->log();\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Remote/ActivityProcessingController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Remote;\n\nuse Carbon\\Carbon;\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\User;\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Support\\Facades\\Log;\nuse Pterodactyl\\Models\\ActivityLog;\nuse Pterodactyl\\Models\\ActivityLogSubject;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Http\\Requests\\Api\\Remote\\ActivityEventRequest;\n\nclass ActivityProcessingController extends Controller\n{\n    public function __invoke(ActivityEventRequest $request)\n    {\n        $tz = Carbon::now()->getTimezone();\n\n        /** @var \\Pterodactyl\\Models\\Node $node */\n        $node = $request->attributes->get('node');\n\n        $servers = $node->servers()->whereIn('uuid', $request->servers())->get()->keyBy('uuid');\n        $users = User::query()->whereIn('uuid', $request->users())->get()->keyBy('uuid');\n\n        $logs = [];\n        foreach ($request->input('data') as $datum) {\n            /** @var Server|null $server */\n            $server = $servers->get($datum['server']);\n            if (is_null($server) || !Str::startsWith($datum['event'], 'server:')) {\n                continue;\n            }\n\n            try {\n                $when = Carbon::createFromFormat(\n                    \\DateTimeInterface::RFC3339,\n                    preg_replace('/(\\.\\d+)Z$/', 'Z', $datum['timestamp']),\n                    'UTC'\n                );\n            } catch (\\Exception $exception) {\n                Log::warning($exception, ['timestamp' => $datum['timestamp']]);\n\n                // If we cannot parse the value for some reason don't blow up this request, just go ahead\n                // and log the event with the current time, and set the metadata value to have the original\n                // timestamp that was provided.\n                $when = Carbon::now();\n                $datum['metadata'] = array_merge($datum['metadata'] ?? [], ['original_timestamp' => $datum['timestamp']]);\n            }\n\n            $log = [\n                'ip' => empty($datum['ip']) ? '127.0.0.1' : $datum['ip'],\n                'event' => $datum['event'],\n                'properties' => json_encode($datum['metadata'] ?? []),\n                // We have to change the time to the current timezone due to the way Laravel is handling\n                // the date casting internally. If we just leave it in UTC it ends up getting double-cast\n                // and the time is way off.\n                'timestamp' => $when->setTimezone($tz),\n            ];\n\n            if ($user = $users->get($datum['user'])) {\n                $log['actor_id'] = $user->id;\n                $log['actor_type'] = $user->getMorphClass();\n            }\n\n            if (!isset($logs[$datum['server']])) {\n                $logs[$datum['server']] = [];\n            }\n\n            $logs[$datum['server']][] = $log;\n        }\n\n        foreach ($logs as $key => $data) {\n            Assert::isInstanceOf($server = $servers->get($key), Server::class);\n\n            $batch = [];\n            foreach ($data as $datum) {\n                $id = ActivityLog::insertGetId($datum);\n                $batch[] = [\n                    'activity_log_id' => $id,\n                    'subject_id' => $server->id,\n                    'subject_type' => $server->getMorphClass(),\n                ];\n            }\n\n            ActivityLogSubject::insert($batch);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Remote/Backups/BackupRemoteUploadController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Remote\\Backups;\n\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Backup;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Extensions\\Backups\\BackupManager;\nuse Pterodactyl\\Extensions\\Filesystem\\S3Filesystem;\nuse Pterodactyl\\Exceptions\\Http\\HttpForbiddenException;\nuse Symfony\\Component\\HttpKernel\\Exception\\ConflictHttpException;\nuse Symfony\\Component\\HttpKernel\\Exception\\BadRequestHttpException;\n\nclass BackupRemoteUploadController extends Controller\n{\n    public const DEFAULT_MAX_PART_SIZE = 5 * 1024 * 1024 * 1024;\n\n    /**\n     * BackupRemoteUploadController constructor.\n     */\n    public function __construct(private BackupManager $backupManager)\n    {\n    }\n\n    /**\n     * Returns the required presigned urls to upload a backup to S3 cloud storage.\n     *\n     * @throws \\Exception\n     * @throws \\Throwable\n     * @throws \\Illuminate\\Database\\Eloquent\\ModelNotFoundException\n     */\n    public function __invoke(Request $request, string $backup): JsonResponse\n    {\n        // Get the node associated with the request.\n        /** @var \\Pterodactyl\\Models\\Node $node */\n        $node = $request->attributes->get('node');\n\n        // Get the size query parameter.\n        $size = (int) $request->query('size');\n        if (empty($size)) {\n            throw new BadRequestHttpException('必须提供非空的 \"文件大小\" 查询参数。');\n        }\n\n        $model = Backup::query()->where('uuid', $backup)->firstOrFail();\n\n        // Check that the backup is \"owned\" by the node making the request. This avoids other nodes\n        // from messing with backups that they don't own.\n        $server = $model->server;\n        if ($server->node_id !== $node->id) {\n            throw new HttpForbiddenException('请求节点无权访问此服务器。');\n        }\n\n        // Prevent backups that have already been completed from trying to\n        // be uploaded again.\n        if (!is_null($model->completed_at)) {\n            throw new ConflictHttpException('此备份已处于完成状态。');\n        }\n\n        // Ensure we are using the S3 adapter.\n        $adapter = $this->backupManager->adapter();\n        if (!$adapter instanceof S3Filesystem) {\n            throw new BadRequestHttpException('当前配置的备份适配器不是 S3 兼容的适配器。');\n        }\n\n        // The path where backup will be uploaded to\n        $path = sprintf('%s/%s.tar.gz', $model->server->uuid, $model->uuid);\n\n        // Get the S3 client\n        $client = $adapter->getClient();\n        $expires = CarbonImmutable::now()->addMinutes(config('backups.presigned_url_lifespan', 60));\n\n        // Params for generating the presigned urls\n        $params = [\n            'Bucket' => $adapter->getBucket(),\n            'Key' => $path,\n            'ContentType' => 'application/x-gzip',\n        ];\n\n        $storageClass = config('backups.disks.s3.storage_class');\n        if (!is_null($storageClass)) {\n            $params['StorageClass'] = $storageClass;\n        }\n\n        // Execute the CreateMultipartUpload request\n        $result = $client->execute($client->getCommand('CreateMultipartUpload', $params));\n\n        // Get the UploadId from the CreateMultipartUpload request, this is needed to create\n        // the other presigned urls.\n        $params['UploadId'] = $result->get('UploadId');\n\n        // Retrieve configured part size\n        $maxPartSize = $this->getConfiguredMaxPartSize();\n\n        // Create as many UploadPart presigned urls as needed\n        $parts = [];\n        for ($i = 0; $i < ($size / $maxPartSize); ++$i) {\n            $parts[] = $client->createPresignedRequest(\n                $client->getCommand('UploadPart', array_merge($params, ['PartNumber' => $i + 1])),\n                $expires\n            )->getUri()->__toString();\n        }\n\n        // Set the upload_id on the backup in the database.\n        $model->update(['upload_id' => $params['UploadId']]);\n\n        return new JsonResponse([\n            'parts' => $parts,\n            'part_size' => $maxPartSize,\n        ]);\n    }\n\n    /**\n     * Get the configured maximum size of a single part in the multipart upload.\n     *\n     * The function tries to retrieve a configured value from the configuration.\n     * If no value is specified, a fallback value will be used.\n     *\n     * Note if the received config cannot be converted to int (0), is zero or is negative,\n     * the fallback value will be used too.\n     *\n     * The fallback value is {@see BackupRemoteUploadController::DEFAULT_MAX_PART_SIZE}.\n     */\n    private function getConfiguredMaxPartSize(): int\n    {\n        $maxPartSize = (int) config('backups.max_part_size', self::DEFAULT_MAX_PART_SIZE);\n        if ($maxPartSize <= 0) {\n            $maxPartSize = self::DEFAULT_MAX_PART_SIZE;\n        }\n\n        return $maxPartSize;\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Remote/Backups/BackupStatusController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Remote\\Backups;\n\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Backup;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Extensions\\Backups\\BackupManager;\nuse Pterodactyl\\Extensions\\Filesystem\\S3Filesystem;\nuse Pterodactyl\\Exceptions\\Http\\HttpForbiddenException;\nuse Symfony\\Component\\HttpKernel\\Exception\\BadRequestHttpException;\nuse Pterodactyl\\Http\\Requests\\Api\\Remote\\ReportBackupCompleteRequest;\n\nclass BackupStatusController extends Controller\n{\n    /**\n     * BackupStatusController constructor.\n     */\n    public function __construct(private BackupManager $backupManager)\n    {\n    }\n\n    /**\n     * Handles updating the state of a backup.\n     *\n     * @throws \\Throwable\n     */\n    public function index(ReportBackupCompleteRequest $request, string $backup): JsonResponse\n    {\n        // Get the node associated with the request.\n        /** @var \\Pterodactyl\\Models\\Node $node */\n        $node = $request->attributes->get('node');\n\n        /** @var Backup $model */\n        $model = Backup::query()\n            ->where('uuid', $backup)\n            ->firstOrFail();\n\n        // Check that the backup is \"owned\" by the node making the request. This avoids other nodes\n        // from messing with backups that they don't own.\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        $server = $model->server;\n        if ($server->node_id !== $node->id) {\n            throw new HttpForbiddenException('请求节点无权访问此服务器。');\n        }\n\n        if ($model->is_successful) {\n            throw new BadRequestHttpException('无法更新已标记为完成的备份状态。');\n        }\n\n        $action = $request->boolean('successful') ? 'server:backup.complete' : 'server:backup.fail';\n        $log = Activity::event($action)->subject($model, $model->server)->property('name', $model->name);\n\n        $log->transaction(function () use ($model, $request) {\n            $successful = $request->boolean('successful');\n\n            $model->fill([\n                'is_successful' => $successful,\n                // Change the lock state to unlocked if this was a failed backup so that it can be\n                // deleted easily. Also does not make sense to have a locked backup on the system\n                // that is failed.\n                'is_locked' => $successful ? $model->is_locked : false,\n                'checksum' => $successful ? ($request->input('checksum_type') . ':' . $request->input('checksum')) : null,\n                'bytes' => $successful ? $request->input('size') : 0,\n                'completed_at' => CarbonImmutable::now(),\n            ])->save();\n\n            // Check if we are using the s3 backup adapter. If so, make sure we mark the backup as\n            // being completed in S3 correctly.\n            $adapter = $this->backupManager->adapter();\n            if ($adapter instanceof S3Filesystem) {\n                $this->completeMultipartUpload($model, $adapter, $successful, $request->input('parts'));\n            }\n        });\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Handles toggling the restoration status of a server. The server status field should be\n     * set back to null, even if the restoration failed. This is not an unsolvable state for\n     * the server, and the user can keep trying to restore, or just use the reinstall button.\n     *\n     * The only thing the successful field does is update the entry value for the audit logs\n     * table tracking for this restoration.\n     *\n     * @throws \\Throwable\n     */\n    public function restore(Request $request, string $backup): JsonResponse\n    {\n        /** @var Backup $model */\n        $model = Backup::query()->where('uuid', $backup)->firstOrFail();\n\n        $node = $request->attributes->get('node');\n        if (! $model->server->node->is($node)) {\n            throw new HttpForbiddenException('请求节点无权访问此服务器。');\n        }\n\n        $model->server->update(['status' => null]);\n\n        Activity::event($request->boolean('successful') ? 'server:backup.restore-complete' : 'server.backup.restore-failed')\n            ->subject($model, $model->server)\n            ->property('name', $model->name)\n            ->log();\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Marks a multipart upload in a given S3-compatible instance as failed or successful for\n     * the given backup.\n     *\n     * @throws \\Exception\n     * @throws DisplayException\n     */\n    protected function completeMultipartUpload(Backup $backup, S3Filesystem $adapter, bool $successful, ?array $parts): void\n    {\n        // This should never really happen, but if it does don't let us fall victim to Amazon's\n        // wildly fun error messaging. Just stop the process right here.\n        if (empty($backup->upload_id)) {\n            // A failed backup doesn't need to error here, this can happen if the backup encounters\n            // an error before we even start the upload. AWS gives you tooling to clear these failed\n            // multipart uploads as needed too.\n            if (!$successful) {\n                return;\n            }\n\n            throw new DisplayException('无法完成备份请求：模型中缺少 upload_id。');\n        }\n\n        $params = [\n            'Bucket' => $adapter->getBucket(),\n            'Key' => sprintf('%s/%s.tar.gz', $backup->server->uuid, $backup->uuid),\n            'UploadId' => $backup->upload_id,\n        ];\n\n        $client = $adapter->getClient();\n        if (!$successful) {\n            $client->execute($client->getCommand('AbortMultipartUpload', $params));\n\n            return;\n        }\n\n        // Otherwise send a CompleteMultipartUpload request.\n        $params['MultipartUpload'] = [\n            'Parts' => [],\n        ];\n\n        if (is_null($parts)) {\n            $params['MultipartUpload']['Parts'] = $client->execute($client->getCommand('ListParts', $params))['Parts'];\n        } else {\n            foreach ($parts as $part) {\n                $params['MultipartUpload']['Parts'][] = [\n                    'ETag' => $part['etag'],\n                    'PartNumber' => $part['part_number'],\n                ];\n            }\n        }\n\n        $client->execute($client->getCommand('CompleteMultipartUpload', $params));\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Remote/EggInstallController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Remote;\n\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Servers\\EnvironmentService;\nuse Pterodactyl\\Contracts\\Repository\\ServerRepositoryInterface;\n\nclass EggInstallController extends Controller\n{\n    /**\n     * EggInstallController constructor.\n     */\n    public function __construct(private EnvironmentService $environment, private ServerRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Handle request to get script and installation information for a server\n     * that is being created on the node.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function index(Request $request, string $uuid): JsonResponse\n    {\n        $node = $request->attributes->get('node');\n\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        $server = $this->repository->findFirstWhere([\n            ['uuid', '=', $uuid],\n            ['node_id', '=', $node->id],\n        ]);\n\n        $this->repository->loadEggRelations($server);\n        $egg = $server->getRelation('egg');\n\n        return response()->json([\n            'scripts' => [\n                'install' => !$egg->copy_script_install ? null : str_replace([\"\\r\\n\", \"\\n\", \"\\r\"], \"\\n\", $egg->copy_script_install),\n                'privileged' => $egg->script_is_privileged,\n            ],\n            'config' => [\n                'container' => $egg->copy_script_container,\n                'entry' => $egg->copy_script_entry,\n            ],\n            'env' => $this->environment->handle($server),\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Remote/Servers/ServerDetailsController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Remote\\Servers;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Node;\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Services\\Eggs\\EggConfigurationService;\nuse Pterodactyl\\Exceptions\\Http\\HttpForbiddenException;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerRepository;\nuse Pterodactyl\\Http\\Resources\\Wings\\ServerConfigurationCollection;\nuse Pterodactyl\\Services\\Servers\\ServerConfigurationStructureService;\n\nclass ServerDetailsController extends Controller\n{\n    /**\n     * ServerConfigurationController constructor.\n     */\n    public function __construct(\n        protected ConnectionInterface $connection,\n        private ServerRepository $repository,\n        private ServerConfigurationStructureService $configurationStructureService,\n        private EggConfigurationService $eggConfigurationService,\n    ) {\n    }\n\n    /**\n     * Returns details about the server that allows Wings to self-recover and ensure\n     * that the state of the server matches the Panel at all times.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function __invoke(Request $request, string $uuid): JsonResponse\n    {\n        Assert::isInstanceOf($node = $request->attributes->get('node'), Node::class);\n\n        $server = $this->repository->getByUuid($uuid);\n        $transfer = $server->transfer;\n\n        // If the server is being transferred allow either node to request information about\n        // the server. If the server is not being transferred only the target node is allowed\n        // to fetch these details.\n        $valid = $transfer\n            ? $node->id === $transfer->old_node || $node->id === $transfer->new_node\n            : $node->id === $server->node_id;\n\n        if (! $valid) {\n            throw new HttpForbiddenException('Requesting node does not have permission to access this server.');\n        }\n\n        return new JsonResponse([\n            'settings' => $this->configurationStructureService->handle($server),\n            'process_configuration' => $this->eggConfigurationService->handle($server),\n        ]);\n    }\n\n    /**\n     * Lists all servers with their configurations that are assigned to the requesting node.\n     */\n    public function list(Request $request): ServerConfigurationCollection\n    {\n        /** @var Node $node */\n        $node = $request->attributes->get('node');\n\n        // Avoid run-away N+1 SQL queries by preloading the relationships that are used\n        // within each of the services called below.\n        $servers = Server::query()->with('allocations', 'egg', 'mounts', 'variables', 'location')\n            ->where('node_id', $node->id)\n            // If you don't cast this to a string you'll end up with a stringified per_page returned in\n            // the metadata, and then Wings will panic crash as a result.\n            ->paginate((int) $request->input('per_page', 50));\n\n        return new ServerConfigurationCollection($servers);\n    }\n\n    /**\n     * Resets the state of all servers on the node to be normal. This is triggered\n     * when Wings restarts and is useful for ensuring that any servers on the node\n     * do not get incorrectly stuck in installing/restoring from backup states since\n     * a Wings reboot would completely stop those processes.\n     *\n     * @throws \\Throwable\n     */\n    public function resetState(Request $request): JsonResponse\n    {\n        $node = $request->attributes->get('node');\n\n        // Get all the servers that are currently marked as restoring from a backup\n        // on this node that do not have a failed backup tracked in the audit logs table\n        // as well.\n        //\n        // For each of those servers we'll track a new audit log entry to mark them as\n        // failed and then update them all to be in a valid state.\n        $servers = Server::query()\n            ->with([\n                'activity' => fn ($builder) => $builder\n                    ->where('activity_logs.event', 'server:backup.restore-started')\n                    ->latest('timestamp'),\n            ])\n            ->where('node_id', $node->id)\n            ->where('status', Server::STATUS_RESTORING_BACKUP)\n            ->get();\n\n        $this->connection->transaction(function () use ($node, $servers) {\n            /** @var Server $server */\n            foreach ($servers as $server) {\n                /** @var \\Pterodactyl\\Models\\ActivityLog|null $activity */\n                $activity = $server->activity->first();\n                if (!is_null($activity)) {\n                    if ($subject = $activity->subjects->where('subject_type', 'backup')->first()) {\n                        // Just create a new audit entry for this event and update the server state\n                        // so that power actions, file management, and backups can resume as normal.\n                        Activity::event('server:backup.restore-failed')\n                            ->subject($server, $subject->subject)\n                            ->property('name', $subject->subject->name) // @phpstan-ignore property.notFound\n                            ->log();\n                    }\n                }\n            }\n\n            // Update any server marked as installing or restoring as being in a normal state\n            // at this point in the process.\n            Server::query()->where('node_id', $node->id)\n                ->whereIn('status', [Server::STATUS_INSTALLING, Server::STATUS_RESTORING_BACKUP])\n                ->update(['status' => null]);\n        });\n\n        return new JsonResponse([], JsonResponse::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Remote/Servers/ServerInstallController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Remote\\Servers;\n\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Exceptions\\Http\\HttpForbiddenException;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerRepository;\nuse Pterodactyl\\Events\\Server\\Installed as ServerInstalled;\nuse Illuminate\\Contracts\\Events\\Dispatcher as EventDispatcher;\nuse Pterodactyl\\Http\\Requests\\Api\\Remote\\InstallationDataRequest;\n\nclass ServerInstallController extends Controller\n{\n    /**\n     * ServerInstallController constructor.\n     */\n    public function __construct(private ServerRepository $repository, private EventDispatcher $eventDispatcher)\n    {\n    }\n\n    /**\n     * Returns installation information for a server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function index(Request $request, string $uuid): JsonResponse\n    {\n        $server = $this->repository->getByUuid($uuid);\n        $egg = $server->egg;\n\n        if (! $server->node->is($request->attributes->get('node'))) {\n            throw new HttpForbiddenException('Requesting node does not have permission to access this server.');\n        }\n\n        return new JsonResponse([\n            'container_image' => $egg->copy_script_container,\n            'entrypoint' => $egg->copy_script_entry,\n            'script' => $egg->copy_script_install,\n        ]);\n    }\n\n    /**\n     * Updates the installation state of a server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function store(InstallationDataRequest $request, string $uuid): JsonResponse\n    {\n        $server = $this->repository->getByUuid($uuid);\n        $status = null;\n\n        if (! $server->node->is($request->attributes->get('node'))) {\n            throw new HttpForbiddenException('Requesting node does not have permission to access this server.');\n        }\n\n        // Make sure the type of failure is accurate\n        if (!$request->boolean('successful')) {\n            $status = Server::STATUS_INSTALL_FAILED;\n\n            if ($request->boolean('reinstall')) {\n                $status = Server::STATUS_REINSTALL_FAILED;\n            }\n        }\n\n        // Keep the server suspended if it's already suspended\n        if ($server->status === Server::STATUS_SUSPENDED) {\n            $status = Server::STATUS_SUSPENDED;\n        }\n\n        $this->repository->update($server->id, ['status' => $status, 'installed_at' => CarbonImmutable::now()], true, true);\n\n        // If the server successfully installed, fire installed event.\n        // This logic allows individually disabling install and reinstall notifications separately.\n        $isInitialInstall = is_null($server->installed_at);\n        if ($isInitialInstall && config()->get('pterodactyl.email.send_install_notification', true)) {\n            $this->eventDispatcher->dispatch(new ServerInstalled($server));\n        } elseif (!$isInitialInstall && config()->get('pterodactyl.email.send_reinstall_notification', true)) {\n            $this->eventDispatcher->dispatch(new ServerInstalled($server));\n        }\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Remote/Servers/ServerTransferController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Remote\\Servers;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Node;\nuse Webmozart\\Assert\\Assert;\nuse Illuminate\\Http\\Response;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Models\\Allocation;\nuse Illuminate\\Support\\Facades\\Log;\nuse Pterodactyl\\Models\\ServerTransfer;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Exceptions\\Http\\HttpForbiddenException;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerRepository;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Symfony\\Component\\HttpKernel\\Exception\\ConflictHttpException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass ServerTransferController extends Controller\n{\n    /**\n     * ServerTransferController constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private ServerRepository $repository,\n        private DaemonServerRepository $daemonServerRepository,\n    ) {\n    }\n\n    /**\n     * The daemon notifies us about a transfer failure.\n     *\n     * @throws \\Throwable\n     */\n    public function failure(Request $request, string $uuid): JsonResponse\n    {\n        $server = $this->repository->getByUuid($uuid);\n        $transfer = $server->transfer;\n        if (is_null($transfer)) {\n            throw new ConflictHttpException('服务器未被转移。');\n        }\n\n        /* @var Node $node */\n        Assert::isInstanceOf($node = $request->attributes->get('node'), Node::class);\n\n        // Either node can tell the panel that the transfer has failed. Only the new node\n        // can tell the panel that it was successful.\n        if (! $node->is($transfer->newNode) && ! $node->is($transfer->oldNode)) {\n            throw new HttpForbiddenException('Requesting node does not have permission to access this server.');\n        }\n\n        return $this->processFailedTransfer($transfer);\n    }\n\n    /**\n     * The daemon notifies us about a transfer success.\n     *\n     * @throws \\Throwable\n     */\n    public function success(Request $request, string $uuid): JsonResponse\n    {\n        $server = $this->repository->getByUuid($uuid);\n        $transfer = $server->transfer;\n        if (is_null($transfer)) {\n            throw new ConflictHttpException('服务器未被转移。');\n        }\n\n        /* @var Node $node */\n        Assert::isInstanceOf($node = $request->attributes->get('node'), Node::class);\n\n        // Only the new node communicates a successful state to the panel, so we should\n        // not allow the old node to hit this endpoint.\n        if (! $node->is($transfer->newNode)) {\n            throw new HttpForbiddenException('Requesting node does not have permission to access this server.');\n        }\n\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        $server = $this->connection->transaction(function () use ($server, $transfer) {\n            $allocations = array_merge([$transfer->old_allocation], $transfer->old_additional_allocations);\n\n            // Remove the old allocations for the server and re-assign the server to the new\n            // primary allocation and node.\n            Allocation::query()->whereIn('id', $allocations)->update(['server_id' => null]);\n            $server->update([\n                'allocation_id' => $transfer->new_allocation,\n                'node_id' => $transfer->new_node,\n            ]);\n\n            $server = $server->fresh();\n            $server->transfer->update(['successful' => true]);\n\n            return $server;\n        });\n\n        // Delete the server from the old node making sure to point it to the old node so\n        // that we do not delete it from the new node the server was transferred to.\n        try {\n            $this->daemonServerRepository\n                ->setServer($server)\n                ->setNode($transfer->oldNode)\n                ->delete();\n        } catch (DaemonConnectionException $exception) {\n            Log::warning($exception, ['transfer_id' => $server->transfer->id]);\n        }\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Release all the reserved allocations for this transfer and mark it as failed in\n     * the database.\n     *\n     * @throws \\Throwable\n     */\n    protected function processFailedTransfer(ServerTransfer $transfer): JsonResponse\n    {\n        $this->connection->transaction(function () use (&$transfer) {\n            $transfer->forceFill(['successful' => false])->saveOrFail();\n\n            $allocations = array_merge([$transfer->new_allocation], $transfer->new_additional_allocations);\n            Allocation::query()->whereIn('id', $allocations)->update(['server_id' => null]);\n        });\n\n        return new JsonResponse([], Response::HTTP_NO_CONTENT);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Api/Remote/SftpAuthenticationController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Api\\Remote;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Pterodactyl\\Models\\Permission;\nuse phpseclib3\\Crypt\\PublicKeyLoader;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse phpseclib3\\Exception\\NoKeyLoadedException;\nuse Illuminate\\Foundation\\Auth\\ThrottlesLogins;\nuse Pterodactyl\\Exceptions\\Http\\HttpForbiddenException;\nuse Pterodactyl\\Services\\Servers\\GetUserPermissionsService;\nuse Symfony\\Component\\HttpKernel\\Exception\\BadRequestHttpException;\nuse Pterodactyl\\Http\\Requests\\Api\\Remote\\SftpAuthenticationFormRequest;\nuse Symfony\\Component\\HttpKernel\\Exception\\TooManyRequestsHttpException;\n\nclass SftpAuthenticationController extends Controller\n{\n    use ThrottlesLogins;\n\n    public function __construct(protected GetUserPermissionsService $permissions)\n    {\n    }\n\n    /**\n     * Authenticate a set of credentials and return the associated server details\n     * for a SFTP connection on the daemon. This supports both public key and password\n     * based credentials.\n     */\n    public function __invoke(SftpAuthenticationFormRequest $request): JsonResponse\n    {\n        $connection = $this->parseUsername($request->input('username'));\n        if (empty($connection['server'])) {\n            throw new BadRequestHttpException('No valid server identifier was included in the request.');\n        }\n\n        if ($this->hasTooManyLoginAttempts($request)) {\n            $seconds = $this->limiter()->availableIn($this->throttleKey($request));\n\n            throw new TooManyRequestsHttpException($seconds, \"Too many login attempts for this account, please try again in $seconds seconds.\");\n        }\n\n        $user = $this->getUser($request, $connection['username']);\n        $server = $this->getServer($request, $connection['server']);\n\n        if ($request->input('type') !== 'public_key') {\n            if (!password_verify($request->input('password'), $user->password)) {\n                Activity::event('auth:sftp.fail')->property('method', 'password')->subject($user)->log();\n\n                $this->reject($request);\n            }\n        } else {\n            $key = null;\n            try {\n                $key = PublicKeyLoader::loadPublicKey(trim($request->input('password')));\n            } catch (NoKeyLoadedException) {\n                // do nothing\n            }\n\n            if (!$key || !$user->sshKeys()->where('fingerprint', $key->getFingerprint('sha256'))->exists()) {\n                // We don't log here because of the way the SFTP system works. This endpoint\n                // will get hit for every key the user provides, which could be 4 or 5. That is\n                // a lot of unnecessary log noise.\n                //\n                // For now, we'll only log failures due to a bad password as those are not likely\n                // to occur more than once in a session for the user, and are more likely to be of\n                // value to the end user.\n                $this->reject($request, is_null($key));\n            }\n        }\n\n        $this->validateSftpAccess($user, $server);\n\n        return new JsonResponse([\n            'user' => $user->uuid,\n            'server' => $server->uuid,\n            'permissions' => $this->permissions->handle($server, $user),\n        ]);\n    }\n\n    /**\n     * Finds the server being requested and ensures that it belongs to the node this\n     * request stems from.\n     */\n    protected function getServer(Request $request, string $uuid): Server\n    {\n        return Server::query()\n            ->where(fn ($builder) => $builder->where('uuid', $uuid)->orWhere('uuidShort', $uuid))\n            ->where('node_id', $request->attributes->get('node')->id)\n            ->firstOr(function () use ($request) {\n                $this->reject($request);\n            });\n    }\n\n    /**\n     * Finds a user with the given username or increments the login attempts.\n     */\n    protected function getUser(Request $request, string $username): User\n    {\n        return User::query()->where('username', $username)->firstOr(function () use ($request) {\n            $this->reject($request);\n        });\n    }\n\n    /**\n     * Parses the username provided to the request.\n     *\n     * @return array{\"username\": string, \"server\": string}\n     */\n    protected function parseUsername(string $value): array\n    {\n        // Reverse the string to avoid issues with usernames that contain periods.\n        $parts = explode('.', strrev($value), 2);\n\n        // Unreverse the strings after parsing them apart.\n        return [\n            'username' => strrev(array_get($parts, 1)),\n            'server' => strrev(array_get($parts, 0)),\n        ];\n    }\n\n    /**\n     * Rejects the request and increments the login attempts.\n     */\n    protected function reject(Request $request, bool $increment = true): void\n    {\n        if ($increment) {\n            $this->incrementLoginAttempts($request);\n        }\n\n        throw new HttpForbiddenException('授权凭证不正确，请再试一次。');\n    }\n\n    /**\n     * Validates that a user should have permission to use SFTP for the given server.\n     */\n    protected function validateSftpAccess(User $user, Server $server): void\n    {\n        if (!$user->root_admin && $server->owner_id !== $user->id) {\n            $permissions = $this->permissions->handle($server, $user);\n\n            if (!in_array(Permission::ACTION_FILE_SFTP, $permissions)) {\n                Activity::event('server:sftp.denied')->actor($user)->subject($server)->log();\n\n                throw new HttpForbiddenException('您无权访问此服务器的 SFTP。');\n            }\n        }\n\n        $server->validateCurrentState();\n    }\n\n    /**\n     * Get the throttle key for the given request.\n     */\n    protected function throttleKey(Request $request): string\n    {\n        $username = explode('.', strrev($request->input('username', '')));\n\n        return strtolower(strrev($username[0] ?? '') . '|' . $request->ip()); // @phpstan-ignore nullCoalesce.offset\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Auth/AbstractLoginController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Auth;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Auth\\AuthManager;\nuse Illuminate\\Http\\JsonResponse;\nuse Illuminate\\Auth\\Events\\Failed;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Support\\Facades\\Event;\nuse Pterodactyl\\Events\\Auth\\DirectLogin;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Illuminate\\Contracts\\Auth\\Authenticatable;\nuse Illuminate\\Foundation\\Auth\\AuthenticatesUsers;\n\nabstract class AbstractLoginController extends Controller\n{\n    use AuthenticatesUsers;\n\n    protected AuthManager $auth;\n\n    /**\n     * Lockout time for failed login requests.\n     */\n    protected int $lockoutTime;\n\n    /**\n     * After how many attempts should logins be throttled and locked.\n     */\n    protected int $maxLoginAttempts;\n\n    /**\n     * Where to redirect users after login / registration.\n     */\n    protected string $redirectTo = '/';\n\n    /**\n     * LoginController constructor.\n     */\n    public function __construct()\n    {\n        $this->lockoutTime = config('auth.lockout.time');\n        $this->maxLoginAttempts = config('auth.lockout.attempts');\n        $this->auth = Container::getInstance()->make(AuthManager::class);\n    }\n\n    /**\n     * Get the failed login response instance.\n     *\n     * @return never-return\n     *\n     * @throws DisplayException\n     */\n    protected function sendFailedLoginResponse(Request $request, ?Authenticatable $user = null, ?string $message = null)\n    {\n        $this->incrementLoginAttempts($request);\n        $this->fireFailedLoginEvent($user, [\n            $this->getField($request->input('user')) => $request->input('user'),\n        ]);\n\n        if ($request->route()->named('auth.login-checkpoint')) {\n            throw new DisplayException($message ?? trans('auth.two_factor.checkpoint_failed'));\n        }\n\n        throw new DisplayException(trans('auth.failed'));\n    }\n\n    /**\n     * Send the response after the user was authenticated.\n     */\n    protected function sendLoginResponse(User $user, Request $request): JsonResponse\n    {\n        $request->session()->remove('auth_confirmation_token');\n        $request->session()->regenerate();\n\n        $this->clearLoginAttempts($request);\n\n        $this->auth->guard()->login($user, true);\n\n        Event::dispatch(new DirectLogin($user, true));\n\n        return new JsonResponse([\n            'data' => [\n                'complete' => true,\n                'intended' => $this->redirectPath(),\n                'user' => $user->toVueObject(),\n            ],\n        ]);\n    }\n\n    /**\n     * Determine if the user is logging in using an email or username.\n     */\n    protected function getField(?string $input = null): string\n    {\n        return ($input && str_contains($input, '@')) ? 'email' : 'username';\n    }\n\n    /**\n     * Fire a failed login event.\n     */\n    protected function fireFailedLoginEvent(?Authenticatable $user = null, array $credentials = [])\n    {\n        Event::dispatch(new Failed('auth', $user, $credentials));\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Auth/ForgotPasswordController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Auth;\n\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Http\\JsonResponse;\nuse Illuminate\\Support\\Facades\\Password;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Events\\Auth\\FailedPasswordReset;\nuse Illuminate\\Foundation\\Auth\\SendsPasswordResetEmails;\n\nclass ForgotPasswordController extends Controller\n{\n    use SendsPasswordResetEmails;\n\n    /**\n     * Get the response for a failed password reset link.\n     */\n    protected function sendResetLinkFailedResponse(Request $request, $response): JsonResponse\n    {\n        // As noted in #358 we will return success even if it failed\n        // to avoid pointing out that an account does or does not\n        // exist on the system.\n        event(new FailedPasswordReset($request->ip(), $request->input('email')));\n\n        return $this->sendResetLinkResponse($request, Password::RESET_LINK_SENT);\n    }\n\n    /**\n     * Get the response for a successful password reset link.\n     *\n     * @param string $response\n     */\n    protected function sendResetLinkResponse(Request $request, $response): JsonResponse\n    {\n        return response()->json([\n            'status' => trans($response),\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Auth/LoginCheckpointController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Auth;\n\nuse Carbon\\Carbon;\nuse Carbon\\CarbonImmutable;\nuse Carbon\\CarbonInterface;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\JsonResponse;\nuse PragmaRX\\Google2FA\\Google2FA;\nuse Illuminate\\Support\\Facades\\Event;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Pterodactyl\\Events\\Auth\\ProvidedAuthenticationToken;\nuse Pterodactyl\\Http\\Requests\\Auth\\LoginCheckpointRequest;\nuse Illuminate\\Contracts\\Validation\\Factory as ValidationFactory;\n\nclass LoginCheckpointController extends AbstractLoginController\n{\n    private const TOKEN_EXPIRED_MESSAGE = '提供的动态口令已过期，请刷新页面重试。';\n\n    /**\n     * LoginCheckpointController constructor.\n     */\n    public function __construct(\n        private Encrypter $encrypter,\n        private Google2FA $google2FA,\n        private ValidationFactory $validation,\n    ) {\n        parent::__construct();\n    }\n\n    /**\n     * Handle a login where the user is required to provide a TOTP authentication\n     * token. Once a user has reached this stage it is assumed that they have already\n     * provided a valid username and password.\n     *\n     * @throws \\PragmaRX\\Google2FA\\Exceptions\\IncompatibleWithGoogleAuthenticatorException\n     * @throws \\PragmaRX\\Google2FA\\Exceptions\\InvalidCharactersException\n     * @throws \\PragmaRX\\Google2FA\\Exceptions\\SecretKeyTooShortException\n     * @throws \\Exception\n     * @throws \\Illuminate\\Validation\\ValidationException\n     */\n    public function __invoke(LoginCheckpointRequest $request): JsonResponse\n    {\n        if ($this->hasTooManyLoginAttempts($request)) {\n            $this->sendLockoutResponse($request);\n        }\n\n        $details = $request->session()->get('auth_confirmation_token');\n        if (!$this->hasValidSessionData($details)) {\n            $this->sendFailedLoginResponse($request, null, self::TOKEN_EXPIRED_MESSAGE);\n        }\n\n        if (!hash_equals($request->input('confirmation_token') ?? '', $details['token_value'])) {\n            $this->sendFailedLoginResponse($request);\n        }\n\n        try {\n            $user = User::query()->findOrFail($details['user_id']);\n        } catch (ModelNotFoundException) {\n            $this->sendFailedLoginResponse($request, null, self::TOKEN_EXPIRED_MESSAGE);\n        }\n\n        // Recovery tokens go through a slightly different pathway for usage.\n        if (!is_null($recoveryToken = $request->input('recovery_token'))) {\n            if ($this->isValidRecoveryToken($user, $recoveryToken)) {\n                Event::dispatch(new ProvidedAuthenticationToken($user, true));\n\n                return $this->sendLoginResponse($user, $request);\n            }\n        } else {\n            $decrypted = $this->encrypter->decrypt($user->totp_secret);\n            $oldTimestamp = $user->totp_authenticated_at\n                ? (int) floor($user->totp_authenticated_at->unix() / $this->google2FA->getKeyRegeneration())\n                : null;\n\n            $verified = $this->google2FA->verifyKeyNewer(\n                $decrypted,\n                $request->input('authentication_code') ?? '',\n                $oldTimestamp,\n                config('pterodactyl.auth.2fa.window') ?? 1,\n            );\n\n            if ($verified !== false) {\n                $user->update(['totp_authenticated_at' => Carbon::now()]);\n\n                Event::dispatch(new ProvidedAuthenticationToken($user));\n\n                return $this->sendLoginResponse($user, $request);\n            }\n        }\n\n        $this->sendFailedLoginResponse($request, $user, !empty($recoveryToken) ? '提供的恢复口令无效。' : null);\n    }\n\n    /**\n     * Determines if a given recovery token is valid for the user account. If we find a matching token\n     * it will be deleted from the database.\n     *\n     * @throws \\Exception\n     */\n    protected function isValidRecoveryToken(User $user, string $value): bool\n    {\n        foreach ($user->recoveryTokens as $token) {\n            if (password_verify($value, $token->token)) {\n                $token->delete();\n\n                return true;\n            }\n        }\n\n        return false;\n    }\n\n    /**\n     * Determines if the data provided from the session is valid or not. This\n     * will return false if the data is invalid, or if more time has passed than\n     * was configured when the session was written.\n     */\n    protected function hasValidSessionData(?array $data): bool\n    {\n        $validator = $this->validation->make($data ?? [], [\n            'user_id' => 'required|integer|min:1',\n            'token_value' => 'required|string',\n            'expires_at' => 'required',\n        ]);\n\n        if ($validator->fails()) {\n            return false;\n        }\n\n        if (!$data['expires_at'] instanceof CarbonInterface) {\n            return false;\n        }\n\n        if ($data['expires_at']->isBefore(CarbonImmutable::now())) {\n            return false;\n        }\n\n        return true;\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Auth/LoginController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Auth;\n\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\JsonResponse;\nuse Pterodactyl\\Facades\\Activity;\nuse Illuminate\\Contracts\\View\\View;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\n\nclass LoginController extends AbstractLoginController\n{\n    /**\n     * Handle all incoming requests for the authentication routes and render the\n     * base authentication view component. React will take over at this point and\n     * turn the login area into an SPA.\n     */\n    public function index(): View\n    {\n        return view('templates/auth.core');\n    }\n\n    /**\n     * Handle a login request to the application.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Illuminate\\Validation\\ValidationException\n     */\n    public function login(Request $request): JsonResponse\n    {\n        if ($this->hasTooManyLoginAttempts($request)) {\n            $this->fireLockoutEvent($request);\n            $this->sendLockoutResponse($request);\n        }\n\n        try {\n            $username = $request->input('user');\n\n            /** @var User $user */\n            $user = User::query()->where($this->getField($username), $username)->firstOrFail();\n        } catch (ModelNotFoundException) {\n            $this->sendFailedLoginResponse($request);\n        }\n\n        // Ensure that the account is using a valid username and password before trying to\n        // continue. Previously this was handled in the 2FA checkpoint, however that has\n        // a flaw in which you can discover if an account exists simply by seeing if you\n        // can proceed to the next step in the login process.\n        if (!password_verify($request->input('password'), $user->password)) {\n            $this->sendFailedLoginResponse($request, $user);\n        }\n\n        if (!$user->use_totp) {\n            return $this->sendLoginResponse($user, $request);\n        }\n\n        Activity::event('auth:checkpoint')->withRequestMetadata()->subject($user)->log();\n\n        $request->session()->put('auth_confirmation_token', [\n            'user_id' => $user->id,\n            'token_value' => $token = Str::random(64),\n            'expires_at' => CarbonImmutable::now()->addMinutes(5),\n        ]);\n\n        return new JsonResponse([\n            'data' => [\n                'complete' => false,\n                'confirmation_token' => $token,\n            ],\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Auth/ResetPasswordController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Auth;\n\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Http\\JsonResponse;\nuse Illuminate\\Contracts\\Hashing\\Hasher;\nuse Illuminate\\Support\\Facades\\Password;\nuse Illuminate\\Auth\\Events\\PasswordReset;\nuse Illuminate\\Contracts\\Events\\Dispatcher;\nuse Pterodactyl\\Events\\User\\PasswordChanged;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Illuminate\\Foundation\\Auth\\ResetsPasswords;\nuse Pterodactyl\\Http\\Requests\\Auth\\ResetPasswordRequest;\nuse Pterodactyl\\Contracts\\Repository\\UserRepositoryInterface;\n\nclass ResetPasswordController extends Controller\n{\n    use ResetsPasswords;\n\n    /**\n     * The URL to redirect users to after password reset.\n     */\n    public string $redirectTo = '/';\n\n    protected bool $hasTwoFactor = false;\n\n    /**\n     * ResetPasswordController constructor.\n     */\n    public function __construct(\n        private Dispatcher $dispatcher,\n        private Hasher $hasher,\n        private UserRepositoryInterface $userRepository,\n    ) {\n    }\n\n    /**\n     * Reset the given user's password.\n     *\n     * @throws DisplayException\n     */\n    public function __invoke(ResetPasswordRequest $request): JsonResponse\n    {\n        // Here we will attempt to reset the user's password. If it is successful we\n        // will update the password on an actual user model and persist it to the\n        // database. Otherwise, we will parse the error and return the response.\n        $response = $this->broker()->reset(\n            $this->credentials($request),\n            function ($user, $password) {\n                $this->resetPassword($user, $password);\n            }\n        );\n\n        // If the password was successfully reset, we will redirect the user back to\n        // the application's home authenticated view. If there is an error we can\n        // redirect them back to where they came from with their error message.\n        if ($response === Password::PASSWORD_RESET) {\n            return $this->sendResetResponse();\n        }\n\n        throw new DisplayException(trans($response));\n    }\n\n    /**\n     * Reset the given user's password. If the user has two-factor authentication enabled on their\n     * account do not automatically log them in. In those cases, send the user back to the login\n     * form with a note telling them their password was changed and to log back in.\n     *\n     * @param \\Illuminate\\Contracts\\Auth\\CanResetPassword&\\Pterodactyl\\Models\\User $user\n     * @param string $password\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    protected function resetPassword($user, $password)\n    {\n        $user = $this->userRepository->update($user->id, [\n            'password' => $this->hasher->make($password),\n            $user->getRememberTokenName() => Str::random(60),\n        ]);\n\n        $this->dispatcher->dispatch(new PasswordReset($user));\n        PasswordChanged::dispatch($user);\n\n        // If the user is not using 2FA log them in, otherwise skip this step and force a\n        // fresh login where they'll be prompted to enter a token.\n        if (!$user->use_totp) {\n            $this->guard()->login($user);\n        }\n\n        $this->hasTwoFactor = $user->use_totp;\n    }\n\n    /**\n     * Send a successful password reset response back to the callee.\n     */\n    protected function sendResetResponse(): JsonResponse\n    {\n        return response()->json([\n            'success' => true,\n            'redirect_to' => $this->redirectTo,\n            'send_to_login' => $this->hasTwoFactor,\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Base/IndexController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Base;\n\nuse Illuminate\\View\\View;\nuse Illuminate\\View\\Factory as ViewFactory;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Contracts\\Repository\\ServerRepositoryInterface;\n\nclass IndexController extends Controller\n{\n    /**\n     * IndexController constructor.\n     */\n    public function __construct(\n        protected ServerRepositoryInterface $repository,\n        protected ViewFactory $view,\n    ) {\n    }\n\n    /**\n     * Returns listing of user's servers.\n     */\n    public function index(): View\n    {\n        return view('templates/base.core');\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Base/LocaleController.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers\\Base;\n\nuse Illuminate\\Http\\JsonResponse;\nuse Illuminate\\Translation\\Translator;\nuse Illuminate\\Contracts\\Translation\\Loader;\nuse Pterodactyl\\Http\\Controllers\\Controller;\nuse Pterodactyl\\Http\\Requests\\Base\\LocaleRequest;\n\nclass LocaleController extends Controller\n{\n    protected Loader $loader;\n\n    public function __construct(Translator $translator)\n    {\n        $this->loader = $translator->getLoader();\n    }\n\n    /**\n     * Returns translation data given a specific locale and namespace.\n     */\n    public function __invoke(LocaleRequest $request): JsonResponse\n    {\n        $locale = $request->input('locale');\n        $namespace = $request->input('namespace');\n        $response[$locale][$namespace] = $this->i18n($this->loader->load($locale, $namespace));\n\n        return new JsonResponse($response, 200, [\n            // Cache this in the browser for an hour, and allow the browser to use a stale\n            // cache for up to a day after it was created while it fetches an updated set\n            // of translation keys.\n            'Cache-Control' => 'public, max-age=3600, stale-while-revalidate=86400',\n            'ETag' => md5(json_encode($response, JSON_THROW_ON_ERROR)),\n        ]);\n    }\n\n    /**\n     * Convert standard Laravel translation keys that look like \":foo\"\n     * into key structures that are supported by the front-end i18n\n     * library, like \"{{foo}}\".\n     */\n    protected function i18n(array $data): array\n    {\n        foreach ($data as $key => $value) {\n            if (is_array($value)) {\n                $data[$key] = $this->i18n($value);\n            } else {\n                // Find a Laravel style translation replacement in the string and replace it with\n                // one that the front-end is able to use. This won't always be present, especially\n                // for complex strings or things where we'd never have a backend component anyways.\n                //\n                // For example:\n                // \"Hello :name, the :notifications.0.title notification needs :count actions :foo.0.bar.\"\n                //\n                // Becomes:\n                // \"Hello {{name}}, the {{notifications.0.title}} notification needs {{count}} actions {{foo.0.bar}}.\"\n                $data[$key] = preg_replace('/:([\\w.-]+\\w)([^\\w:]?|$)/m', '{{$1}}$2', $value);\n            }\n        }\n\n        return $data;\n    }\n}\n"
  },
  {
    "path": "app/Http/Controllers/Controller.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Controllers;\n\nuse Illuminate\\Foundation\\Bus\\DispatchesJobs;\nuse Illuminate\\Routing\\Controller as BaseController;\nuse Illuminate\\Foundation\\Validation\\ValidatesRequests;\nuse Illuminate\\Foundation\\Auth\\Access\\AuthorizesRequests;\n\nabstract class Controller extends BaseController\n{\n    use AuthorizesRequests;\n    use DispatchesJobs;\n    use ValidatesRequests;\n}\n"
  },
  {
    "path": "app/Http/Kernel.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http;\n\nuse Illuminate\\Auth\\Middleware\\Authorize;\nuse Illuminate\\Http\\Middleware\\HandleCors;\nuse Illuminate\\Auth\\Middleware\\Authenticate;\nuse Illuminate\\Http\\Middleware\\TrustProxies;\nuse Pterodactyl\\Http\\Middleware\\TrimStrings;\nuse Illuminate\\Session\\Middleware\\StartSession;\nuse Pterodactyl\\Http\\Middleware\\EncryptCookies;\nuse Pterodactyl\\Http\\Middleware\\Api\\IsValidJson;\nuse Pterodactyl\\Http\\Middleware\\VerifyCsrfToken;\nuse Pterodactyl\\Http\\Middleware\\VerifyReCaptcha;\nuse Illuminate\\Routing\\Middleware\\ThrottleRequests;\nuse Pterodactyl\\Http\\Middleware\\LanguageMiddleware;\nuse Pterodactyl\\Http\\Middleware\\SetSecurityHeaders;\nuse Illuminate\\Foundation\\Http\\Kernel as HttpKernel;\nuse Illuminate\\Routing\\Middleware\\SubstituteBindings;\nuse Pterodactyl\\Http\\Middleware\\Activity\\TrackAPIKey;\nuse Illuminate\\Session\\Middleware\\AuthenticateSession;\nuse Illuminate\\View\\Middleware\\ShareErrorsFromSession;\nuse Pterodactyl\\Http\\Middleware\\MaintenanceMiddleware;\nuse Pterodactyl\\Http\\Middleware\\EnsureStatefulRequests;\nuse Pterodactyl\\Http\\Middleware\\RedirectIfAuthenticated;\nuse Illuminate\\Auth\\Middleware\\AuthenticateWithBasicAuth;\nuse Pterodactyl\\Http\\Middleware\\Api\\AuthenticateIPAccess;\nuse Illuminate\\Foundation\\Http\\Middleware\\ValidatePostSize;\nuse Illuminate\\Cookie\\Middleware\\AddQueuedCookiesToResponse;\nuse Pterodactyl\\Http\\Middleware\\Api\\Daemon\\DaemonAuthenticate;\nuse Pterodactyl\\Http\\Middleware\\Api\\Client\\RequireClientApiKey;\nuse Pterodactyl\\Http\\Middleware\\RequireTwoFactorAuthentication;\nuse Illuminate\\Foundation\\Http\\Middleware\\ConvertEmptyStringsToNull;\nuse Pterodactyl\\Http\\Middleware\\Api\\Client\\SubstituteClientBindings;\nuse Illuminate\\Foundation\\Http\\Middleware\\PreventRequestsDuringMaintenance;\nuse Pterodactyl\\Http\\Middleware\\Api\\Application\\AuthenticateApplicationUser;\n\nclass Kernel extends HttpKernel\n{\n    /**\n     * The application's global HTTP middleware stack.\n     */\n    protected $middleware = [\n        TrustProxies::class,\n        HandleCors::class,\n        PreventRequestsDuringMaintenance::class,\n        ValidatePostSize::class,\n        TrimStrings::class,\n        ConvertEmptyStringsToNull::class,\n        SetSecurityHeaders::class,\n    ];\n\n    protected $middlewarePriority = [\n        SubstituteClientBindings::class,\n    ];\n\n    /**\n     * The application's route middleware groups.\n     */\n    protected $middlewareGroups = [\n        'web' => [\n            EncryptCookies::class,\n            AddQueuedCookiesToResponse::class,\n            StartSession::class,\n            ShareErrorsFromSession::class,\n            VerifyCsrfToken::class,\n            SubstituteBindings::class,\n            LanguageMiddleware::class,\n        ],\n        'api' => [\n            EnsureStatefulRequests::class,\n            'auth:sanctum',\n            IsValidJson::class,\n            TrackAPIKey::class,\n            RequireTwoFactorAuthentication::class,\n            AuthenticateIPAccess::class,\n        ],\n        'application-api' => [\n            SubstituteBindings::class,\n            AuthenticateApplicationUser::class,\n        ],\n        'client-api' => [\n            SubstituteClientBindings::class,\n            RequireClientApiKey::class,\n        ],\n        'daemon' => [\n            SubstituteBindings::class,\n            DaemonAuthenticate::class,\n        ],\n    ];\n\n    /**\n     * The application's route middleware.\n     */\n    protected $middlewareAliases = [\n        'auth' => Authenticate::class,\n        'auth.basic' => AuthenticateWithBasicAuth::class,\n        'auth.session' => AuthenticateSession::class,\n        'guest' => RedirectIfAuthenticated::class,\n        'csrf' => VerifyCsrfToken::class,\n        'throttle' => ThrottleRequests::class,\n        'can' => Authorize::class,\n        'bindings' => SubstituteBindings::class,\n        'recaptcha' => VerifyReCaptcha::class,\n        'node.maintenance' => MaintenanceMiddleware::class,\n    ];\n}\n"
  },
  {
    "path": "app/Http/Middleware/Activity/AccountSubject.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Activity;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Facades\\LogTarget;\n\nclass AccountSubject\n{\n    /**\n     * Sets the actor and default subject for all requests passing through this\n     * middleware to be the currently logged in user.\n     */\n    public function handle(Request $request, \\Closure $next)\n    {\n        LogTarget::setActor($request->user());\n        LogTarget::setSubject($request->user());\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Activity/ServerSubject.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Activity;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Facades\\LogTarget;\n\nclass ServerSubject\n{\n    /**\n     * Attempts to automatically scope all of the activity log events registered\n     * within the request instance to the given user and server. This only sets\n     * the actor and subject if there is a server present on the request.\n     *\n     * If no server is found this is a no-op as the activity log service can always\n     * set the user based on the authmanager response.\n     */\n    public function handle(Request $request, \\Closure $next)\n    {\n        $server = $request->route()->parameter('server');\n        if ($server instanceof Server) {\n            LogTarget::setActor($request->user());\n            LogTarget::setSubject($server);\n        }\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Activity/TrackAPIKey.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Activity;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\ApiKey;\nuse Pterodactyl\\Facades\\LogTarget;\n\nclass TrackAPIKey\n{\n    /**\n     * Determines if the authenticated user making this request is using an actual\n     * API key, or it is just a cookie authenticated session. This data is set in a\n     * request singleton so that all tracked activity log events are properly associated\n     * with the given API key.\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        if ($request->user()) {\n            $token = $request->user()->currentAccessToken();\n\n            LogTarget::setApiKeyId($token instanceof ApiKey ? $token->id : null); // @phpstan-ignore instanceof.alwaysTrue\n        }\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Admin/Servers/ServerInstalled.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Admin\\Servers;\n\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpException;\nuse Symfony\\Component\\HttpKernel\\Exception\\NotFoundHttpException;\n\nclass ServerInstalled\n{\n    /**\n     * Checks that the server is installed before allowing access through the route.\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        /** @var Server|null $server */\n        $server = $request->route()->parameter('server');\n\n        if (!$server instanceof Server) {\n            throw new NotFoundHttpException('No server resource was located in the request parameters.');\n        }\n\n        if (!$server->isInstalled()) {\n            throw new HttpException(Response::HTTP_FORBIDDEN, 'Access to this resource is not allowed due to the current installation state.');\n        }\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/AdminAuthenticate.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse Illuminate\\Http\\Request;\nuse Symfony\\Component\\HttpKernel\\Exception\\AccessDeniedHttpException;\n\nclass AdminAuthenticate\n{\n    /**\n     * Handle an incoming request.\n     *\n     * @throws AccessDeniedHttpException\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        if (!$request->user() || !$request->user()->root_admin) {\n            throw new AccessDeniedHttpException();\n        }\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Api/Application/AuthenticateApplicationUser.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Api\\Application;\n\nuse Illuminate\\Http\\Request;\nuse Symfony\\Component\\HttpKernel\\Exception\\AccessDeniedHttpException;\n\nclass AuthenticateApplicationUser\n{\n    /**\n     * Authenticate that the currently authenticated user is an administrator\n     * and should be allowed to proceed through the application API.\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        /** @var \\Pterodactyl\\Models\\User|null $user */\n        $user = $request->user();\n        if (!$user || !$user->root_admin) {\n            throw new AccessDeniedHttpException('This account does not have permission to access the API.');\n        }\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Api/AuthenticateIPAccess.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Api;\n\nuse IPTools\\IP;\nuse IPTools\\Range;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Facades\\Activity;\nuse Laravel\\Sanctum\\TransientToken;\nuse Symfony\\Component\\HttpKernel\\Exception\\AccessDeniedHttpException;\n\nclass AuthenticateIPAccess\n{\n    /**\n     * Determine if a request IP has permission to access the API.\n     *\n     * @throws \\Exception\n     * @throws AccessDeniedHttpException\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        /** @var TransientToken|\\Pterodactyl\\Models\\ApiKey $token */\n        $token = $request->user()->currentAccessToken();\n\n        // If this is a stateful request just push the request through to the next\n        // middleware in the stack, there is nothing we need to explicitly check. If\n        // this is a valid API Key, but there is no allowed IP restriction, also pass\n        // the request through.\n        if ($token instanceof TransientToken || empty($token->allowed_ips)) {\n            return $next($request);\n        }\n\n        $find = new IP($request->ip());\n        foreach ($token->allowed_ips as $ip) {\n            if (Range::parse($ip)->contains($find)) {\n                return $next($request);\n            }\n        }\n\n        Activity::event('auth:ip-blocked')\n            ->actor($request->user())\n            ->subject($request->user(), $token)\n            ->property('identifier', $token->identifier)\n            ->log();\n\n        throw new AccessDeniedHttpException('This IP address (' . $request->ip() . ') does not have permission to access the API using these credentials.');\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Api/Client/RequireClientApiKey.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Api\\Client;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\ApiKey;\nuse Symfony\\Component\\HttpKernel\\Exception\\AccessDeniedHttpException;\n\nclass RequireClientApiKey\n{\n    /**\n     * Blocks a request to the Client API endpoints if the user is providing an API token\n     * that was created for the application API.\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        $token = $request->user()->currentAccessToken();\n\n        if ($token instanceof ApiKey && $token->key_type === ApiKey::TYPE_APPLICATION) { // @phpstan-ignore instanceof.alwaysTrue\n            throw new AccessDeniedHttpException('You are attempting to use an application API key on an endpoint that requires a client API key.');\n        }\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Api/Client/Server/AuthenticateServerAccess.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Api\\Client\\Server;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Server;\nuse Symfony\\Component\\HttpKernel\\Exception\\NotFoundHttpException;\nuse Pterodactyl\\Exceptions\\Http\\Server\\ServerStateConflictException;\n\nclass AuthenticateServerAccess\n{\n    /**\n     * Routes that this middleware should not apply to if the user is an admin.\n     */\n    protected array $except = [\n        'api:client:server.ws',\n    ];\n\n    /**\n     * AuthenticateServerAccess constructor.\n     */\n    public function __construct()\n    {\n    }\n\n    /**\n     * Authenticate that this server exists and is not suspended or marked as installing.\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        /** @var \\Pterodactyl\\Models\\User $user */\n        $user = $request->user();\n        $server = $request->route()->parameter('server');\n\n        if (!$server instanceof Server) {\n            throw new NotFoundHttpException(trans('exceptions.api.resource_not_found'));\n        }\n\n        // At the very least, ensure that the user trying to make this request is the\n        // server owner, a subuser, or a root admin. We'll leave it up to the controllers\n        // to authenticate more detailed permissions if needed.\n        if ($user->id !== $server->owner_id && !$user->root_admin) {\n            // Check for subuser status.\n            if (!$server->subusers->contains('user_id', $user->id)) {\n                throw new NotFoundHttpException(trans('exceptions.api.resource_not_found'));\n            }\n        }\n\n        try {\n            $server->validateCurrentState();\n        } catch (ServerStateConflictException $exception) {\n            // Still allow users to get information about their server if it is installing or\n            // being transferred.\n            if (!$request->routeIs('api:client:server.view')) {\n                if (($server->isSuspended() || $server->node->isUnderMaintenance()) && !$request->routeIs('api:client:server.resources')) {\n                    throw $exception;\n                }\n                if (!$user->root_admin || !$request->routeIs($this->except)) {\n                    throw $exception;\n                }\n            }\n        }\n\n        $request->attributes->set('server', $server);\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Api/Client/Server/ResourceBelongsToServer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Api\\Client\\Server;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Task;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Backup;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Models\\Allocation;\nuse Illuminate\\Database\\Eloquent\\Model;\nuse Symfony\\Component\\HttpKernel\\Exception\\NotFoundHttpException;\n\nclass ResourceBelongsToServer\n{\n    /**\n     * Looks at the request parameters to determine if the given resource belongs\n     * to the requested server. If not, a 404 error will be returned to the caller.\n     *\n     * This is critical to ensuring that all subsequent logic is using exactly the\n     * server that is expected, and that we're not accessing a resource completely\n     * unrelated to the server provided in the request.\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        $params = $request->route()->parameters();\n        if (! isset($params['server']) || !$params['server'] instanceof Server) {\n            throw new \\InvalidArgumentException('This middleware cannot be used in a context that is missing a server in the parameters.');\n        }\n\n        /** @var Server $server */\n        $server = $request->route()->parameter('server');\n        $exception = new NotFoundHttpException('The requested resource was not found for this server.');\n        foreach ($params as $key => $model) {\n            // Specifically skip the server, we're just trying to see if all of the\n            // other resources are assigned to this server. Also skip anything that\n            // is not currently a Model instance since those will just end up being\n            // a 404 down the road.\n            if ($key === 'server' || !$model instanceof Model) {\n                continue;\n            }\n\n            switch (get_class($model)) {\n                // All of these models use \"server_id\" as the field key for the server\n                // they are assigned to, so the logic is identical for them all.\n                case Allocation::class:\n                case Backup::class:\n                case Database::class:\n                case Schedule::class:\n                case Subuser::class:\n                    if ($model->server_id !== $server->id) {\n                        throw $exception;\n                    }\n                    break;\n                    // Regular users are a special case here as we need to make sure they're\n                    // currently assigned as a subuser on the server.\n                case User::class:\n                    $subuser = $server->subusers()->where('user_id', $model->id)->first();\n                    if (is_null($subuser)) {\n                        throw $exception;\n                    }\n                    // This is a special case to avoid an additional query being triggered\n                    // in the underlying logic.\n                    $request->attributes->set('subuser', $subuser);\n                    break;\n                    // Tasks are special since they're (currently) the only item in the API\n                    // that requires something in addition to the server in order to be accessed.\n                case Task::class:\n                    $schedule = $request->route()->parameter('schedule');\n                    if (!$schedule instanceof Schedule || $model->schedule_id !== $schedule->id || $schedule->server_id !== $server->id) {\n                        throw $exception;\n                    }\n                    break;\n                default:\n                    // Don't return a 404 here since we want to make sure no one relies\n                    // on this middleware in a context in which it will not work. Fail safe.\n                    throw new \\InvalidArgumentException('There is no handler configured for a resource of this type: ' . get_class($model));\n            }\n        }\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Api/Client/SubstituteClientBindings.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Api\\Client;\n\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Routing\\Middleware\\SubstituteBindings;\n\nclass SubstituteClientBindings extends SubstituteBindings\n{\n    /**\n     * @param \\Illuminate\\Http\\Request $request\n     */\n    public function handle($request, \\Closure $next): mixed\n    {\n        // Override default behavior of the model binding to use a specific table\n        // column rather than the default 'id'.\n        $this->router->bind('server', function ($value) {\n            return Server::query()\n                ->when(\n                    str_starts_with($value, 'serv_'),\n                    fn ($builder) => $builder->whereIdentifier($value),\n                    fn ($builder) => $builder->where(strlen($value) === 8 ? 'uuidShort' : 'uuid', $value)\n                )\n                ->firstOrFail();\n        });\n\n        $this->router->bind('user', function ($value, $route) {\n            /** @var \\Pterodactyl\\Models\\Subuser $match */\n            $match = $route->parameter('server')\n                ->subusers()\n                ->whereRelation('user', 'uuid', '=', $value)\n                ->firstOrFail();\n\n            return $match->user;\n        });\n\n        return parent::handle($request, $next);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Api/Daemon/DaemonAuthenticate.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Api\\Daemon;\n\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Repositories\\Eloquent\\NodeRepository;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpException;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\nuse Symfony\\Component\\HttpKernel\\Exception\\BadRequestHttpException;\nuse Symfony\\Component\\HttpKernel\\Exception\\AccessDeniedHttpException;\n\nclass DaemonAuthenticate\n{\n    /**\n     * Daemon routes that this middleware should be skipped on.\n     */\n    protected array $except = [\n        'daemon.configuration',\n    ];\n\n    /**\n     * DaemonAuthenticate constructor.\n     */\n    public function __construct(private Encrypter $encrypter, private NodeRepository $repository)\n    {\n    }\n\n    /**\n     * Check if a request from the daemon can be properly attributed back to a single node instance.\n     *\n     * @throws HttpException\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        if (in_array($request->route()->getName(), $this->except)) {\n            return $next($request);\n        }\n\n        if (is_null($bearer = $request->bearerToken())) {\n            throw new HttpException(401, '对此端点的访问必须包含授权标头。', null, ['WWW-Authenticate' => 'Bearer']);\n        }\n\n        $parts = explode('.', $bearer);\n        // Ensure that all of the correct parts are provided in the header.\n        if (count($parts) !== 2 || empty($parts[0]) || empty($parts[1])) {\n            throw new BadRequestHttpException('提供的授权标头格式无效。');\n        }\n\n        try {\n            /** @var \\Pterodactyl\\Models\\Node $node */\n            $node = $this->repository->findFirstWhere([\n                'daemon_token_id' => $parts[0],\n            ]);\n\n            if (hash_equals((string) $this->encrypter->decrypt($node->daemon_token), $parts[1])) {\n                $request->attributes->set('node', $node);\n\n                return $next($request);\n            }\n        } catch (RecordNotFoundException $exception) {\n            // Do nothing, we don't want to expose a node not existing at all.\n        }\n\n        throw new AccessDeniedHttpException('您无权访问此资源。');\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/Api/IsValidJson.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware\\Api;\n\nuse Illuminate\\Http\\Request;\nuse Symfony\\Component\\HttpKernel\\Exception\\BadRequestHttpException;\n\nclass IsValidJson\n{\n    /**\n     * Throw an exception if the request should be valid JSON data but there is an error while\n     * parsing the data. This avoids confusing validation errors where every field is flagged and\n     * it is not immediately clear that there is an issue with the JSON being passed.\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        if ($request->isJson() && !empty($request->getContent())) {\n            try {\n                json_decode($request->getContent(), true, 512, JSON_THROW_ON_ERROR);\n            } catch (\\JsonException $exception) {\n                throw new BadRequestHttpException('The JSON data passed in the request appears to be malformed: ' . $exception->getMessage());\n            }\n        }\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/EncryptCookies.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse Illuminate\\Cookie\\Middleware\\EncryptCookies as BaseEncrypter;\n\nclass EncryptCookies extends BaseEncrypter\n{\n    /**\n     * The names of the cookies that should not be encrypted.\n     */\n    protected $except = [];\n}\n"
  },
  {
    "path": "app/Http/Middleware/EnsureStatefulRequests.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse Laravel\\Sanctum\\Http\\Middleware\\EnsureFrontendRequestsAreStateful;\n\nclass EnsureStatefulRequests extends EnsureFrontendRequestsAreStateful\n{\n    /**\n     * Determines if a request is stateful or not. This is determined using the default\n     * Sanctum \"fromFrontend\" helper method. However, we also check if the request includes\n     * a cookie value for the Pterodactyl session. If so, we assume this is a stateful\n     * request.\n     *\n     * We don't want to support API usage using the cookies, except for requests stemming\n     * from the front-end we control.\n     */\n    public static function fromFrontend($request)\n    {\n        if (parent::fromFrontend($request)) {\n            return true;\n        }\n\n        return $request->hasCookie(config('session.cookie'));\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/LanguageMiddleware.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Foundation\\Application;\n\nclass LanguageMiddleware\n{\n    /**\n     * LanguageMiddleware constructor.\n     */\n    public function __construct(private Application $app)\n    {\n    }\n\n    /**\n     * Handle an incoming request and set the user's preferred language.\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        $this->app->setLocale($request->user()->language ?? config('app.locale', 'zh'));\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/MaintenanceMiddleware.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Contracts\\Routing\\ResponseFactory;\n\nclass MaintenanceMiddleware\n{\n    /**\n     * MaintenanceMiddleware constructor.\n     */\n    public function __construct(private ResponseFactory $response)\n    {\n    }\n\n    /**\n     * Handle an incoming request.\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        $server = $request->attributes->get('server');\n        $node = $server->getRelation('node');\n\n        if ($node->maintenance_mode) {\n            return $this->response->view('errors.maintenance');\n        }\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/RedirectIfAuthenticated.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Auth\\AuthManager;\n\nclass RedirectIfAuthenticated\n{\n    /**\n     * RedirectIfAuthenticated constructor.\n     */\n    public function __construct(private AuthManager $authManager)\n    {\n    }\n\n    /**\n     * Handle an incoming request.\n     */\n    public function handle(Request $request, \\Closure $next, ?string $guard = null): mixed\n    {\n        if ($this->authManager->guard($guard)->check()) {\n            return redirect()->route('index');\n        }\n\n        return $next($request);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/RequireTwoFactorAuthentication.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Http\\Request;\nuse Prologue\\Alerts\\AlertsMessageBag;\nuse Pterodactyl\\Exceptions\\Http\\TwoFactorAuthRequiredException;\n\nclass RequireTwoFactorAuthentication\n{\n    public const LEVEL_NONE = 0;\n    public const LEVEL_ADMIN = 1;\n    public const LEVEL_ALL = 2;\n\n    /**\n     * The route to redirect a user to enable 2FA.\n     */\n    protected string $redirectRoute = '/account';\n\n    /**\n     * RequireTwoFactorAuthentication constructor.\n     */\n    public function __construct(private AlertsMessageBag $alert)\n    {\n    }\n\n    /**\n     * Check the user state on the incoming request to determine if they should be allowed to\n     * proceed or not. This checks if the Panel is configured to require 2FA on an account in\n     * order to perform actions. If so, we check the level at which it is required (all users\n     * or just admins) and then check if the user has enabled it for their account.\n     *\n     * @throws TwoFactorAuthRequiredException\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        $user = $request->user();\n        $uri = rtrim($request->getRequestUri(), '/') . '/';\n        $current = $request->route()->getName();\n\n        if (!$user || Str::startsWith($uri, ['/auth/']) || Str::startsWith($current, ['auth.', 'account.'])) {\n            return $next($request);\n        }\n\n        $level = (int) config('pterodactyl.auth.2fa_required');\n        // If this setting is not configured, or the user is already using 2FA then we can just\n        // send them right through, nothing else needs to be checked.\n        //\n        // If the level is set as admin and the user is not an admin, pass them through as well.\n        if ($level === self::LEVEL_NONE || $user->use_totp) {\n            return $next($request);\n        } elseif ($level === self::LEVEL_ADMIN && !$user->root_admin) {\n            return $next($request);\n        }\n\n        // For API calls return an exception which gets rendered nicely in the API response.\n        if ($request->isJson() || Str::startsWith($uri, '/api/')) {\n            throw new TwoFactorAuthRequiredException();\n        }\n\n        $this->alert->danger(trans('auth.2fa_must_be_enabled'))->flash();\n\n        return redirect()->to($this->redirectRoute);\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/SetSecurityHeaders.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse Illuminate\\Http\\Request;\n\nclass SetSecurityHeaders\n{\n    /**\n     * Ideally we move away from X-Frame-Options/X-XSS-Protection and implement a\n     * proper standard CSP, but I can guarantee that will break for a lot of folks\n     * using custom plugins and who knows what image embeds.\n     *\n     * We'll circle back to that at a later date when it can be more fully controlled\n     * by the admin to support those cases without too much trouble.\n     */\n    private static array $headers = [\n        'X-Frame-Options' => 'DENY',\n        'X-Content-Type-Options' => 'nosniff',\n        'X-XSS-Protection' => '1; mode=block',\n        'Referrer-Policy' => 'no-referrer-when-downgrade',\n    ];\n\n    /**\n     * Enforces some basic security headers on all responses returned by the software.\n     * If a header has already been set in another location within the code it will be\n     * skipped over here.\n     *\n     * @param (\\Closure(mixed): \\Illuminate\\Http\\Response) $next\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        $response = $next($request);\n\n        foreach (static::$headers as $key => $value) {\n            if (! $response->headers->has($key)) {\n                $response->headers->set($key, $value);\n            }\n        }\n\n        return $response;\n    }\n}\n"
  },
  {
    "path": "app/Http/Middleware/TrimStrings.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse Illuminate\\Foundation\\Http\\Middleware\\TrimStrings as BaseTrimmer;\n\nclass TrimStrings extends BaseTrimmer\n{\n    /**\n     * The names of the attributes that should not be trimmed.\n     */\n    protected $except = [\n        'password',\n        'password_confirmation',\n    ];\n}\n"
  },
  {
    "path": "app/Http/Middleware/VerifyCsrfToken.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse Illuminate\\Foundation\\Http\\Middleware\\VerifyCsrfToken as BaseVerifier;\n\nclass VerifyCsrfToken extends BaseVerifier\n{\n    /**\n     * The URIs that should be excluded from CSRF verification. These are\n     * never hit by the front-end, and require specific token validation\n     * to work.\n     */\n    protected $except = ['remote/*', 'daemon/*'];\n}\n"
  },
  {
    "path": "app/Http/Middleware/VerifyReCaptcha.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Middleware;\n\nuse GuzzleHttp\\Client;\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Events\\Auth\\FailedCaptcha;\nuse Illuminate\\Contracts\\Config\\Repository;\nuse Illuminate\\Contracts\\Events\\Dispatcher;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpException;\n\nclass VerifyReCaptcha\n{\n    /**\n     * VerifyReCaptcha constructor.\n     */\n    public function __construct(private Dispatcher $dispatcher, private Repository $config)\n    {\n    }\n\n    /**\n     * Handle an incoming request.\n     */\n    public function handle(Request $request, \\Closure $next): mixed\n    {\n        if (!$this->config->get('recaptcha.enabled')) {\n            return $next($request);\n        }\n\n        if ($request->filled('g-recaptcha-response')) {\n            $client = new Client();\n            $res = $client->post($this->config->get('recaptcha.domain'), [\n                'form_params' => [\n                    'secret' => $this->config->get('recaptcha.secret_key'),\n                    'response' => $request->input('g-recaptcha-response'),\n                ],\n            ]);\n\n            if ($res->getStatusCode() === 200) {\n                $result = json_decode($res->getBody());\n\n                if ($result->success && (!$this->config->get('recaptcha.verify_domain') || $this->isResponseVerified($result, $request))) {\n                    return $next($request);\n                }\n            }\n        }\n\n        $this->dispatcher->dispatch(\n            new FailedCaptcha(\n                $request->ip(),\n                !empty($result) ? ($result->hostname ?? null) : null\n            )\n        );\n\n        throw new HttpException(Response::HTTP_BAD_REQUEST, '验证 reCAPTCHA 数据失败。');\n    }\n\n    /**\n     * Determine if the response from the recaptcha servers was valid.\n     */\n    private function isResponseVerified(\\stdClass $result, Request $request): bool\n    {\n        if (!$this->config->get('recaptcha.verify_domain')) {\n            return false;\n        }\n\n        $url = parse_url($request->url());\n\n        return $result->hostname === array_get($url, 'host');\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/AdminFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin;\n\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nabstract class AdminFormRequest extends FormRequest\n{\n    /**\n     * The rules to apply to the incoming form request.\n     */\n    abstract public function rules(): array;\n\n    /**\n     * Determine if the user is an admin and has permission to access this\n     * form controller in the first place.\n     */\n    public function authorize(): bool\n    {\n        if (is_null($this->user())) {\n            return false;\n        }\n\n        return (bool) $this->user()->root_admin;\n    }\n\n    /**\n     * Return only the fields that we are interested in from the request.\n     * This will include empty fields as a null value.\n     */\n    public function normalize(?array $only = null): array\n    {\n        return $this->only($only ?? array_keys($this->rules()));\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Api/StoreApplicationApiKeyRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Api;\n\nuse Pterodactyl\\Models\\ApiKey;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass StoreApplicationApiKeyRequest extends AdminFormRequest\n{\n    /**\n     * @throws \\ReflectionException\n     * @throws \\ReflectionException\n     */\n    public function rules(): array\n    {\n        $modelRules = ApiKey::getRules();\n\n        return collect(AdminAcl::getResourceList())->mapWithKeys(function ($resource) use ($modelRules) {\n            return [AdminAcl::COLUMN_IDENTIFIER . $resource => $modelRules['r_' . $resource]];\n        })->merge(['memo' => $modelRules['memo']])->toArray();\n    }\n\n    public function attributes(): array\n    {\n        return [\n            'memo' => 'Description',\n        ];\n    }\n\n    public function getKeyPermissions(): array\n    {\n        return collect($this->validated())->filter(function ($value, $key) {\n            return substr($key, 0, strlen(AdminAcl::COLUMN_IDENTIFIER)) === AdminAcl::COLUMN_IDENTIFIER;\n        })->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/BaseFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin;\n\nclass BaseFormRequest extends AdminFormRequest\n{\n    public function rules(): array\n    {\n        return [\n            'company' => 'required|between:1,256',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/DatabaseHostFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin;\n\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Illuminate\\Contracts\\Validation\\Validator;\n\nclass DatabaseHostFormRequest extends AdminFormRequest\n{\n    public function rules(): array\n    {\n        if ($this->method() !== 'POST') {\n            return DatabaseHost::getRulesForUpdate($this->route()->parameter('host'));\n        }\n\n        return DatabaseHost::getRules();\n    }\n\n    /**\n     * Modify submitted data before it is passed off to the validator.\n     */\n    protected function getValidatorInstance(): Validator\n    {\n        if (!$this->filled('node_id')) {\n            $this->merge(['node_id' => null]);\n        }\n\n        return parent::getValidatorInstance();\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Egg/EggFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Egg;\n\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass EggFormRequest extends AdminFormRequest\n{\n    public function rules(): array\n    {\n        $rules = [\n            'name' => 'required|string|max:191',\n            'description' => 'nullable|string',\n            'docker_images' => ['required', 'string'],\n            'force_outgoing_ip' => 'sometimes|boolean',\n            'file_denylist' => 'array',\n            'features' => 'sometimes|array',\n            'startup' => 'required|string',\n            'config_from' => 'sometimes|bail|nullable|numeric',\n            'config_stop' => 'required_without:config_from|nullable|string|max:191',\n            'config_startup' => 'required_without:config_from|nullable|json',\n            'config_logs' => 'required_without:config_from|nullable|json',\n            'config_files' => 'required_without:config_from|nullable|json',\n        ];\n\n        if ($this->method() === 'POST') {\n            $rules['nest_id'] = 'required|numeric|exists:nests,id';\n        }\n\n        return $rules;\n    }\n\n    public function withValidator($validator)\n    {\n        $validator->sometimes('config_from', 'exists:eggs,id', function () {\n            return (int) $this->input('config_from') !== 0;\n        });\n    }\n\n    public function validated($key = null, $default = null): array\n    {\n        $data = parent::validated();\n\n        return array_merge($data, [\n            'force_outgoing_ip' => array_get($data, 'force_outgoing_ip', false),\n            'features' => array_get($data, 'features', []),\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Egg/EggImportFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Egg;\n\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass EggImportFormRequest extends AdminFormRequest\n{\n    public function rules(): array\n    {\n        $rules = [\n            'import_file' => 'bail|required|file|max:1000|mimetypes:application/json,text/plain',\n        ];\n\n        if ($this->method() !== 'PUT') {\n            $rules['import_to_nest'] = 'bail|required|integer|exists:nests,id';\n        }\n\n        return $rules;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Egg/EggScriptFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Egg;\n\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass EggScriptFormRequest extends AdminFormRequest\n{\n    /**\n     * Return the rules to be used when validating the data sent in the request.\n     */\n    public function rules(): array\n    {\n        return [\n            'script_install' => 'sometimes|nullable|string',\n            'script_is_privileged' => 'sometimes|required|boolean',\n            'script_entry' => 'sometimes|required|string',\n            'script_container' => 'sometimes|required|string',\n            'copy_script_from' => 'sometimes|nullable|numeric',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Egg/EggVariableFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Egg;\n\nuse Pterodactyl\\Models\\EggVariable;\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass EggVariableFormRequest extends AdminFormRequest\n{\n    /**\n     * Define rules for validation of this request.\n     */\n    public function rules(): array\n    {\n        return [\n            'name' => 'required|string|min:1|max:191',\n            'description' => 'sometimes|nullable|string',\n            'env_variable' => 'required|regex:/^[\\w]{1,191}$/|notIn:' . EggVariable::RESERVED_ENV_NAMES,\n            'options' => 'sometimes|required|array',\n            'rules' => 'bail|required|string',\n            'default_value' => 'present',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/LocationFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin;\n\nuse Pterodactyl\\Models\\Location;\n\nclass LocationFormRequest extends AdminFormRequest\n{\n    /**\n     * Set up the validation rules to use for these requests.\n     */\n    public function rules(): array\n    {\n        if ($this->method() === 'PATCH') {\n            return Location::getRulesForUpdate($this->route()->parameter('location')->id); // @phpstan-ignore property.nonObject\n        }\n\n        return Location::getRules();\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/MountFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin;\n\nuse Pterodactyl\\Models\\Mount;\n\nclass MountFormRequest extends AdminFormRequest\n{\n    /**\n     * Set up the validation rules to use for these requests.\n     */\n    public function rules(): array\n    {\n        if ($this->method() === 'PATCH') {\n            return Mount::getRulesForUpdate($this->route()->parameter('mount')->id); // @phpstan-ignore property.nonObject\n        }\n\n        return Mount::getRules();\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Nest/StoreNestFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Nest;\n\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass StoreNestFormRequest extends AdminFormRequest\n{\n    public function rules(): array\n    {\n        return [\n            'name' => 'required|string|min:1|max:191|regex:/^[\\w\\- ]+$/',\n            'description' => 'string|nullable',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/NewUserFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Support\\Collection;\n\nclass NewUserFormRequest extends AdminFormRequest\n{\n    /**\n     * Rules to apply to requests for updating or creating a user\n     * in the Admin CP.\n     */\n    public function rules(): array\n    {\n        return Collection::make(\n            User::getRules()\n        )->only([\n            'email',\n            'username',\n            'name_first',\n            'name_last',\n            'password',\n            'language',\n            'root_admin',\n        ])->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Node/AllocationAliasFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Node;\n\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass AllocationAliasFormRequest extends AdminFormRequest\n{\n    public function rules(): array\n    {\n        return [\n            'alias' => 'present|nullable|string',\n            'allocation_id' => 'required|numeric|exists:allocations,id',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Node/AllocationFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Node;\n\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass AllocationFormRequest extends AdminFormRequest\n{\n    public function rules(): array\n    {\n        return [\n            'allocation_ip' => 'required|string',\n            'allocation_alias' => 'sometimes|nullable|string|max:191',\n            'allocation_ports' => 'required|array',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Node/NodeFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Node;\n\nuse Pterodactyl\\Rules\\Fqdn;\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass NodeFormRequest extends AdminFormRequest\n{\n    /**\n     * Get rules to apply to data in this request.\n     */\n    public function rules(): array\n    {\n        if ($this->method() === 'PATCH') {\n            return Node::getRulesForUpdate($this->route()->parameter('node'));\n        }\n\n        $data = Node::getRules();\n        $data['fqdn'][] = Fqdn::make('scheme');\n\n        return $data;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/ServerFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin;\n\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Validation\\Rule;\nuse Illuminate\\Validation\\Validator;\n\nclass ServerFormRequest extends AdminFormRequest\n{\n    /**\n     * Rules to be applied to this request.\n     */\n    public function rules(): array\n    {\n        $rules = Server::getRules();\n        $rules['description'][] = 'nullable';\n        $rules['custom_image'] = 'sometimes|nullable|string';\n\n        return $rules;\n    }\n\n    /**\n     * Run validation after the rules above have been applied.\n     */\n    public function withValidator(Validator $validator): void\n    {\n        $validator->after(function ($validator) {\n            $validator->sometimes('node_id', 'required|numeric|bail|exists:nodes,id', function ($input) {\n                return !$input->auto_deploy;\n            });\n\n            $validator->sometimes('allocation_id', [\n                'required',\n                'numeric',\n                'bail',\n                Rule::exists('allocations', 'id')->where(function ($query) {\n                    $query->where('node_id', $this->input('node_id'));\n                    $query->whereNull('server_id');\n                }),\n            ], function ($input) {\n                return !$input->auto_deploy;\n            });\n\n            $validator->sometimes('allocation_additional.*', [\n                'sometimes',\n                'required',\n                'numeric',\n                Rule::exists('allocations', 'id')->where(function ($query) {\n                    $query->where('node_id', $this->input('node_id'));\n                    $query->whereNull('server_id');\n                }),\n            ], function ($input) {\n                return !$input->auto_deploy;\n            });\n        });\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Servers/Databases/StoreServerDatabaseRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Servers\\Databases;\n\nuse Illuminate\\Validation\\Rule;\nuse Illuminate\\Database\\Query\\Builder;\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass StoreServerDatabaseRequest extends AdminFormRequest\n{\n    /**\n     * Validation rules for database creation.\n     */\n    public function rules(): array\n    {\n        return [\n            'database' => [\n                'required',\n                'string',\n                'min:1',\n                'max:24',\n                Rule::unique('databases')->where(function (Builder $query) {\n                    $query->where('database_host_id', $this->input('database_host_id') ?? 0);\n                }),\n            ],\n            'max_connections' => 'nullable',\n            'remote' => 'required|string|regex:/^[0-9%.]{1,15}$/',\n            'database_host_id' => 'required|integer|exists:database_hosts,id',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Settings/AdvancedSettingsFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Settings;\n\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass AdvancedSettingsFormRequest extends AdminFormRequest\n{\n    /**\n     * Return all the rules to apply to this request's data.\n     */\n    public function rules(): array\n    {\n        return [\n            'icp:enabled' => 'required|in:true,false',\n            'icp:record' => 'nullable|required_if:icp:enabled,true|string|max:100',\n            'icp:security_record' => 'nullable|string|max:100',\n            'recaptcha:enabled' => 'required|in:true,false',\n            'recaptcha:secret_key' => 'required|string|max:191',\n            'recaptcha:website_key' => 'required|string|max:191',\n            'pterodactyl:guzzle:timeout' => 'required|integer|between:1,60',\n            'pterodactyl:guzzle:connect_timeout' => 'required|integer|between:1,60',\n            'pterodactyl:client_features:allocations:enabled' => 'required|in:true,false',\n            'pterodactyl:client_features:allocations:range_start' => [\n                'nullable',\n                'required_if:pterodactyl:client_features:allocations:enabled,true',\n                'integer',\n                'between:1024,65535',\n            ],\n            'pterodactyl:client_features:allocations:range_end' => [\n                'nullable',\n                'required_if:pterodactyl:client_features:allocations:enabled,true',\n                'integer',\n                'between:1024,65535',\n                'gt:pterodactyl:client_features:allocations:range_start',\n            ],\n            'pterodactyl:client_features:allocations:consecutive_enabled' => 'required|in:true,false',\n            'pterodactyl:client_features:allocations:consecutive_limit' => [\n                'required_if:pterodactyl:client_features:allocations:consecutive_enabled,true',\n                'nullable',\n                'integer',\n                'between:2,10',\n            ],\n            'pterodactyl:client_features:egg_change:mode' => 'required|in:disabled,egg_only,both',\n        ];\n    }\n\n    public function attributes(): array\n    {\n        return [\n            'icp:enabled' => 'ICP record Enabled',\n            'icp:record' => '苏ICP备1000000号',\n            'icp:security_record' => '苏公网安备10000000000000号',\n            'recaptcha:enabled' => 'reCAPTCHA Enabled',\n            'recaptcha:secret_key' => 'reCAPTCHA Secret Key',\n            'recaptcha:website_key' => 'reCAPTCHA Website Key',\n            'pterodactyl:guzzle:timeout' => 'HTTP Request Timeout',\n            'pterodactyl:guzzle:connect_timeout' => 'HTTP Connection Timeout',\n            'pterodactyl:client_features:allocations:enabled' => 'Auto Create Allocations Enabled',\n            'pterodactyl:client_features:allocations:range_start' => 'Starting Port',\n            'pterodactyl:client_features:allocations:range_end' => 'Ending Port',\n            'pterodactyl:client_features:allocations:consecutive_enabled' => 'Consecutive Port Creation Enabled',\n            'pterodactyl:client_features:allocations:consecutive_limit' => 'Max Consecutive Ports',\n            'pterodactyl:client_features:egg_change:mode' => 'Allow Egg Change Mode',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Settings/BaseSettingsFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Settings;\n\nuse Illuminate\\Validation\\Rule;\nuse Pterodactyl\\Traits\\Helpers\\AvailableLanguages;\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass BaseSettingsFormRequest extends AdminFormRequest\n{\n    use AvailableLanguages;\n\n    public function rules(): array\n    {\n        return [\n            'app:name' => 'required|string|max:191',\n            'pterodactyl:auth:2fa_required' => 'required|integer|in:0,1,2',\n            'app:locale' => ['required', 'string', Rule::in(array_keys($this->getAvailableLanguages()))],\n            'logo:title' => 'nullable|string',\n            'logo:favicon' => 'nullable|string',\n            'logo:auth' => 'nullable|string',\n        ];\n    }\n\n    public function attributes(): array\n    {\n        return [\n            'app:name' => '公司名称',\n            'pterodactyl:auth:2fa_required' => '要求动态口令认证登录',\n            'app:locale' => '默认语言',\n            'logo:title' => '',\n            'logo:favicon' => '/favicons/favicon.ico',\n            'logo:auth' => '',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/Settings/MailSettingsFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin\\Settings;\n\nuse Illuminate\\Validation\\Rule;\nuse Pterodactyl\\Http\\Requests\\Admin\\AdminFormRequest;\n\nclass MailSettingsFormRequest extends AdminFormRequest\n{\n    /**\n     * Return rules to validate mail settings POST data against.\n     */\n    public function rules(): array\n    {\n        return [\n            'mail:mailers:smtp:host' => 'required|string',\n            'mail:mailers:smtp:port' => 'required|integer|between:1,65535',\n            'mail:mailers:smtp:encryption' => ['present', Rule::in([null, 'tls', 'ssl'])],\n            'mail:mailers:smtp:username' => 'nullable|string|max:191',\n            'mail:mailers:smtp:password' => 'nullable|string|max:191',\n            'mail:from:address' => 'required|string|email',\n            'mail:from:name' => 'nullable|string|max:191',\n        ];\n    }\n\n    /**\n     * Override the default normalization function for this type of request\n     * as we need to accept empty values on the keys.\n     */\n    public function normalize(?array $only = null): array\n    {\n        $keys = array_flip(array_keys($this->rules()));\n\n        if (empty($this->input('mail:mailers:smtp:password'))) {\n            unset($keys['mail:mailers:smtp:password']);\n        }\n\n        return $this->only(array_flip($keys));\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Admin/UserFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Admin;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Support\\Collection;\n\nclass UserFormRequest extends AdminFormRequest\n{\n    /**\n     * Rules to apply to requests for updating or creating a user\n     * in the Admin CP.\n     */\n    public function rules(): array\n    {\n        return Collection::make(\n            User::getRulesForUpdate($this->route()->parameter('user'))\n        )->only([\n            'email',\n            'username',\n            'name_first',\n            'name_last',\n            'password',\n            'language',\n            'root_admin',\n        ])->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Allocations/DeleteAllocationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Allocations;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass DeleteAllocationRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_ALLOCATIONS;\n\n    protected int $permission = AdminAcl::WRITE;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Allocations/GetAllocationsRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Allocations;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetAllocationsRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_ALLOCATIONS;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Allocations/StoreAllocationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Allocations;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass StoreAllocationRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_ALLOCATIONS;\n\n    protected int $permission = AdminAcl::WRITE;\n\n    public function rules(): array\n    {\n        return [\n            'ip' => 'required|string',\n            'alias' => 'sometimes|nullable|string|max:191',\n            'ports' => 'required|array',\n            'ports.*' => 'string',\n        ];\n    }\n\n    public function validated($key = null, $default = null): array\n    {\n        $data = parent::validated();\n\n        return [\n            'allocation_ip' => $data['ip'],\n            'allocation_ports' => $data['ports'],\n            'allocation_alias' => $data['alias'] ?? null,\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/ApplicationApiRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\ApiKey;\nuse Laravel\\Sanctum\\TransientToken;\nuse Illuminate\\Validation\\Validator;\nuse Illuminate\\Database\\Eloquent\\Model;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Illuminate\\Foundation\\Http\\FormRequest;\nuse Pterodactyl\\Exceptions\\PterodactylException;\n\nabstract class ApplicationApiRequest extends FormRequest\n{\n    /**\n     * The resource that should be checked when performing the authorization\n     * function for this request.\n     */\n    protected ?string $resource;\n\n    /**\n     * The permission level that a given API key should have for accessing\n     * the defined $resource during the request cycle.\n     */\n    protected int $permission = AdminAcl::NONE;\n\n    /**\n     * Determine if the current user is authorized to perform\n     * the requested action against the API.\n     *\n     * @throws PterodactylException\n     */\n    public function authorize(): bool\n    {\n        if (is_null($this->resource)) {\n            throw new PterodactylException('An ACL resource must be defined on API requests.');\n        }\n\n        $token = $this->user()->currentAccessToken();\n        if ($token instanceof TransientToken) { // @phpstan-ignore instanceof.alwaysFalse\n            return true;\n        }\n\n        if ($token->key_type === ApiKey::TYPE_ACCOUNT) {\n            return true;\n        }\n\n        return AdminAcl::check($token, $this->resource, $this->permission);\n    }\n\n    /**\n     * Default set of rules to apply to API requests.\n     */\n    public function rules(): array\n    {\n        return [];\n    }\n\n    /**\n     * Helper method allowing a developer to easily hook into this logic without having\n     * to remember what the method name is called or where to use it. By default this is\n     * a no-op.\n     */\n    public function withValidator(Validator $validator): void\n    {\n        // do nothing\n    }\n\n    /**\n     * Returns the named route parameter and asserts that it is a real model that\n     * exists in the database.\n     *\n     * @template T of \\Illuminate\\Database\\Eloquent\\Model\n     *\n     * @param class-string<T> $expect\n     *\n     * @return T\n     *\n     * @noinspection PhpDocSignatureInspection\n     */\n    public function parameter(string $key, string $expect)\n    {\n        $value = $this->route()->parameter($key);\n\n        Assert::isInstanceOf($value, $expect);\n        Assert::isInstanceOf($value, Model::class); // @phpstan-ignore staticMethod.alreadyNarrowedType\n        Assert::true($value->exists);\n\n        /* @var T $value */\n        return $value;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Locations/DeleteLocationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Locations;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass DeleteLocationRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_LOCATIONS;\n\n    protected int $permission = AdminAcl::WRITE;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Locations/GetLocationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Locations;\n\nclass GetLocationRequest extends GetLocationsRequest\n{\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Locations/GetLocationsRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Locations;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetLocationsRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_LOCATIONS;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Locations/StoreLocationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Locations;\n\nuse Pterodactyl\\Models\\Location;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass StoreLocationRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_LOCATIONS;\n\n    protected int $permission = AdminAcl::WRITE;\n\n    /**\n     * Rules to validate the request against.\n     */\n    public function rules(): array\n    {\n        return collect(Location::getRules())->only([\n            'long',\n            'short',\n        ])->toArray();\n    }\n\n    /**\n     * Rename fields to be more clear in error messages.\n     */\n    public function attributes(): array\n    {\n        return [\n            'long' => 'Location Description',\n            'short' => 'Location Identifier',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Locations/UpdateLocationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Locations;\n\nuse Pterodactyl\\Models\\Location;\n\nclass UpdateLocationRequest extends StoreLocationRequest\n{\n    /**\n     * Rules to validate this request against.\n     */\n    public function rules(): array\n    {\n        $locationId = $this->route()->parameter('location')->id; // @phpstan-ignore property.nonObject\n\n        return collect(Location::getRulesForUpdate($locationId))->only([\n            'short',\n            'long',\n        ])->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Nests/Eggs/GetEggRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Nests\\Eggs;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetEggRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_EGGS;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Nests/Eggs/GetEggsRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Nests\\Eggs;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetEggsRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_EGGS;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Nests/GetNestsRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Nests;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetNestsRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_NESTS;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Nodes/DeleteNodeRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass DeleteNodeRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_NODES;\n\n    protected int $permission = AdminAcl::WRITE;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Nodes/GetDeployableNodesRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes;\n\nclass GetDeployableNodesRequest extends GetNodesRequest\n{\n    public function rules(): array\n    {\n        return [\n            'page' => 'integer',\n            'memory' => 'required|integer|min:0',\n            'disk' => 'required|integer|min:0',\n            'location_ids' => 'array',\n            'location_ids.*' => 'integer',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Nodes/GetNodeRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes;\n\nclass GetNodeRequest extends GetNodesRequest\n{\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Nodes/GetNodesRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetNodesRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_NODES;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Nodes/StoreNodeRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes;\n\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass StoreNodeRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_NODES;\n\n    protected int $permission = AdminAcl::WRITE;\n\n    /**\n     * Validation rules to apply to this request.\n     */\n    public function rules(?array $rules = null): array\n    {\n        return collect($rules ?? Node::getRules())->only([\n            'public',\n            'name',\n            'description',\n            'location_id',\n            'fqdn',\n            'scheme',\n            'behind_proxy',\n            'maintenance_mode',\n            'memory',\n            'memory_overallocate',\n            'disk',\n            'disk_overallocate',\n            'upload_size',\n            'daemonListen',\n            'daemonSFTP',\n            'daemonBase',\n        ])->mapWithKeys(function ($value, $key) {\n            $key = ($key === 'daemonSFTP') ? 'daemonSftp' : $key;\n\n            return [snake_case($key) => $value];\n        })->toArray();\n    }\n\n    /**\n     * Fields to rename for clarity in the API response.\n     */\n    public function attributes(): array\n    {\n        return [\n            'daemon_base' => 'Daemon Base Path',\n            'upload_size' => 'File Upload Size Limit',\n            'location_id' => 'Location',\n            'public' => 'Node Visibility',\n        ];\n    }\n\n    /**\n     * Change the formatting of some data keys in the validated response data\n     * to match what the application expects in the services.\n     */\n    public function validated($key = null, $default = null): array\n    {\n        $response = parent::validated();\n        $response['daemonListen'] = $response['daemon_listen'];\n        $response['daemonSFTP'] = $response['daemon_sftp'];\n        $response['daemonBase'] = $response['daemon_base'] ?? (new Node())->getAttribute('daemonBase');\n\n        unset($response['daemon_base'], $response['daemon_listen'], $response['daemon_sftp']);\n\n        return $response;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Nodes/UpdateNodeRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Nodes;\n\nuse Pterodactyl\\Models\\Node;\n\nclass UpdateNodeRequest extends StoreNodeRequest\n{\n    /**\n     * Apply validation rules to this request. Uses the parent class rules()\n     * function but passes in the rules for updating rather than creating.\n     */\n    public function rules(?array $rules = null): array\n    {\n        $node = $this->parameter('node', Node::class);\n\n        return parent::rules(Node::getRulesForUpdate($node));\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/Databases/GetServerDatabaseRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\Databases;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetServerDatabaseRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_SERVER_DATABASES;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/Databases/GetServerDatabasesRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\Databases;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetServerDatabasesRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_SERVER_DATABASES;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/Databases/ServerDatabaseWriteRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\Databases;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass ServerDatabaseWriteRequest extends GetServerDatabasesRequest\n{\n    protected int $permission = AdminAcl::WRITE;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/Databases/StoreServerDatabaseRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers\\Databases;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Validation\\Rule;\nuse Illuminate\\Database\\Query\\Builder;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Services\\Databases\\DatabaseManagementService;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass StoreServerDatabaseRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_SERVER_DATABASES;\n\n    protected int $permission = AdminAcl::WRITE;\n\n    /**\n     * Validation rules for database creation.\n     */\n    public function rules(): array\n    {\n        $server = $this->parameter('server', Server::class);\n\n        return [\n            'database' => [\n                'required',\n                'alpha_dash',\n                'min:1',\n                'max:48',\n                Rule::unique('databases')->where(function (Builder $query) use ($server) {\n                    $query->where('server_id', $server->id)->where('database', $this->databaseName());\n                }),\n            ],\n            'remote' => 'required|string|regex:/^[0-9%.]{1,15}$/',\n            'host' => 'required|integer|exists:database_hosts,id',\n        ];\n    }\n\n    /**\n     * Return data formatted in the correct format for the service to consume.\n     */\n    public function validated($key = null, $default = null): array\n    {\n        return [\n            'database' => $this->input('database'),\n            'remote' => $this->input('remote'),\n            'database_host_id' => $this->input('host'),\n        ];\n    }\n\n    /**\n     * Format error messages in a more understandable format for API output.\n     */\n    public function attributes(): array\n    {\n        return [\n            'host' => 'Database Host Server ID',\n            'remote' => 'Remote Connection String',\n            'database' => 'Database Name',\n        ];\n    }\n\n    /**\n     * Returns the database name in the expected format.\n     */\n    public function databaseName(): string\n    {\n        $server = $this->route()->parameter('server');\n\n        Assert::isInstanceOf($server, Server::class);\n\n        return DatabaseManagementService::generateUniqueDatabaseName($this->input('database'), $server->id);\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/GetExternalServerRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetExternalServerRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_SERVERS;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/GetServerRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetServerRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_SERVERS;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/GetServersRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers;\n\nclass GetServersRequest extends GetServerRequest\n{\n    public function rules(): array\n    {\n        return [\n            'search' => 'string|max:100',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/ServerWriteRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass ServerWriteRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_SERVERS;\n\n    protected int $permission = AdminAcl::WRITE;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/StoreServerRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers;\n\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Validation\\Rule;\nuse Illuminate\\Validation\\Validator;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Models\\Objects\\DeploymentObject;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass StoreServerRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_SERVERS;\n\n    protected int $permission = AdminAcl::WRITE;\n\n    /**\n     * Rules to be applied to this request.\n     */\n    public function rules(): array\n    {\n        $rules = Server::getRules();\n\n        return [\n            'external_id' => $rules['external_id'],\n            'name' => $rules['name'],\n            'description' => array_merge(['nullable'], $rules['description']),\n            'user' => $rules['owner_id'],\n            'egg' => $rules['egg_id'],\n            'docker_image' => $rules['image'],\n            'startup' => $rules['startup'],\n            'environment' => 'present|array',\n            'skip_scripts' => 'sometimes|boolean',\n            'oom_disabled' => 'sometimes|boolean',\n\n            // Resource limitations\n            'limits' => 'required|array',\n            'limits.memory' => $rules['memory'],\n            'limits.swap' => $rules['swap'],\n            'limits.disk' => $rules['disk'],\n            'limits.io' => $rules['io'],\n            'limits.threads' => $rules['threads'],\n            'limits.cpu' => $rules['cpu'],\n\n            // Application Resource Limits\n            'feature_limits' => 'required|array',\n            'feature_limits.databases' => $rules['database_limit'],\n            'feature_limits.allocations' => $rules['allocation_limit'],\n            'feature_limits.backups' => $rules['backup_limit'],\n\n            // Placeholders for rules added in withValidator() function.\n            'allocation.default' => '',\n            'allocation.additional.*' => '',\n\n            // Automatic deployment rules\n            'deploy' => 'sometimes|required|array',\n            'deploy.locations' => 'array',\n            'deploy.locations.*' => 'integer|min:1',\n            'deploy.dedicated_ip' => 'required_with:deploy,boolean',\n            'deploy.port_range' => 'array',\n            'deploy.port_range.*' => 'string',\n\n            'start_on_completion' => 'sometimes|boolean',\n        ];\n    }\n\n    /**\n     * Normalize the data into a format that can be consumed by the service.\n     */\n    public function validated($key = null, $default = null): array\n    {\n        $data = parent::validated();\n\n        return [\n            'external_id' => array_get($data, 'external_id'),\n            'name' => array_get($data, 'name'),\n            'description' => array_get($data, 'description'),\n            'owner_id' => array_get($data, 'user'),\n            'egg_id' => array_get($data, 'egg'),\n            'image' => array_get($data, 'docker_image'),\n            'startup' => array_get($data, 'startup'),\n            'environment' => array_get($data, 'environment'),\n            'memory' => array_get($data, 'limits.memory'),\n            'swap' => array_get($data, 'limits.swap'),\n            'disk' => array_get($data, 'limits.disk'),\n            'io' => array_get($data, 'limits.io'),\n            'cpu' => array_get($data, 'limits.cpu'),\n            'threads' => array_get($data, 'limits.threads'),\n            'skip_scripts' => array_get($data, 'skip_scripts', false),\n            'allocation_id' => array_get($data, 'allocation.default'),\n            'allocation_additional' => array_get($data, 'allocation.additional'),\n            'start_on_completion' => array_get($data, 'start_on_completion', false),\n            'database_limit' => array_get($data, 'feature_limits.databases'),\n            'allocation_limit' => array_get($data, 'feature_limits.allocations'),\n            'backup_limit' => array_get($data, 'feature_limits.backups'),\n            'oom_disabled' => array_get($data, 'oom_disabled'),\n        ];\n    }\n\n    /*\n     * Run validation after the rules above have been applied.\n     *\n     * @param \\Illuminate\\Validation\\Validator $validator\n     */\n    public function withValidator(Validator $validator): void\n    {\n        $validator->sometimes('allocation.default', [\n            'required', 'integer', 'bail',\n            Rule::exists('allocations', 'id')->where(function ($query) {\n                $query->whereNull('server_id');\n            }),\n        ], function ($input) {\n            return !$input->deploy;\n        });\n\n        $validator->sometimes('allocation.additional.*', [\n            'integer',\n            Rule::exists('allocations', 'id')->where(function ($query) {\n                $query->whereNull('server_id');\n            }),\n        ], function ($input) {\n            return !$input->deploy;\n        });\n\n        $validator->sometimes('deploy.locations', 'present', function ($input) {\n            return $input->deploy;\n        });\n\n        $validator->sometimes('deploy.port_range', 'present', function ($input) {\n            return $input->deploy;\n        });\n    }\n\n    /**\n     * Return a deployment object that can be passed to the server creation service.\n     */\n    public function getDeploymentObject(): ?DeploymentObject\n    {\n        if (is_null($this->input('deploy'))) {\n            return null;\n        }\n\n        $object = new DeploymentObject();\n        $object->setDedicated($this->input('deploy.dedicated_ip', false));\n        $object->setLocations($this->input('deploy.locations', []));\n        $object->setPorts($this->input('deploy.port_range', []));\n\n        return $object;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/UpdateServerBuildConfigurationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers;\n\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Support\\Collection;\n\nclass UpdateServerBuildConfigurationRequest extends ServerWriteRequest\n{\n    /**\n     * Return the rules to validate this request against.\n     */\n    public function rules(): array\n    {\n        $rules = Server::getRulesForUpdate($this->parameter('server', Server::class));\n\n        return [\n            'allocation' => $rules['allocation_id'],\n            'oom_disabled' => $rules['oom_disabled'],\n\n            'limits' => 'sometimes|array',\n            'limits.memory' => $this->requiredToOptional('memory', $rules['memory'], true),\n            'limits.swap' => $this->requiredToOptional('swap', $rules['swap'], true),\n            'limits.io' => $this->requiredToOptional('io', $rules['io'], true),\n            'limits.cpu' => $this->requiredToOptional('cpu', $rules['cpu'], true),\n            'limits.threads' => $this->requiredToOptional('threads', $rules['threads'], true),\n            'limits.disk' => $this->requiredToOptional('disk', $rules['disk'], true),\n\n            // Legacy rules to maintain backwards compatable API support without requiring\n            // a major version bump.\n            //\n            // @see https://github.com/pterodactyl/panel/issues/1500\n            'memory' => $this->requiredToOptional('memory', $rules['memory']),\n            'swap' => $this->requiredToOptional('swap', $rules['swap']),\n            'io' => $this->requiredToOptional('io', $rules['io']),\n            'cpu' => $this->requiredToOptional('cpu', $rules['cpu']),\n            'threads' => $this->requiredToOptional('threads', $rules['threads']),\n            'disk' => $this->requiredToOptional('disk', $rules['disk']),\n\n            'add_allocations' => 'bail|array',\n            'add_allocations.*' => 'integer',\n            'remove_allocations' => 'bail|array',\n            'remove_allocations.*' => 'integer',\n\n            'feature_limits' => 'required|array',\n            'feature_limits.databases' => $rules['database_limit'],\n            'feature_limits.allocations' => $rules['allocation_limit'],\n            'feature_limits.backups' => $rules['backup_limit'],\n        ];\n    }\n\n    /**\n     * Convert the allocation field into the expected format for the service handler.\n     */\n    public function validated($key = null, $default = null): array\n    {\n        $data = parent::validated();\n\n        $data['allocation_id'] = $data['allocation'];\n        $data['database_limit'] = $data['feature_limits']['databases'] ?? null;\n        $data['allocation_limit'] = $data['feature_limits']['allocations'] ?? null;\n        $data['backup_limit'] = $data['feature_limits']['backups'] ?? null;\n        unset($data['allocation'], $data['feature_limits']);\n\n        // Adjust the limits field to match what is expected by the model.\n        if (!empty($data['limits'])) {\n            foreach ($data['limits'] as $key => $value) {\n                $data[$key] = $value;\n            }\n\n            unset($data['limits']);\n        }\n\n        return $data;\n    }\n\n    /**\n     * Custom attributes to use in error message responses.\n     */\n    public function attributes(): array\n    {\n        return [\n            'add_allocations' => 'allocations to add',\n            'remove_allocations' => 'allocations to remove',\n            'add_allocations.*' => 'allocation to add',\n            'remove_allocations.*' => 'allocation to remove',\n            'feature_limits.databases' => 'Database Limit',\n            'feature_limits.allocations' => 'Allocation Limit',\n            'feature_limits.backups' => 'Backup Limit',\n        ];\n    }\n\n    /**\n     * Converts existing rules for certain limits into a format that maintains backwards\n     * compatability with the old API endpoint while also supporting a more correct API\n     * call.\n     *\n     * @see https://github.com/pterodactyl/panel/issues/1500\n     */\n    protected function requiredToOptional(string $field, array $rules, bool $limits = false): array\n    {\n        if (!in_array('required', $rules)) {\n            return $rules;\n        }\n\n        return (new Collection($rules))\n            ->filter(function ($value) {\n                return $value !== 'required';\n            })\n            ->prepend($limits ? 'required_with:limits' : 'required_without:limits')\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/UpdateServerDetailsRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers;\n\nuse Pterodactyl\\Models\\Server;\n\nclass UpdateServerDetailsRequest extends ServerWriteRequest\n{\n    /**\n     * Rules to apply to a server details update request.\n     */\n    public function rules(): array\n    {\n        $rules = Server::getRulesForUpdate($this->parameter('server', Server::class));\n\n        return [\n            'external_id' => $rules['external_id'],\n            'name' => $rules['name'],\n            'user' => $rules['owner_id'],\n            'description' => array_merge(['nullable'], $rules['description']),\n        ];\n    }\n\n    /**\n     * Convert the posted data into the correct format that is expected\n     * by the application.\n     */\n    public function validated($key = null, $default = null): array\n    {\n        return [\n            'external_id' => $this->input('external_id'),\n            'name' => $this->input('name'),\n            'owner_id' => $this->input('user'),\n            'description' => $this->input('description'),\n        ];\n    }\n\n    /**\n     * Rename some attributes in error messages to clarify the field\n     * being discussed.\n     */\n    public function attributes(): array\n    {\n        return [\n            'user' => 'User ID',\n            'name' => 'Server Name',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Servers/UpdateServerStartupRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Servers;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass UpdateServerStartupRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_SERVERS;\n\n    protected int $permission = AdminAcl::WRITE;\n\n    /**\n     * Validation rules to run the input against.\n     */\n    public function rules(): array\n    {\n        $data = Server::getRulesForUpdate($this->parameter('server', Server::class));\n\n        return [\n            'startup' => $data['startup'],\n            'environment' => 'present|array',\n            'egg' => $data['egg_id'],\n            'image' => $data['image'],\n            'skip_scripts' => 'present|boolean',\n        ];\n    }\n\n    /**\n     * Return the validated data in a format that is expected by the service.\n     */\n    public function validated($key = null, $default = null): array\n    {\n        $data = parent::validated();\n\n        return collect($data)->only(['startup', 'environment', 'skip_scripts'])->merge([\n            'egg_id' => array_get($data, 'egg'),\n            'docker_image' => array_get($data, 'image'),\n        ])->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Users/DeleteUserRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Users;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass DeleteUserRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_USERS;\n\n    protected int $permission = AdminAcl::WRITE;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Users/GetExternalUserRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Users;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetExternalUserRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_USERS;\n\n    protected int $permission = AdminAcl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Users/GetUsersRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Users;\n\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl as Acl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass GetUsersRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = Acl::RESOURCE_USERS;\n\n    protected int $permission = Acl::READ;\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Users/StoreUserRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Users;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\nclass StoreUserRequest extends ApplicationApiRequest\n{\n    protected ?string $resource = AdminAcl::RESOURCE_USERS;\n\n    protected int $permission = AdminAcl::WRITE;\n\n    /**\n     * Return the validation rules for this request.\n     */\n    public function rules(?array $rules = null): array\n    {\n        $rules = $rules ?? User::getRules();\n\n        $response = collect($rules)->only([\n            'external_id',\n            'email',\n            'username',\n            'password',\n            'language',\n            'root_admin',\n        ])->toArray();\n\n        $response['first_name'] = $rules['name_first'];\n        $response['last_name'] = $rules['name_last'];\n\n        return $response;\n    }\n\n    public function validated($key = null, $default = null): array\n    {\n        $data = parent::validated();\n\n        $data['name_first'] = $data['first_name'];\n        $data['name_last'] = $data['last_name'];\n\n        unset($data['first_name'], $data['last_name']);\n\n        return $data;\n    }\n\n    /**\n     * Rename some fields to be more user friendly.\n     */\n    public function attributes(): array\n    {\n        return [\n            'external_id' => '第三方识别码',\n            'name_first' => '名字',\n            'name_last' => '姓氏',\n            'root_admin' => '管理员状态',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Application/Users/UpdateUserRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Application\\Users;\n\nuse Pterodactyl\\Models\\User;\n\nclass UpdateUserRequest extends StoreUserRequest\n{\n    /**\n     * Return the validation rules for this request.\n     */\n    public function rules(?array $rules = null): array\n    {\n        $userId = $this->parameter('user', User::class)->id;\n\n        return parent::rules(User::getRulesForUpdate($userId));\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Account/StoreApiKeyRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Account;\n\nuse IPTools\\Range;\nuse Pterodactyl\\Models\\ApiKey;\nuse Illuminate\\Validation\\Validator;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass StoreApiKeyRequest extends ClientApiRequest\n{\n    public function rules(): array\n    {\n        $rules = ApiKey::getRules();\n\n        return [\n            'description' => $rules['memo'],\n            'allowed_ips' => [...$rules['allowed_ips'], 'max:50'],\n            'allowed_ips.*' => 'string',\n        ];\n    }\n\n    /**\n     * Check that each of the values entered is actually valid.\n     */\n    public function withValidator(Validator $validator): void\n    {\n        $validator->after(function (Validator $validator) {\n            if (!is_array($ips = $this->input('allowed_ips'))) {\n                return;\n            }\n\n            foreach ($ips as $index => $ip) {\n                $valid = false;\n                try {\n                    $valid = Range::parse($ip)->valid();\n                } catch (\\Exception $exception) {\n                    if ($exception->getMessage() !== 'Invalid IP address format') {\n                        throw $exception;\n                    }\n                } finally {\n                    $validator->errors()->addIf(!$valid, \"allowed_ips.{$index}\", '\"' . $ip . '\" is not a valid IP address or CIDR range.');\n                }\n            }\n        });\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Account/StoreSSHKeyRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Account;\n\nuse phpseclib3\\Crypt\\DSA;\nuse phpseclib3\\Crypt\\RSA;\nuse Pterodactyl\\Models\\UserSSHKey;\nuse Illuminate\\Validation\\Validator;\nuse phpseclib3\\Crypt\\PublicKeyLoader;\nuse phpseclib3\\Crypt\\Common\\PublicKey;\nuse phpseclib3\\Exception\\NoKeyLoadedException;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass StoreSSHKeyRequest extends ClientApiRequest\n{\n    protected ?PublicKey $key;\n\n    /**\n     * Returns the rules for this request.\n     */\n    public function rules(): array\n    {\n        return [\n            'name' => UserSSHKey::getRulesForField('name'),\n            'public_key' => UserSSHKey::getRulesForField('public_key'),\n        ];\n    }\n\n    /**\n     * Check to see if this SSH key has already been added to the user's account\n     * and if so return an error.\n     */\n    public function withValidator(Validator $validator): void\n    {\n        $validator->after(function () {\n            try {\n                $this->key = PublicKeyLoader::loadPublicKey($this->input('public_key'));\n            } catch (NoKeyLoadedException $exception) {\n                $this->validator->errors()->add('public_key', 'The public key provided is not valid.');\n\n                return;\n            }\n\n            if ($this->key instanceof DSA) {\n                $this->validator->errors()->add('public_key', 'DSA keys are not supported.');\n            }\n\n            if ($this->key instanceof RSA && $this->key->getLength() < 2048) {\n                $this->validator->errors()->add('public_key', 'RSA keys must be at least 2048 bytes in length.');\n            }\n\n            $fingerprint = $this->key->getFingerprint('sha256');\n            if ($this->user()->sshKeys()->where('fingerprint', $fingerprint)->exists()) {\n                $this->validator->errors()->add('public_key', 'The public key provided already exists on your account.');\n            }\n        });\n    }\n\n    /**\n     * Returns the public key but formatted in a consistent manner.\n     */\n    public function getPublicKey(): string\n    {\n        return $this->key->toString('PKCS8');\n    }\n\n    /**\n     * Returns the SHA256 fingerprint of the key provided.\n     */\n    public function getKeyFingerprint(): string\n    {\n        if (!$this->key) {\n            throw new \\Exception('The public key was not properly loaded for this request.');\n        }\n\n        return $this->key->getFingerprint('sha256');\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Account/UpdateEmailRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Account;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Contracts\\Hashing\\Hasher;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Pterodactyl\\Exceptions\\Http\\Base\\InvalidPasswordProvidedException;\n\nclass UpdateEmailRequest extends ClientApiRequest\n{\n    /**\n     * @throws InvalidPasswordProvidedException\n     */\n    public function authorize(): bool\n    {\n        if (!parent::authorize()) {\n            return false;\n        }\n\n        $hasher = Container::getInstance()->make(Hasher::class);\n\n        // Verify password matches when changing password or email.\n        if (!$hasher->check($this->input('password'), $this->user()->password)) {\n            throw new InvalidPasswordProvidedException(trans('validation.internal.invalid_password'));\n        }\n\n        return true;\n    }\n\n    public function rules(): array\n    {\n        $rules = User::getRulesForUpdate($this->user());\n\n        return ['email' => $rules['email']];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Account/UpdatePasswordRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Account;\n\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Contracts\\Hashing\\Hasher;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Pterodactyl\\Exceptions\\Http\\Base\\InvalidPasswordProvidedException;\n\nclass UpdatePasswordRequest extends ClientApiRequest\n{\n    /**\n     * @throws InvalidPasswordProvidedException\n     */\n    public function authorize(): bool\n    {\n        if (!parent::authorize()) {\n            return false;\n        }\n\n        $hasher = Container::getInstance()->make(Hasher::class);\n\n        // Verify password matches when changing password or email.\n        if (!$hasher->check($this->input('current_password'), $this->user()->password)) {\n            throw new InvalidPasswordProvidedException(trans('validation.internal.invalid_password'));\n        }\n\n        return true;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'password' => ['required', 'string', 'confirmed', 'min:8'],\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/ClientApiRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Application\\ApplicationApiRequest;\n\n/**\n * @method \\Pterodactyl\\Models\\User user($guard = null)\n */\nclass ClientApiRequest extends ApplicationApiRequest\n{\n    /**\n     * Determine if the current user is authorized to perform the requested action against the API.\n     */\n    public function authorize(): bool\n    {\n        if ($this instanceof ClientPermissionsRequest || method_exists($this, 'permission')) {\n            $server = $this->route()->parameter('server');\n\n            if ($server instanceof Server) {\n                return $this->user()->can($this->permission(), $server);\n            }\n\n            // If there is no server available on the reqest, trigger a failure since\n            // we expect there to be one at this point.\n            return false;\n        }\n\n        return true;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/GetServersRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client;\n\nclass GetServersRequest extends ClientApiRequest\n{\n    public function authorize(): bool\n    {\n        return true;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Backups/RestoreBackupRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Backups;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass RestoreBackupRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_BACKUP_RESTORE;\n    }\n\n    public function rules(): array\n    {\n        return ['truncate' => 'required|boolean'];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Backups/StoreBackupRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Backups;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass StoreBackupRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_BACKUP_CREATE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'name' => 'nullable|string|max:191',\n            'is_locked' => 'nullable|boolean',\n            'ignored' => 'nullable|string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Databases/DeleteDatabaseRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Databases;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass DeleteDatabaseRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_DATABASE_DELETE;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Databases/GetDatabasesRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Databases;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass GetDatabasesRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_DATABASE_READ;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Databases/RotatePasswordRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Databases;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass RotatePasswordRequest extends ClientApiRequest\n{\n    /**\n     * Check that the user has permission to rotate the password.\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_DATABASE_UPDATE;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Databases/StoreDatabaseRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Databases;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Validation\\Rule;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Database\\Query\\Builder;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Pterodactyl\\Services\\Databases\\DatabaseManagementService;\n\nclass StoreDatabaseRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_DATABASE_CREATE;\n    }\n\n    public function rules(): array\n    {\n        $server = $this->route()->parameter('server');\n\n        Assert::isInstanceOf($server, Server::class);\n\n        return [\n            'database' => [\n                'required',\n                'alpha_dash',\n                'min:3',\n                'max:48',\n                // Yes, I am aware that you could have the same database name across two unique hosts. However,\n                // I don't really care about that for this validation. We just want to make sure it is unique to\n                // the server itself. No need for complexity.\n                Rule::unique('databases')->where(function (Builder $query) use ($server) {\n                    $query->where('server_id', $server->id)\n                        ->where('database', DatabaseManagementService::generateUniqueDatabaseName($this->input('database'), $server->id));\n                }),\n            ],\n            'remote' => Database::getRulesForField('remote'),\n        ];\n    }\n\n    public function messages(): array\n    {\n        return [\n            'database.unique' => '你选择的数据库名已经被这个服务器使用。',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/ChmodFilesRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass ChmodFilesRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_UPDATE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'root' => 'required|nullable|string',\n            'files' => 'required|array',\n            'files.*.file' => 'required|string',\n            'files.*.mode' => 'required|numeric',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/CompressFilesRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass CompressFilesRequest extends ClientApiRequest\n{\n    /**\n     * Checks that the authenticated user is allowed to create archives for this server.\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_ARCHIVE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'root' => 'sometimes|nullable|string',\n            'files' => 'required|array',\n            'files.*' => 'string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/CopyFileRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass CopyFileRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_CREATE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'location' => 'required|string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/CreateFolderRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass CreateFolderRequest extends ClientApiRequest\n{\n    /**\n     * Checks that the authenticated user is allowed to create files on the server.\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_CREATE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'root' => 'sometimes|nullable|string',\n            'name' => 'required|string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/DecompressFilesRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass DecompressFilesRequest extends ClientApiRequest\n{\n    /**\n     * Checks that the authenticated user is allowed to create new files for the server. We don't\n     * rely on the archive permission here as it makes more sense to make sure the user can create\n     * additional files rather than make an archive.\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_CREATE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'root' => 'sometimes|nullable|string',\n            'file' => 'required|string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/DeleteFileRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass DeleteFileRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_DELETE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'root' => 'required|nullable|string',\n            'files' => 'required|array',\n            'files.*' => 'string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/DownloadFileRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass DownloadFileRequest extends ClientApiRequest\n{\n    /**\n     * Ensure that the user making this request has permission to download files\n     * from this server.\n     */\n    public function authorize(): bool\n    {\n        return $this->user()->can('file.read', $this->parameter('server', Server::class));\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/GetFileContentsRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass GetFileContentsRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    /**\n     * Returns the permissions string indicating which permission should be used to\n     * validate that the authenticated user has permission to perform this action aganist\n     * the given resource (server).\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_READ_CONTENT;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'file' => 'required|string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/ListFilesRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass ListFilesRequest extends ClientApiRequest\n{\n    /**\n     * Check that the user making this request to the API is authorized to list all\n     * the files that exist for a given server.\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_READ;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'directory' => 'sometimes|nullable|string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/PullFileRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass PullFileRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_CREATE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'url' => 'required|string|url',\n            'directory' => 'nullable|string',\n            'filename' => 'nullable|string',\n            'use_header' => 'boolean',\n            'foreground' => 'boolean',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/RenameFileRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass RenameFileRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    /**\n     * The permission the user is required to have in order to perform this\n     * request action.\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_UPDATE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'root' => 'required|nullable|string',\n            'files' => 'required|array',\n            'files.*' => 'array',\n            'files.*.to' => 'required|string',\n            'files.*.from' => 'required|string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/UploadFileRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass UploadFileRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_CREATE;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Files/WriteFileContentRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Files;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass WriteFileContentRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    /**\n     * Returns the permissions string indicating which permission should be used to\n     * validate that the authenticated user has permission to perform this action aganist\n     * the given resource (server).\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_FILE_CREATE;\n    }\n\n    /**\n     * There is no rule here for the file contents since we just use the body content\n     * on the request to set the file contents. If nothing is passed that is fine since\n     * it just means we want to set the file to be empty.\n     */\n    public function rules(): array\n    {\n        return [\n            'file' => 'required|string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/GetServerRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers;\n\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass GetServerRequest extends ClientApiRequest\n{\n    /**\n     * Determine if a client has permission to view this server on the API. This\n     * should never be false since this would be checking the same permission as\n     * resourceExists().\n     */\n    public function authorize(): bool\n    {\n        return true;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Network/DeleteAllocationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Network;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass DeleteAllocationRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_ALLOCATION_DELETE;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Network/GetNetworkRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Network;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass GetNetworkRequest extends ClientApiRequest\n{\n    /**\n     * Check that the user has permission to view the allocations for\n     * this server.\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_ALLOCATION_READ;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Network/NewAllocationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Network;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass NewAllocationRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_ALLOCATION_CREATE;\n    }\n\n    public function rules(): array\n    {\n        $limit = (int) config('pterodactyl.client_features.allocations.consecutive_limit', 3);\n\n        return [\n            'count' => ['nullable', 'integer', \"between:1,{$limit}\"],\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Network/SetPrimaryAllocationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Network;\n\nclass SetPrimaryAllocationRequest extends UpdateAllocationRequest\n{\n    public function rules(): array\n    {\n        return [];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Network/UpdateAllocationRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Network;\n\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass UpdateAllocationRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_ALLOCATION_UPDATE;\n    }\n\n    public function rules(): array\n    {\n        $rules = Allocation::getRules();\n\n        return [\n            'notes' => array_merge($rules['notes'], ['present']),\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Schedules/DeleteScheduleRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules;\n\nuse Pterodactyl\\Models\\Permission;\n\nclass DeleteScheduleRequest extends ViewScheduleRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_SCHEDULE_DELETE;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Schedules/StoreScheduleRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules;\n\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Models\\Permission;\n\nclass StoreScheduleRequest extends ViewScheduleRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_SCHEDULE_CREATE;\n    }\n\n    public function rules(): array\n    {\n        $rules = Schedule::getRules();\n\n        return [\n            'name' => $rules['name'],\n            'is_active' => array_merge(['filled'], $rules['is_active']),\n            'minute' => $rules['cron_minute'],\n            'hour' => $rules['cron_hour'],\n            'day_of_month' => $rules['cron_day_of_month'],\n            'day_of_week' => $rules['cron_day_of_week'],\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Schedules/StoreTaskRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules;\n\nuse Pterodactyl\\Models\\Permission;\n\nclass StoreTaskRequest extends ViewScheduleRequest\n{\n    /**\n     * Determine if the user is allowed to create a new task for this schedule. We simply\n     * check if they can modify a schedule to determine if they're able to do this. There\n     * are no task specific permissions.\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_SCHEDULE_UPDATE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'action' => 'required|in:command,power,backup',\n            'payload' => 'required_unless:action,backup|string|nullable',\n            'time_offset' => 'required|numeric|min:0|max:900',\n            'sequence_id' => 'sometimes|required|numeric|min:1',\n            'continue_on_failure' => 'sometimes|required|boolean',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Schedules/TriggerScheduleRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass TriggerScheduleRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_SCHEDULE_UPDATE;\n    }\n\n    public function rules(): array\n    {\n        return [];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Schedules/UpdateScheduleRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules;\n\nuse Pterodactyl\\Models\\Permission;\n\nclass UpdateScheduleRequest extends StoreScheduleRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_SCHEDULE_UPDATE;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Schedules/ViewScheduleRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Schedules;\n\nuse Pterodactyl\\Models\\Task;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Symfony\\Component\\HttpKernel\\Exception\\NotFoundHttpException;\n\nclass ViewScheduleRequest extends ClientApiRequest\n{\n    /**\n     * Determine if this resource can be viewed.\n     */\n    public function authorize(): bool\n    {\n        if (!parent::authorize()) {\n            return false;\n        }\n\n        $server = $this->route()->parameter('server');\n        $schedule = $this->route()->parameter('schedule');\n\n        // If the schedule does not belong to this server throw a 404 error. Also throw an\n        // error if the task being requested does not belong to the associated schedule.\n        if ($server instanceof Server && $schedule instanceof Schedule) {\n            $task = $this->route()->parameter('task');\n\n            if ($schedule->server_id !== $server->id || ($task instanceof Task && $task->schedule_id !== $schedule->id)) {\n                throw new NotFoundHttpException('The requested resource does not exist on the system.');\n            }\n        }\n\n        return true;\n    }\n\n    public function permission(): string\n    {\n        return Permission::ACTION_SCHEDULE_READ;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/SendCommandRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass SendCommandRequest extends ClientApiRequest\n{\n    /**\n     * Determine if the API user has permission to perform this action.\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_CONTROL_CONSOLE;\n    }\n\n    /**\n     * Rules to validate this request against.\n     */\n    public function rules(): array\n    {\n        return [\n            'command' => 'required|string|min:1',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/SendPowerRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass SendPowerRequest extends ClientApiRequest\n{\n    /**\n     * Determine if the user has permission to send a power command to a server.\n     */\n    public function permission(): string\n    {\n        switch ($this->input('signal')) {\n            case 'start':\n                return Permission::ACTION_CONTROL_START;\n            case 'stop':\n            case 'kill':\n                return Permission::ACTION_CONTROL_STOP;\n            case 'restart':\n                return Permission::ACTION_CONTROL_RESTART;\n        }\n\n        return '__invalid';\n    }\n\n    /**\n     * Rules to validate this request against.\n     */\n    public function rules(): array\n    {\n        return [\n            'signal' => 'required|string|in:start,stop,restart,kill',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Settings/ReinstallServerRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Settings;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass ReinstallServerRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_SETTINGS_REINSTALL;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Settings/RenameServerRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Settings;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass RenameServerRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    /**\n     * Returns the permissions string indicating which permission should be used to\n     * validate that the authenticated user has permission to perform this action against\n     * the given resource (server).\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_SETTINGS_RENAME;\n    }\n\n    /**\n     * The rules to apply when validating this request.\n     */\n    public function rules(): array\n    {\n        return [\n            'name' => Server::getRules()['name'],\n            'description' => 'string|nullable',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Settings/SetDockerImageRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Settings;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Validation\\Rule;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Contracts\\Http\\ClientPermissionsRequest;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass SetDockerImageRequest extends ClientApiRequest implements ClientPermissionsRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_STARTUP_DOCKER_IMAGE;\n    }\n\n    public function rules(): array\n    {\n        $server = $this->route()->parameter('server');\n\n        Assert::isInstanceOf($server, Server::class);\n\n        return [\n            'docker_image' => ['required', 'string', 'max:191', Rule::in(array_values($server->egg->docker_images))],\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Startup/GetStartupRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Startup;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass GetStartupRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_STARTUP_READ;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Startup/UpdateEggRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Startup;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass UpdateEggRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_STARTUP_EGG_CHANGE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'egg_id' => 'required|integer|exists:eggs,id',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Startup/UpdateStartupVariableRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Startup;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\n\nclass UpdateStartupVariableRequest extends ClientApiRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_STARTUP_UPDATE;\n    }\n\n    /**\n     * The actual validation of the variable's value will happen inside the controller.\n     */\n    public function rules(): array\n    {\n        return [\n            'key' => 'required|string',\n            'value' => 'present',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Subusers/DeleteSubuserRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Subusers;\n\nuse Pterodactyl\\Models\\Permission;\n\nclass DeleteSubuserRequest extends SubuserRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_USER_DELETE;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Subusers/GetSubuserRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Subusers;\n\nuse Pterodactyl\\Models\\Permission;\n\nclass GetSubuserRequest extends SubuserRequest\n{\n    /**\n     * Confirm that a user is able to view subusers for the specified server.\n     */\n    public function permission(): string\n    {\n        return Permission::ACTION_USER_READ;\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Subusers/StoreSubuserRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Subusers;\n\nuse Pterodactyl\\Models\\Permission;\n\nclass StoreSubuserRequest extends SubuserRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_USER_CREATE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'email' => 'required|email|between:1,191',\n            'permissions' => 'required|array',\n            'permissions.*' => 'string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Subusers/SubuserRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Subusers;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Exceptions\\Http\\HttpForbiddenException;\nuse Pterodactyl\\Http\\Requests\\Api\\Client\\ClientApiRequest;\nuse Pterodactyl\\Services\\Servers\\GetUserPermissionsService;\n\nabstract class SubuserRequest extends ClientApiRequest\n{\n    protected ?Subuser $model;\n\n    /**\n     * Authorize the request and ensure that a user is not trying to modify themselves.\n     *\n     * @throws \\Illuminate\\Contracts\\Container\\BindingResolutionException\n     */\n    public function authorize(): bool\n    {\n        if (!parent::authorize()) {\n            return false;\n        }\n\n        $user = $this->route()->parameter('user');\n        // Don't allow a user to edit themselves on the server.\n        if ($user instanceof User) {\n            if ($user->uuid === $this->user()->uuid) {\n                return false;\n            }\n        }\n\n        // If this is a POST request, validate that the user can even assign the permissions they\n        // have selected to assign.\n        if ($this->method() === Request::METHOD_POST && $this->has('permissions')) {\n            $this->validatePermissionsCanBeAssigned(\n                $this->input('permissions') ?? []\n            );\n        }\n\n        return true;\n    }\n\n    /**\n     * Validates that the permissions we are trying to assign can actually be assigned\n     * by the user making the request.\n     *\n     * @throws \\Illuminate\\Contracts\\Container\\BindingResolutionException\n     */\n    protected function validatePermissionsCanBeAssigned(array $permissions)\n    {\n        $user = $this->user();\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        $server = $this->route()->parameter('server');\n\n        // If we are a root admin or the server owner, no need to perform these checks.\n        if ($user->root_admin || $user->id === $server->owner_id) {\n            return;\n        }\n\n        // Otherwise, get the current subuser's permission set, and ensure that the\n        // permissions they are trying to assign are not _more_ than the ones they\n        // already have.\n        $service = $this->container->make(GetUserPermissionsService::class);\n\n        if (count(array_diff($permissions, $service->handle($server, $user))) > 0) {\n            throw new HttpForbiddenException('Cannot assign permissions to a subuser that your account does not actively possess.');\n        }\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Client/Servers/Subusers/UpdateSubuserRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Client\\Servers\\Subusers;\n\nuse Pterodactyl\\Models\\Permission;\n\nclass UpdateSubuserRequest extends SubuserRequest\n{\n    public function permission(): string\n    {\n        return Permission::ACTION_USER_UPDATE;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'permissions' => 'required|array',\n            'permissions.*' => 'string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Remote/ActivityEventRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Remote;\n\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nclass ActivityEventRequest extends FormRequest\n{\n    public function authorize(): bool\n    {\n        return true;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'data' => ['required', 'array'],\n            'data.*' => ['array'],\n            'data.*.user' => ['sometimes', 'nullable', 'uuid'],\n            'data.*.server' => ['required', 'uuid'],\n            'data.*.event' => ['required', 'string'],\n            'data.*.metadata' => ['present', 'nullable', 'array'],\n            'data.*.ip' => ['sometimes', 'nullable', 'ip'],\n            'data.*.timestamp' => ['required', 'string'],\n        ];\n    }\n\n    /**\n     * Returns all the unique server UUIDs that were received in this request.\n     */\n    public function servers(): array\n    {\n        return Collection::make($this->input('data'))->pluck('server')->unique()->toArray();\n    }\n\n    /**\n     * Returns all the unique user UUIDs that were submitted in this request.\n     */\n    public function users(): array\n    {\n        return Collection::make($this->input('data'))\n            ->filter(function ($value) {\n                return !empty($value['user']);\n            })\n            ->pluck('user')\n            ->unique()\n            ->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Remote/AuthenticateWebsocketDetailsRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Remote;\n\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nclass AuthenticateWebsocketDetailsRequest extends FormRequest\n{\n    public function authorize(): bool\n    {\n        return true;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'server_uuid' => 'required|string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Remote/InstallationDataRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Remote;\n\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nclass InstallationDataRequest extends FormRequest\n{\n    public function authorize(): bool\n    {\n        return true;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'successful' => 'present|boolean',\n            'reinstall' => 'sometimes|boolean',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Remote/ReportBackupCompleteRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Remote;\n\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nclass ReportBackupCompleteRequest extends FormRequest\n{\n    public function rules(): array\n    {\n        return [\n            'successful' => 'required|boolean',\n            'checksum' => 'nullable|string|required_if:successful,true',\n            'checksum_type' => 'nullable|string|required_if:successful,true',\n            'size' => 'nullable|numeric|required_if:successful,true',\n            'parts' => 'nullable|array',\n            'parts.*.etag' => 'required|string',\n            'parts.*.part_number' => 'required|numeric',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Api/Remote/SftpAuthenticationFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Api\\Remote;\n\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nclass SftpAuthenticationFormRequest extends FormRequest\n{\n    /**\n     * Authenticate the request.\n     */\n    public function authorize(): bool\n    {\n        return true;\n    }\n\n    /**\n     * Rules to apply to the request.\n     */\n    public function rules(): array\n    {\n        return [\n            'type' => ['nullable', 'in:password,public_key'],\n            'username' => ['required', 'string'],\n            'password' => ['required', 'string'],\n        ];\n    }\n\n    /**\n     * Return only the fields that we are interested in from the request.\n     * This will include empty fields as a null value.\n     */\n    public function normalize(): array\n    {\n        return $this->only(\n            array_keys($this->rules())\n        );\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Auth/LoginCheckpointRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Auth;\n\nuse Illuminate\\Validation\\Rule;\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nclass LoginCheckpointRequest extends FormRequest\n{\n    /**\n     * Determine if the request is authorized.\n     */\n    public function authorize(): bool\n    {\n        return true;\n    }\n\n    /**\n     * Rules to apply to the request.\n     */\n    public function rules(): array\n    {\n        return [\n            'confirmation_token' => 'required|string',\n            'authentication_code' => [\n                'nullable',\n                'numeric',\n                Rule::requiredIf(function () {\n                    return empty($this->input('recovery_token'));\n                }),\n            ],\n            'recovery_token' => [\n                'nullable',\n                'string',\n                Rule::requiredIf(function () {\n                    return empty($this->input('authentication_code'));\n                }),\n            ],\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Auth/LoginRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Auth;\n\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nclass LoginRequest extends FormRequest\n{\n    public function authorized(): bool\n    {\n        return true;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'user' => 'required|string|min:1',\n            'password' => 'required|string',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Auth/ResetPasswordRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Auth;\n\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nclass ResetPasswordRequest extends FormRequest\n{\n    public function authorize(): bool\n    {\n        return true;\n    }\n\n    public function rules(): array\n    {\n        return [\n            'token' => 'required|string',\n            'email' => 'required|email',\n            'password' => 'required|string|confirmed|min:8',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/Base/LocaleRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests\\Base;\n\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nclass LocaleRequest extends FormRequest\n{\n    public function rules(): array\n    {\n        return [\n            'locale' => ['required', 'string', 'regex:/^[a-z][a-z]$/'],\n            'namespace' => ['required', 'string', 'regex:/^[a-z]{1,191}$/'],\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Http/Requests/FrontendUserFormRequest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Requests;\n\nuse Illuminate\\Foundation\\Http\\FormRequest;\n\nabstract class FrontendUserFormRequest extends FormRequest\n{\n    abstract public function rules(): array;\n\n    /**\n     * Determine if a user is authorized to access this endpoint.\n     */\n    public function authorize(): bool\n    {\n        return !is_null($this->user());\n    }\n\n    /**\n     * Return only the fields that we are interested in from the request.\n     * This will include empty fields as a null value.\n     */\n    public function normalize(): array\n    {\n        return $this->only(\n            array_keys($this->rules())\n        );\n    }\n}\n"
  },
  {
    "path": "app/Http/Resources/Wings/ServerConfigurationCollection.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\Resources\\Wings;\n\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Http\\Resources\\Json\\ResourceCollection;\nuse Pterodactyl\\Services\\Eggs\\EggConfigurationService;\nuse Pterodactyl\\Services\\Servers\\ServerConfigurationStructureService;\n\nclass ServerConfigurationCollection extends ResourceCollection\n{\n    /**\n     * Converts a collection of Server models into an array of configuration responses\n     * that can be understood by Wings. Make sure you've properly loaded the required\n     * relationships on the Server models before calling this function, otherwise you'll\n     * have some serious performance issues from all the N+1 queries.\n     */\n    public function toArray($request): array\n    {\n        $egg = Container::getInstance()->make(EggConfigurationService::class);\n        $configuration = Container::getInstance()->make(ServerConfigurationStructureService::class);\n\n        return $this->collection->map(function (Server $server) use ($configuration, $egg) {\n            return [\n                'uuid' => $server->uuid,\n                'settings' => $configuration->handle($server),\n                'process_configuration' => $egg->handle($server),\n            ];\n        })->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Http/ViewComposers/AssetComposer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Http\\ViewComposers;\n\nuse Illuminate\\View\\View;\nuse Pterodactyl\\Services\\Helpers\\AssetHashService;\n\nclass AssetComposer\n{\n    /**\n     * AssetComposer constructor.\n     */\n    public function __construct(private AssetHashService $assetHashService)\n    {\n    }\n\n    /**\n     * Provide access to the asset service in the views.\n     */\n    public function compose(View $view): void\n    {\n        $view->with('asset', $this->assetHashService);\n        $view->with('siteConfiguration', [\n            'name' => config('app.name') ?? 'Pterodactyl',\n            'locale' => config('app.locale') ?? 'zh',\n            'logo' => [\n                'title' => config('logo.title') ?? '',\n                'favicon' => config('logo.favicon') ?? '/favicons/favicon.ico',\n                'auth' => config('logo.auth') ?? '',\n            ],\n            'recaptcha' => [\n                'enabled' => config('recaptcha.enabled', false),\n                'siteKey' => config('recaptcha.website_key') ?? '',\n            ],\n            'icp' => [\n                'enabled' => config('icp.enabled', false),\n                'record' => config('icp.record') ?? '',\n                'security_record' => config('icp.security_record') ?? '',\n            ],\n            'allocations' => [\n                'consecutiveEnabled' => config('pterodactyl.client_features.allocations.consecutive_enabled', false),\n                'consecutiveLimit' => (int) config('pterodactyl.client_features.allocations.consecutive_limit', 3),\n            ],\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Jobs/RevokeSftpAccessJob.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Jobs;\n\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Foundation\\Queue\\Queueable;\nuse Illuminate\\Contracts\\Queue\\ShouldQueue;\nuse Illuminate\\Contracts\\Queue\\ShouldBeUnique;\nuse Illuminate\\Queue\\Attributes\\WithoutRelations;\nuse Illuminate\\Queue\\Attributes\\DeleteWhenMissingModels;\nuse Pterodactyl\\Repositories\\Wings\\DaemonRevocationRepository;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\n/**\n * Revokes all SFTP access for a user on a given node or for a specific server.\n */\n#[DeleteWhenMissingModels]\nclass RevokeSftpAccessJob implements ShouldQueue, ShouldBeUnique\n{\n    use Queueable;\n\n    public int $tries = 3;\n\n    public int $maxExceptions = 1;\n\n    public function __construct(\n        public readonly string $user,\n        #[WithoutRelations]\n        public readonly Server|Node $target,\n    ) {\n    }\n\n    public function uniqueId(): string\n    {\n        $target = $this->target instanceof Node ? \"node:{$this->target->uuid}\" : \"server:{$this->target->uuid}\";\n\n        return \"revoke-sftp:{$this->user}:{$target}\";\n    }\n\n    public function handle(DaemonRevocationRepository $repository): void\n    {\n        $node = $this->target instanceof Node ? $this->target : $this->target->node;\n\n        try {\n            $repository->setNode($node)->deauthorize(\n                $this->user,\n                $this->target instanceof Server ? [$this->target->uuid] : []\n            );\n        } catch (DaemonConnectionException) {\n            // Keep retrying this job with a longer and longer backoff until we hit three\n            // attempts at which point we stop and will assume the node is fully offline\n            // and we are just wasting time.\n            $this->release($this->attempts() * 10);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Jobs/Schedule/RunTaskJob.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Jobs\\Schedule;\n\nuse Carbon\\CarbonImmutable;\nuse Pterodactyl\\Models\\Task;\nuse Illuminate\\Bus\\Queueable;\nuse Illuminate\\Queue\\SerializesModels;\nuse Illuminate\\Contracts\\Queue\\ShouldQueue;\nuse Illuminate\\Foundation\\Bus\\DispatchesJobs;\nuse Pterodactyl\\Services\\Backups\\InitiateBackupService;\nuse Pterodactyl\\Repositories\\Wings\\DaemonPowerRepository;\nuse Pterodactyl\\Repositories\\Wings\\DaemonCommandRepository;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass RunTaskJob implements ShouldQueue\n{\n    use Queueable;\n    use DispatchesJobs;\n    use SerializesModels;\n\n    /**\n     * RunTaskJob constructor.\n     */\n    public function __construct(public Task $task, public bool $manualRun = false)\n    {\n        $this->queue = 'standard';\n    }\n\n    /**\n     * Run the job and send actions to the daemon running the server.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(\n        DaemonCommandRepository $commandRepository,\n        InitiateBackupService $backupService,\n        DaemonPowerRepository $powerRepository,\n    ) {\n        // Do not process a task that is not set to active, unless it's been manually triggered.\n        if (!$this->task->schedule->is_active && !$this->manualRun) {\n            $this->markTaskNotQueued();\n            $this->markScheduleComplete();\n\n            return;\n        }\n\n        $server = $this->task->server;\n        // If we made it to this point and the server status is not null it means the\n        // server was likely suspended or marked as reinstalling after the schedule\n        // was queued up. Just end the task right now — this should be a very rare\n        // condition.\n        if (!is_null($server->status)) {\n            $this->failed();\n\n            return;\n        }\n\n        // Perform the provided task against the daemon.\n        try {\n            switch ($this->task->action) {\n                case Task::ACTION_POWER:\n                    $powerRepository->setServer($server)->send($this->task->payload);\n                    break;\n                case Task::ACTION_COMMAND:\n                    $commandRepository->setServer($server)->send($this->task->payload);\n                    break;\n                case Task::ACTION_BACKUP:\n                    $backupService->setIgnoredFiles(explode(PHP_EOL, $this->task->payload))->handle($server, null, true);\n                    break;\n                default:\n                    throw new \\InvalidArgumentException('提供的任务操作无效: ' . $this->task->action);\n            }\n        } catch (\\Exception $exception) {\n            // If this isn't a DaemonConnectionException on a task that allows for failures\n            // throw the exception back up the chain so that the task is stopped.\n            if (!($this->task->continue_on_failure && $exception instanceof DaemonConnectionException)) {\n                throw $exception;\n            }\n        }\n\n        $this->markTaskNotQueued();\n        $this->queueNextTask();\n    }\n\n    /**\n     * Handle a failure while sending the action to the daemon or otherwise processing the job.\n     */\n    public function failed(?\\Exception $exception = null)\n    {\n        $this->markTaskNotQueued();\n        $this->markScheduleComplete();\n    }\n\n    /**\n     * Get the next task in the schedule and queue it for running after the defined period of wait time.\n     */\n    private function queueNextTask()\n    {\n        /** @var Task|null $nextTask */\n        $nextTask = Task::query()->where('schedule_id', $this->task->schedule_id)\n            ->orderBy('sequence_id', 'asc')\n            ->where('sequence_id', '>', $this->task->sequence_id)\n            ->first();\n\n        if (is_null($nextTask)) {\n            $this->markScheduleComplete();\n\n            return;\n        }\n\n        $nextTask->update(['is_queued' => true]);\n\n        $this->dispatch((new self($nextTask, $this->manualRun))->delay($nextTask->time_offset));\n    }\n\n    /**\n     * Marks the parent schedule as being complete.\n     */\n    private function markScheduleComplete()\n    {\n        $this->task->schedule()->update([\n            'is_processing' => false,\n            'last_run_at' => CarbonImmutable::now()->toDateTimeString(),\n        ]);\n    }\n\n    /**\n     * Mark a specific task as no longer being queued.\n     */\n    private function markTaskNotQueued()\n    {\n        $this->task->update(['is_queued' => false]);\n    }\n}\n"
  },
  {
    "path": "app/Listeners/AuthenticationListener.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Listeners;\n\nuse Pterodactyl\\Facades\\Activity;\nuse Illuminate\\Auth\\Events\\Failed;\nuse Pterodactyl\\Events\\Auth\\DirectLogin;\nuse Illuminate\\Auth\\Events\\PasswordReset;\nuse Illuminate\\Contracts\\Events\\Dispatcher;\nuse Pterodactyl\\Extensions\\Illuminate\\Events\\Contracts\\SubscribesToEvents;\n\nclass AuthenticationListener implements SubscribesToEvents\n{\n    /**\n     * Handles an authentication event by logging the user and information about\n     * the request.\n     */\n    public function login(Failed|DirectLogin $event): void\n    {\n        $activity = Activity::withRequestMetadata();\n        if ($event->user) {\n            $activity = $activity->subject($event->user);\n        }\n\n        if ($event instanceof Failed) {\n            foreach ($event->credentials as $key => $value) {\n                $activity = $activity->property($key, $value);\n            }\n        }\n\n        $activity->event($event instanceof Failed ? 'auth:fail' : 'auth:success')->log();\n    }\n\n    public function reset(PasswordReset $event): void\n    {\n        Activity::event('event:password-reset')->withRequestMetadata()->subject($event->user)->log();\n    }\n\n    public function subscribe(Dispatcher $events): void\n    {\n        $events->listen(Failed::class, [self::class, 'login']);\n        $events->listen(DirectLogin::class, [self::class, 'login']);\n        $events->listen(PasswordReset::class, [self::class, 'reset']);\n    }\n}\n"
  },
  {
    "path": "app/Listeners/RevocationListener.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Listeners;\n\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Events\\User\\Deleting;\nuse Pterodactyl\\Jobs\\RevokeSftpAccessJob;\nuse Illuminate\\Contracts\\Events\\Dispatcher;\nuse Illuminate\\Database\\Eloquent\\Collection;\nuse Pterodactyl\\Events\\User\\PasswordChanged;\nuse Pterodactyl\\Extensions\\Illuminate\\Events\\Contracts\\SubscribesToEvents;\n\nclass RevocationListener implements SubscribesToEvents\n{\n    public function revoke(Deleting|PasswordChanged $event): void\n    {\n        $user = $event->user;\n\n        // Look at all of the nodes that a user is associated with and trigger a job\n        // that disconnects them from websockets and SFTP.\n        Node::query()\n            ->whereIn('nodes.id', $user->accessibleServers()->select('servers.node_id')->distinct())\n            ->chunk(50, function (Collection $nodes) use ($user) {\n                $nodes->each(fn (Node $node) => RevokeSftpAccessJob::dispatch($user->uuid, $node));\n            });\n    }\n\n    public function subscribe(Dispatcher $events): void\n    {\n        $events->listen(Deleting::class, [self::class, 'revoke']);\n        $events->listen(PasswordChanged::class, [self::class, 'revoke']);\n    }\n}\n"
  },
  {
    "path": "app/Listeners/TwoFactorListener.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Listeners;\n\nuse Pterodactyl\\Facades\\Activity;\nuse Illuminate\\Contracts\\Events\\Dispatcher;\nuse Pterodactyl\\Events\\Auth\\ProvidedAuthenticationToken;\nuse Pterodactyl\\Extensions\\Illuminate\\Events\\Contracts\\SubscribesToEvents;\n\nclass TwoFactorListener implements SubscribesToEvents\n{\n    public function __invoke(ProvidedAuthenticationToken $event): void\n    {\n        Activity::event($event->recovery ? 'auth:recovery-token' : 'auth:token')\n            ->withRequestMetadata()\n            ->subject($event->user)\n            ->log();\n    }\n\n    public function subscribe(Dispatcher $events): void\n    {\n        $events->listen(ProvidedAuthenticationToken::class, self::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/APILog.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Model;\n\nclass APILog extends Model\n{\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'api_logs';\n\n    /**\n     * The attributes excluded from the model's JSON form.\n     */\n    protected $hidden = [];\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $guarded = ['id', 'created_at', 'updated_at'];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'authorized' => 'boolean',\n    ];\n}\n"
  },
  {
    "path": "app/Models/ActivityLog.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Carbon\\Carbon;\nuse Illuminate\\Support\\Facades\\Event;\nuse Pterodactyl\\Events\\ActivityLogged;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Illuminate\\Database\\Eloquent\\MassPrunable;\nuse Pterodactyl\\Contracts\\Models\\Identifiable;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasOne;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Illuminate\\Database\\Eloquent\\Relations\\MorphTo;\nuse Pterodactyl\\Models\\Traits\\HasRealtimeIdentifier;\nuse Illuminate\\Database\\Eloquent\\Model as IlluminateModel;\n\n/**\n * \\Pterodactyl\\Models\\ActivityLog.\n *\n * @property int $id\n * @property string|null $batch\n * @property string $event\n * @property string $ip\n * @property string|null $description\n * @property string|null $actor_type\n * @property int|null $actor_id\n * @property int|null $api_key_id\n * @property \\Illuminate\\Support\\Collection|null $properties\n * @property Carbon $timestamp\n * @property IlluminateModel|\\Eloquent $actor\n * @property \\Illuminate\\Database\\Eloquent\\Collection<int, \\Pterodactyl\\Models\\ActivityLogSubject> $subjects\n * @property int|null $subjects_count\n * @property ApiKey|null $apiKey\n *\n * @method static Builder|ActivityLog forActor(\\Illuminate\\Database\\Eloquent\\Model $actor)\n * @method static Builder|ActivityLog forEvent(string $action)\n * @method static Builder|ActivityLog newModelQuery()\n * @method static Builder|ActivityLog newQuery()\n * @method static Builder|ActivityLog query()\n * @method static Builder|ActivityLog whereActorId($value)\n * @method static Builder|ActivityLog whereActorType($value)\n * @method static Builder|ActivityLog whereApiKeyId($value)\n * @method static Builder|ActivityLog whereBatch($value)\n * @method static Builder|ActivityLog whereDescription($value)\n * @method static Builder|ActivityLog whereEvent($value)\n * @method static Builder|ActivityLog whereId($value)\n * @method static Builder|ActivityLog whereIp($value)\n * @method static Builder|ActivityLog whereProperties($value)\n * @method static Builder|ActivityLog whereTimestamp($value)\n *\n * @mixin \\Eloquent\n */\n#[Attributes\\Identifiable('actl')]\nclass ActivityLog extends Model implements Identifiable\n{\n    use MassPrunable;\n    use HasRealtimeIdentifier;\n\n    public const RESOURCE_NAME = 'activity_log';\n\n    /**\n     * Tracks all the events we no longer wish to display to users. These are either legacy\n     * events or just events where we never ended up using the associated data.\n     */\n    public const DISABLED_EVENTS = ['server:file.upload'];\n\n    public $timestamps = false;\n\n    protected $guarded = [\n        'id',\n        'timestamp',\n    ];\n\n    protected $casts = [\n        'properties' => 'collection',\n        'timestamp' => 'datetime',\n    ];\n\n    protected $with = ['subjects'];\n\n    public static array $validationRules = [\n        'event' => ['required', 'string'],\n        'batch' => ['nullable', 'uuid'],\n        'ip' => ['required', 'string'],\n        'description' => ['nullable', 'string'],\n        'properties' => ['array'],\n    ];\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\MorphTo<\\Illuminate\\Database\\Eloquent\\Model, $this>\n     */\n    public function actor(): MorphTo\n    {\n        $morph = $this->morphTo();\n        if (method_exists($morph, 'withTrashed')) { // @phpstan-ignore function.alreadyNarrowedType\n            return $morph->withTrashed();\n        }\n\n        return $morph;\n    }\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\ActivityLogSubject, $this>\n     */\n    public function subjects(): HasMany\n    {\n        return $this->hasMany(ActivityLogSubject::class);\n    }\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasOne<\\Pterodactyl\\Models\\ApiKey, $this>\n     */\n    public function apiKey(): HasOne\n    {\n        return $this->hasOne(ApiKey::class, 'id', 'api_key_id');\n    }\n\n    public function scopeForEvent(Builder $builder, string $action): Builder\n    {\n        return $builder->where('event', $action);\n    }\n\n    /**\n     * Scopes a query to only return results where the actor is a given model.\n     */\n    public function scopeForActor(Builder $builder, IlluminateModel $actor): Builder\n    {\n        return $builder->whereMorphedTo('actor', $actor);\n    }\n\n    /**\n     * Returns models to be pruned.\n     *\n     * @see https://laravel.com/docs/9.x/eloquent#pruning-models\n     */\n    public function prunable()\n    {\n        if (is_null(config('activity.prune_days'))) {\n            throw new \\LogicException('Cannot prune activity logs: no \"prune_days\" configuration value is set.');\n        }\n\n        return static::where('timestamp', '<=', Carbon::now()->subDays(config('activity.prune_days')));\n    }\n\n    /**\n     * Boots the model event listeners. This will trigger an activity log event every\n     * time a new model is inserted which can then be captured and worked with as needed.\n     */\n    protected static function boot()\n    {\n        parent::boot();\n\n        static::created(function (self $model) {\n            Event::dispatch(new ActivityLogged($model));\n        });\n    }\n}\n"
  },
  {
    "path": "app/Models/ActivityLogSubject.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Relations\\Pivot;\nuse Illuminate\\Database\\Eloquent\\Relations\\MorphTo;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\n\n/**\n * \\Pterodactyl\\Models\\ActivityLogSubject.\n *\n * @property int $id\n * @property int $activity_log_id\n * @property int $subject_id\n * @property string $subject_type\n * @property ActivityLog|null $activityLog\n * @property \\Illuminate\\Database\\Eloquent\\Model $subject\n *\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ActivityLogSubject newModelQuery()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ActivityLogSubject newQuery()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ActivityLogSubject query()\n *\n * @mixin \\Illuminate\\Database\\Eloquent\\Model\n */\nclass ActivityLogSubject extends Pivot\n{\n    public $incrementing = true;\n    public $timestamps = false;\n\n    protected $table = 'activity_log_subjects';\n\n    protected $guarded = ['id'];\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\ActivityLog, $this>\n     */\n    public function activityLog(): BelongsTo\n    {\n        return $this->belongsTo(ActivityLog::class);\n    }\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\MorphTo<\\Illuminate\\Database\\Eloquent\\Model, $this>\n     */\n    public function subject(): MorphTo\n    {\n        $morph = $this->morphTo();\n        if (method_exists($morph, 'withTrashed')) { // @phpstan-ignore function.alreadyNarrowedType\n            return $morph->withTrashed();\n        }\n\n        return $morph;\n    }\n}\n"
  },
  {
    "path": "app/Models/Allocation.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\n\n/**\n * Pterodactyl\\Models\\Allocation.\n *\n * @property int $id\n * @property int $node_id\n * @property string $ip\n * @property string|null $ip_alias\n * @property int $port\n * @property int|null $server_id\n * @property string|null $notes\n * @property \\Carbon\\Carbon|null $created_at\n * @property \\Carbon\\Carbon|null $updated_at\n * @property string $alias\n * @property bool $has_alias\n * @property Server|null $server\n * @property Node $node\n * @property string $hashid\n *\n * @method static \\Database\\Factories\\AllocationFactory factory(...$parameters)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation newModelQuery()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation newQuery()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation query()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation whereCreatedAt($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation whereId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation whereIp($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation whereIpAlias($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation whereNodeId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation whereNotes($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation wherePort($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation whereServerId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Allocation whereUpdatedAt($value)\n *\n * @mixin \\Eloquent\n */\nclass Allocation extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\AllocationFactory> */\n    use HasFactory;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'allocation';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'allocations';\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $guarded = ['id', 'created_at', 'updated_at'];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'node_id' => 'integer',\n        'port' => 'integer',\n        'server_id' => 'integer',\n    ];\n\n    public static array $validationRules = [\n        'node_id' => 'required|exists:nodes,id',\n        'ip' => 'required|ip',\n        'port' => 'required|numeric|between:1024,65535',\n        'ip_alias' => 'nullable|string',\n        'server_id' => 'nullable|exists:servers,id',\n        'notes' => 'nullable|string|max:256',\n    ];\n\n    public function getRouteKeyName(): string\n    {\n        return $this->getKeyName();\n    }\n\n    /**\n     * Return a hashid encoded string to represent the ID of the allocation.\n     */\n    public function getHashidAttribute(): string\n    {\n        return app()->make('hashids')->encode($this->id);\n    }\n\n    /**\n     * Accessor to automatically provide the IP alias if defined.\n     */\n    public function getAliasAttribute(?string $value): string\n    {\n        return (is_null($this->ip_alias)) ? $this->ip : $this->ip_alias;\n    }\n\n    /**\n     * Accessor to quickly determine if this allocation has an alias.\n     */\n    public function getHasAliasAttribute(?string $value): bool\n    {\n        return !is_null($this->ip_alias);\n    }\n\n    public function toString(): string\n    {\n        return sprintf('%s:%s', $this->ip, $this->port);\n    }\n\n    /**\n     * Gets information for the server associated with this allocation.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function server(): BelongsTo\n    {\n        return $this->belongsTo(Server::class);\n    }\n\n    /**\n     * Return the Node model associated with this allocation.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Node, $this>\n     */\n    public function node(): BelongsTo\n    {\n        return $this->belongsTo(Node::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/ApiKey.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Support\\Str;\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Laravel\\Sanctum\\Contracts\\HasAbilities;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\n\n/**\n * Pterodactyl\\Models\\ApiKey.\n *\n * @property int $id\n * @property int $user_id\n * @property int $key_type\n * @property string $identifier\n * @property string $token\n * @property array|null $allowed_ips\n * @property string|null $memo\n * @property \\Illuminate\\Support\\Carbon|null $last_used_at\n * @property \\Illuminate\\Support\\Carbon|null $expires_at\n * @property \\Illuminate\\Support\\Carbon|null $created_at\n * @property \\Illuminate\\Support\\Carbon|null $updated_at\n * @property int $r_servers\n * @property int $r_nodes\n * @property int $r_allocations\n * @property int $r_users\n * @property int $r_locations\n * @property int $r_nests\n * @property int $r_eggs\n * @property int $r_database_hosts\n * @property int $r_server_databases\n * @property User $tokenable\n * @property User $user\n *\n * @method static \\Database\\Factories\\ApiKeyFactory factory(...$parameters)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey newModelQuery()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey newQuery()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey query()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereAllowedIps($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereCreatedAt($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereIdentifier($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereKeyType($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereLastUsedAt($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereMemo($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereRAllocations($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereRDatabaseHosts($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereREggs($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereRLocations($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereRNests($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereRNodes($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereRServerDatabases($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereRServers($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereRUsers($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereToken($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereUpdatedAt($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|ApiKey whereUserId($value)\n *\n * @mixin \\Eloquent\n */\nclass ApiKey extends Model implements HasAbilities\n{\n    /** @use HasFactory<\\Database\\Factories\\ApiKeyFactory> */\n    use HasFactory;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'api_key';\n    /**\n     * Different API keys that can exist on the system.\n     */\n    public const TYPE_NONE = 0;\n    public const TYPE_ACCOUNT = 1;\n    /* @deprecated */\n    public const TYPE_APPLICATION = 2;\n    /* @deprecated */\n    public const TYPE_DAEMON_USER = 3;\n    /* @deprecated */\n    public const TYPE_DAEMON_APPLICATION = 4;\n    /**\n     * The length of API key identifiers.\n     */\n    public const IDENTIFIER_LENGTH = 16;\n    /**\n     * The length of the actual API key that is encrypted and stored\n     * in the database.\n     */\n    public const KEY_LENGTH = 32;\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'api_keys';\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'allowed_ips' => 'array',\n        'user_id' => 'int',\n        'last_used_at' => 'datetime',\n        'expires_at' => 'datetime',\n        self::CREATED_AT => 'datetime',\n        self::UPDATED_AT => 'datetime',\n        'r_' . AdminAcl::RESOURCE_USERS => 'int',\n        'r_' . AdminAcl::RESOURCE_ALLOCATIONS => 'int',\n        'r_' . AdminAcl::RESOURCE_DATABASE_HOSTS => 'int',\n        'r_' . AdminAcl::RESOURCE_SERVER_DATABASES => 'int',\n        'r_' . AdminAcl::RESOURCE_EGGS => 'int',\n        'r_' . AdminAcl::RESOURCE_LOCATIONS => 'int',\n        'r_' . AdminAcl::RESOURCE_NESTS => 'int',\n        'r_' . AdminAcl::RESOURCE_NODES => 'int',\n        'r_' . AdminAcl::RESOURCE_SERVERS => 'int',\n    ];\n\n    /**\n     * Fields that are mass assignable.\n     */\n    protected $fillable = [\n        'identifier',\n        'token',\n        'allowed_ips',\n        'memo',\n        'last_used_at',\n        'expires_at',\n    ];\n\n    /**\n     * Fields that should not be included when calling toArray() or toJson()\n     * on this model.\n     */\n    protected $hidden = ['token'];\n\n    /**\n     * Rules to protect against invalid data entry to DB.\n     */\n    public static array $validationRules = [\n        'user_id' => 'required|exists:users,id',\n        'key_type' => 'present|integer|min:0|max:4',\n        'identifier' => 'required|string|size:16|unique:api_keys,identifier',\n        'token' => 'required|string',\n        'memo' => 'required|nullable|string|max:500',\n        'allowed_ips' => 'nullable|array',\n        'allowed_ips.*' => 'string',\n        'last_used_at' => 'nullable|date',\n        'expires_at' => 'nullable|date',\n        'r_' . AdminAcl::RESOURCE_USERS => 'integer|min:0|max:3',\n        'r_' . AdminAcl::RESOURCE_ALLOCATIONS => 'integer|min:0|max:3',\n        'r_' . AdminAcl::RESOURCE_DATABASE_HOSTS => 'integer|min:0|max:3',\n        'r_' . AdminAcl::RESOURCE_SERVER_DATABASES => 'integer|min:0|max:3',\n        'r_' . AdminAcl::RESOURCE_EGGS => 'integer|min:0|max:3',\n        'r_' . AdminAcl::RESOURCE_LOCATIONS => 'integer|min:0|max:3',\n        'r_' . AdminAcl::RESOURCE_NESTS => 'integer|min:0|max:3',\n        'r_' . AdminAcl::RESOURCE_NODES => 'integer|min:0|max:3',\n        'r_' . AdminAcl::RESOURCE_SERVERS => 'integer|min:0|max:3',\n    ];\n\n    public function can($ability)\n    {\n        // todo: this was never initially implemented and only became obvious once\n        //  internal tooling was updated and started catching this mistake.\n        return false;\n    }\n\n    public function cant($ability)\n    {\n        return ! $this->can($ability);\n    }\n\n    /**\n     * Returns the user this token is assigned to.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\User, $this>\n     */\n    public function user(): BelongsTo\n    {\n        return $this->belongsTo(User::class);\n    }\n\n    /**\n     * Required for support with Laravel Sanctum.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\User, $this>\n     *\n     * @see \\Laravel\\Sanctum\\Guard::supportsTokens()\n     */\n    public function tokenable(): BelongsTo\n    {\n        return $this->user();\n    }\n\n    /**\n     * Finds the model matching the provided token.\n     */\n    public static function findToken(string $token): ?self\n    {\n        $identifier = substr($token, 0, self::IDENTIFIER_LENGTH);\n\n        $model = static::where('identifier', $identifier)->first();\n        if (!is_null($model) && decrypt($model->token) === substr($token, strlen($identifier))) {\n            return $model;\n        }\n\n        return null;\n    }\n\n    /**\n     * Returns the standard prefix for API keys in the system.\n     */\n    public static function getPrefixForType(int $type): string\n    {\n        Assert::oneOf($type, [self::TYPE_ACCOUNT, self::TYPE_APPLICATION]);\n\n        return $type === self::TYPE_ACCOUNT ? 'ptlc_' : 'ptla_';\n    }\n\n    /**\n     * Generates a new identifier for an API key.\n     */\n    public static function generateTokenIdentifier(int $type): string\n    {\n        $prefix = self::getPrefixForType($type);\n\n        return $prefix . Str::random(self::IDENTIFIER_LENGTH - strlen($prefix));\n    }\n}\n"
  },
  {
    "path": "app/Models/Attributes/Identifiable.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models\\Attributes;\n\n#[\\Attribute(\\Attribute::TARGET_CLASS)]\nreadonly class Identifiable\n{\n    public function __construct(public string $prefix, public string $column = 'uuid')\n    {\n    }\n}\n"
  },
  {
    "path": "app/Models/AuditLog.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Http\\Request;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\n\n/**\n * @deprecated — this class will be dropped in a future version, use the activity log\n */\nclass AuditLog extends Model\n{\n    public const UPDATED_AT = null;\n\n    public static array $validationRules = [\n        'uuid' => 'required|uuid',\n        'action' => 'required|string|max:191',\n        'subaction' => 'nullable|string|max:191',\n        'device' => 'array',\n        'device.ip_address' => 'ip',\n        'device.user_agent' => 'string',\n        'metadata' => 'array',\n    ];\n\n    protected $table = 'audit_logs';\n\n    protected bool $immutableDates = true;\n\n    protected $casts = [\n        'is_system' => 'bool',\n        'device' => 'array',\n        'metadata' => 'array',\n    ];\n\n    protected $guarded = [\n        'id',\n        'created_at',\n    ];\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\User, $this>\n     */\n    public function user(): BelongsTo\n    {\n        return $this->belongsTo(User::class);\n    }\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function server(): BelongsTo\n    {\n        return $this->belongsTo(Server::class);\n    }\n\n    /**\n     * Creates a new AuditLog model and returns it, attaching device information and the\n     * currently authenticated user if available. This model is not saved at this point, so\n     * you can always make modifications to it as needed before saving.\n     *\n     * @deprecated\n     */\n    public static function instance(string $action, array $metadata, bool $isSystem = false): self\n    {\n        $request = Container::getInstance()->make('request');\n        if ($isSystem || !$request instanceof Request) { // @phpstan-ignore instanceof.alwaysTrue\n            $request = null;\n        }\n\n        return (new self())->fill([\n            'uuid' => Uuid::uuid4()->toString(),\n            'is_system' => $isSystem,\n            'user_id' => ($request && $request->user()) ? $request->user()->id : null,\n            'server_id' => null,\n            'action' => $action,\n            'device' => $request ? [\n                'ip_address' => $request->getClientIp() ?? '127.0.0.1',\n                'user_agent' => $request->userAgent() ?? '',\n            ] : [],\n            'metadata' => $metadata,\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Models/Backup.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\SoftDeletes;\nuse Pterodactyl\\Contracts\\Models\\Identifiable;\nuse Pterodactyl\\Models\\Traits\\HasRealtimeIdentifier;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\n\n/**\n * @property int $id\n * @property int $server_id\n * @property string $uuid\n * @property bool $is_successful\n * @property bool $is_locked\n * @property string $name\n * @property string[] $ignored_files\n * @property string $disk\n * @property string|null $checksum\n * @property int $bytes\n * @property string|null $upload_id\n * @property \\Carbon\\CarbonImmutable|null $completed_at\n * @property \\Carbon\\CarbonImmutable $created_at\n * @property \\Carbon\\CarbonImmutable $updated_at\n * @property \\Carbon\\CarbonImmutable|null $deleted_at\n * @property Server $server\n * @property \\Pterodactyl\\Models\\AuditLog[] $audits\n */\n#[Attributes\\Identifiable('bkup')]\nclass Backup extends Model implements Identifiable\n{\n    /** @use HasFactory<\\Database\\Factories\\BackupFactory> */\n    use HasFactory;\n    use SoftDeletes;\n    use HasRealtimeIdentifier;\n\n    public const RESOURCE_NAME = 'backup';\n\n    public const ADAPTER_WINGS = 'wings';\n    public const ADAPTER_AWS_S3 = 's3';\n\n    protected $table = 'backups';\n\n    protected bool $immutableDates = true;\n\n    protected $casts = [\n        'id' => 'int',\n        'is_successful' => 'bool',\n        'is_locked' => 'bool',\n        'ignored_files' => 'array',\n        'bytes' => 'int',\n        'completed_at' => 'datetime',\n    ];\n\n    protected $attributes = [\n        'is_successful' => false,\n        'is_locked' => false,\n        'checksum' => null,\n        'bytes' => 0,\n        'upload_id' => null,\n    ];\n\n    protected $guarded = ['id', 'created_at', 'updated_at', 'deleted_at'];\n\n    public static array $validationRules = [\n        'server_id' => 'bail|required|numeric|exists:servers,id',\n        'uuid' => 'required|uuid',\n        'is_successful' => 'boolean',\n        'is_locked' => 'boolean',\n        'name' => 'required|string',\n        'ignored_files' => 'array',\n        'disk' => 'required|string',\n        'checksum' => 'nullable|string',\n        'bytes' => 'numeric',\n        'upload_id' => 'nullable|string',\n    ];\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function server(): BelongsTo\n    {\n        return $this->belongsTo(Server::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/Database.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\nuse Pterodactyl\\Contracts\\Extensions\\HashidsInterface;\n\n/**\n * @property int $id\n * @property int $server_id\n * @property int $database_host_id\n * @property string $database\n * @property string $username\n * @property string $remote\n * @property string $password\n * @property int $max_connections\n * @property \\Carbon\\Carbon $created_at\n * @property \\Carbon\\Carbon $updated_at\n * @property Server $server\n * @property DatabaseHost $host\n */\nclass Database extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\DatabaseFactory> */\n    use HasFactory;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'server_database';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'databases';\n\n    /**\n     * The attributes excluded from the model's JSON form.\n     */\n    protected $hidden = ['password'];\n\n    /**\n     * Fields that are mass assignable.\n     */\n    protected $fillable = [\n        'server_id', 'database_host_id', 'database', 'username', 'password', 'remote', 'max_connections',\n    ];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'server_id' => 'integer',\n        'database_host_id' => 'integer',\n        'max_connections' => 'integer',\n    ];\n\n    public static array $validationRules = [\n        'server_id' => 'required|numeric|exists:servers,id',\n        'database_host_id' => 'required|exists:database_hosts,id',\n        'database' => 'required|string|alpha_dash|between:3,48',\n        'username' => 'string|alpha_dash|between:3,100',\n        'max_connections' => 'nullable|integer',\n        'remote' => 'required|string|regex:/^[\\w\\-\\/.%:]+$/',\n        'password' => 'string',\n    ];\n\n    public function getRouteKeyName(): string\n    {\n        return $this->getKeyName();\n    }\n\n    /**\n     * Resolves the database using the ID by checking if the value provided is a HashID\n     * string value, or just the ID to the database itself.\n     *\n     * @param string|null $field\n     *\n     * @throws \\Illuminate\\Contracts\\Container\\BindingResolutionException\n     */\n    public function resolveRouteBinding($value, $field = null): ?\\Illuminate\\Database\\Eloquent\\Model\n    {\n        if (is_scalar($value) && ($field ?? $this->getRouteKeyName()) === 'id') {\n            $value = ctype_digit((string) $value)\n                ? $value\n                : Container::getInstance()->make(HashidsInterface::class)->decodeFirst($value);\n        }\n\n        return $this->where($field ?? $this->getRouteKeyName(), $value)->firstOrFail();\n    }\n\n    /**\n     * Gets the host database server associated with a database.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\DatabaseHost, $this>\n     */\n    public function host(): BelongsTo\n    {\n        return $this->belongsTo(DatabaseHost::class, 'database_host_id');\n    }\n\n    /**\n     * Gets the server associated with a database.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function server(): BelongsTo\n    {\n        return $this->belongsTo(Server::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/DatabaseHost.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\n\n/**\n * @property int $id\n * @property string $name\n * @property string $host\n * @property int $port\n * @property string $username\n * @property string $password\n * @property int|null $max_databases\n * @property int|null $node_id\n * @property \\Carbon\\CarbonImmutable $created_at\n * @property \\Carbon\\CarbonImmutable $updated_at\n */\nclass DatabaseHost extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\DatabaseHostFactory> */\n    use HasFactory;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'database_host';\n\n    protected bool $immutableDates = true;\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'database_hosts';\n\n    /**\n     * The attributes excluded from the model's JSON form.\n     */\n    protected $hidden = ['password'];\n\n    /**\n     * Fields that are mass assignable.\n     */\n    protected $fillable = [\n        'name', 'host', 'port', 'username', 'password', 'max_databases', 'node_id',\n    ];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'id' => 'integer',\n        'max_databases' => 'integer',\n        'node_id' => 'integer',\n    ];\n\n    /**\n     * Validation rules to assign to this model.\n     */\n    public static array $validationRules = [\n        'name' => 'required|string|max:191',\n        'host' => 'required|string|regex:/^[\\w\\-\\.]+$/',\n        'port' => 'required|numeric|between:1,65535',\n        'username' => 'required|string|max:32',\n        'password' => 'nullable|string',\n        'node_id' => 'sometimes|nullable|integer|exists:nodes,id',\n    ];\n\n    /**\n     * Gets the node associated with a database host.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Node, $this>\n     */\n    public function node(): BelongsTo\n    {\n        return $this->belongsTo(Node::class);\n    }\n\n    /**\n     * Gets the databases associated with this host.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Database, $this>\n     */\n    public function databases(): HasMany\n    {\n        return $this->hasMany(Database::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/Egg.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Pterodactyl\\Contracts\\Models\\Identifiable;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Pterodactyl\\Models\\Traits\\HasRealtimeIdentifier;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\n\n/**\n * @property int $id\n * @property string $uuid\n * @property int $nest_id\n * @property string $author\n * @property string $name\n * @property string|null $description\n * @property array|null $features\n * @property string $docker_image -- deprecated, use $docker_images\n * @property array<string, string> $docker_images\n * @property string $update_url\n * @property bool $force_outgoing_ip\n * @property array|null $file_denylist\n * @property string|null $config_files\n * @property string|null $config_startup\n * @property string|null $config_logs\n * @property string|null $config_stop\n * @property int|null $config_from\n * @property string|null $startup\n * @property bool $script_is_privileged\n * @property string|null $script_install\n * @property string $script_entry\n * @property string $script_container\n * @property int|null $copy_script_from\n * @property \\Carbon\\Carbon $created_at\n * @property \\Carbon\\Carbon $updated_at\n * @property string|null $copy_script_install\n * @property string $copy_script_entry\n * @property string $copy_script_container\n * @property string|null $inherit_config_files\n * @property string|null $inherit_config_startup\n * @property string|null $inherit_config_logs\n * @property string|null $inherit_config_stop\n * @property string $inherit_file_denylist\n * @property array|null $inherit_features\n * @property Nest $nest\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\Server[] $servers\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\EggVariable[] $variables\n * @property Egg|null $scriptFrom\n * @property Egg|null $configFrom\n */\n#[Attributes\\Identifiable('eegg')]\nclass Egg extends Model implements Identifiable\n{\n    /** @use HasFactory<\\Database\\Factories\\EggFactory> */\n    use HasFactory;\n    use HasRealtimeIdentifier;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'egg';\n\n    /**\n     * Defines the current egg export version.\n     */\n    public const EXPORT_VERSION = 'PTDL_v2';\n\n    /**\n     * Different features that can be enabled on any given egg. These are used internally\n     * to determine which types of frontend functionality should be shown to the user. Eggs\n     * will automatically inherit features from a parent egg if they are already configured\n     * to copy configuration values from said egg.\n     *\n     * To skip copying the features, an empty array value should be passed in (\"[]\") rather\n     * than leaving it null.\n     */\n    public const FEATURE_EULA_POPUP = 'eula';\n    public const FEATURE_FASTDL = 'fastdl';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'eggs';\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $fillable = [\n        'name',\n        'description',\n        'features',\n        'docker_images',\n        'force_outgoing_ip',\n        'file_denylist',\n        'config_files',\n        'config_startup',\n        'config_logs',\n        'config_stop',\n        'config_from',\n        'startup',\n        'script_is_privileged',\n        'script_install',\n        'script_entry',\n        'script_container',\n        'copy_script_from',\n    ];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'nest_id' => 'integer',\n        'config_from' => 'integer',\n        'script_is_privileged' => 'boolean',\n        'force_outgoing_ip' => 'boolean',\n        'copy_script_from' => 'integer',\n        'features' => 'array',\n        'docker_images' => 'array',\n        'file_denylist' => 'array',\n    ];\n\n    public static array $validationRules = [\n        'nest_id' => 'required|bail|numeric|exists:nests,id',\n        'uuid' => 'required|string|size:36',\n        'name' => 'required|string|max:191',\n        'description' => 'string|nullable',\n        'features' => 'array|nullable',\n        'author' => 'required|string|email',\n        'file_denylist' => 'array|nullable',\n        'file_denylist.*' => 'string',\n        'docker_images' => 'required|array|min:1',\n        'docker_images.*' => ['required', 'string', 'max:191'],\n        'startup' => 'required|nullable|string',\n        'config_from' => 'sometimes|bail|nullable|numeric|exists:eggs,id',\n        'config_stop' => 'required_without:config_from|nullable|string|max:191',\n        'config_startup' => 'required_without:config_from|nullable|json',\n        'config_logs' => 'required_without:config_from|nullable|json',\n        'config_files' => 'required_without:config_from|nullable|json',\n        'update_url' => 'sometimes|nullable|string',\n        'force_outgoing_ip' => 'sometimes|boolean',\n    ];\n\n    protected $attributes = [\n        'features' => null,\n        'file_denylist' => null,\n        'config_stop' => null,\n        'config_startup' => null,\n        'config_logs' => null,\n        'config_files' => null,\n        'update_url' => null,\n    ];\n\n    /**\n     * Returns the install script for the egg; if egg is copying from another\n     * it will return the copied script.\n     */\n    public function getCopyScriptInstallAttribute(): ?string\n    {\n        if (!is_null($this->script_install) || is_null($this->copy_script_from)) {\n            return $this->script_install;\n        }\n\n        return $this->scriptFrom->script_install;\n    }\n\n    /**\n     * Returns the entry command for the egg; if egg is copying from another\n     * it will return the copied entry command.\n     */\n    public function getCopyScriptEntryAttribute(): string\n    {\n        if (is_null($this->copy_script_from)) {\n            return $this->script_entry;\n        }\n\n        return $this->scriptFrom->script_entry;\n    }\n\n    /**\n     * Returns the install container for the egg; if egg is copying from another\n     * it will return the copied install container.\n     */\n    public function getCopyScriptContainerAttribute(): string\n    {\n        if (is_null($this->copy_script_from)) {\n            return $this->script_container;\n        }\n\n        return $this->scriptFrom->script_container;\n    }\n\n    /**\n     * Return the file configuration for an egg.\n     */\n    public function getInheritConfigFilesAttribute(): ?string\n    {\n        if (!is_null($this->config_files) || is_null($this->config_from)) {\n            return $this->config_files;\n        }\n\n        return $this->configFrom->config_files;\n    }\n\n    /**\n     * Return the startup configuration for an egg.\n     */\n    public function getInheritConfigStartupAttribute(): ?string\n    {\n        if (!is_null($this->config_startup) || is_null($this->config_from)) {\n            return $this->config_startup;\n        }\n\n        return $this->configFrom->config_startup;\n    }\n\n    /**\n     * Return the log reading configuration for an egg.\n     */\n    public function getInheritConfigLogsAttribute(): ?string\n    {\n        if (!is_null($this->config_logs) || is_null($this->config_from)) {\n            return $this->config_logs;\n        }\n\n        return $this->configFrom->config_logs;\n    }\n\n    /**\n     * Return the stop command configuration for an egg.\n     */\n    public function getInheritConfigStopAttribute(): ?string\n    {\n        if (!is_null($this->config_stop) || is_null($this->config_from)) {\n            return $this->config_stop;\n        }\n\n        return $this->configFrom->config_stop;\n    }\n\n    /**\n     * Returns the features available to this egg from the parent configuration if there are\n     * no features defined for this egg specifically and there is a parent egg configured.\n     */\n    public function getInheritFeaturesAttribute(): ?array\n    {\n        if (!is_null($this->features) || is_null($this->config_from)) {\n            return $this->features;\n        }\n\n        return $this->configFrom->features;\n    }\n\n    /**\n     * Returns the features available to this egg from the parent configuration if there are\n     * no features defined for this egg specifically and there is a parent egg configured.\n     */\n    public function getInheritFileDenylistAttribute(): ?array\n    {\n        if (is_null($this->config_from)) {\n            return $this->file_denylist;\n        }\n\n        return $this->configFrom->file_denylist;\n    }\n\n    /**\n     * Gets nest associated with an egg.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Nest, $this>\n     */\n    public function nest(): BelongsTo\n    {\n        return $this->belongsTo(Nest::class);\n    }\n\n    /**\n     * Gets all servers associated with this egg.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function servers(): HasMany\n    {\n        return $this->hasMany(Server::class, 'egg_id');\n    }\n\n    /**\n     * Gets all variables associated with this egg.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\EggVariable, $this>\n     */\n    public function variables(): HasMany\n    {\n        return $this->hasMany(EggVariable::class, 'egg_id');\n    }\n\n    /**\n     * Get the parent egg from which to copy scripts.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<self, $this>\n     */\n    public function scriptFrom(): BelongsTo\n    {\n        return $this->belongsTo(self::class, 'copy_script_from');\n    }\n\n    /**\n     * Get the parent egg from which to copy configuration settings.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<self, $this>\n     */\n    public function configFrom(): BelongsTo\n    {\n        return $this->belongsTo(self::class, 'config_from');\n    }\n}\n"
  },
  {
    "path": "app/Models/EggMount.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nclass EggMount extends Model\n{\n    protected $table = 'egg_mount';\n\n    protected $primaryKey;\n\n    public $incrementing = false;\n}\n"
  },
  {
    "path": "app/Models/EggVariable.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Relations\\HasOne;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\n\n/**\n * @property int $id\n * @property int $egg_id\n * @property string $name\n * @property string $description\n * @property string $env_variable\n * @property string $default_value\n * @property bool $user_viewable\n * @property bool $user_editable\n * @property string $rules\n * @property \\Carbon\\CarbonImmutable $created_at\n * @property \\Carbon\\CarbonImmutable $updated_at\n * @property bool $required\n * @property Egg $egg\n * @property ServerVariable $serverVariable\n *\n * The \"server_value\" variable is only present on the object if you've loaded this model\n * using the server relationship.\n * @property string|null $server_value\n */\nclass EggVariable extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\EggVariableFactory> */\n    use HasFactory;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'egg_variable';\n\n    /**\n     * Reserved environment variable names.\n     */\n    public const RESERVED_ENV_NAMES = 'SERVER_MEMORY,SERVER_IP,SERVER_PORT,ENV,HOME,USER,STARTUP,SERVER_UUID,UUID';\n\n    protected bool $immutableDates = true;\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'egg_variables';\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $guarded = ['id', 'created_at', 'updated_at'];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'egg_id' => 'integer',\n        'user_viewable' => 'bool',\n        'user_editable' => 'bool',\n    ];\n\n    public static array $validationRules = [\n        'egg_id' => 'exists:eggs,id',\n        'name' => 'required|string|between:1,191',\n        'description' => 'string',\n        'env_variable' => 'required|regex:/^[\\w]{1,191}$/|notIn:' . self::RESERVED_ENV_NAMES,\n        'default_value' => 'string',\n        'user_viewable' => 'boolean',\n        'user_editable' => 'boolean',\n        'rules' => 'required|string',\n    ];\n\n    protected $attributes = [\n        'user_editable' => 0,\n        'user_viewable' => 0,\n    ];\n\n    public function getRequiredAttribute(): bool\n    {\n        return in_array('required', explode('|', $this->rules));\n    }\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasOne<\\Pterodactyl\\Models\\Egg, $this>\n     */\n    public function egg(): HasOne\n    {\n        return $this->hasOne(Egg::class);\n    }\n\n    /**\n     * Return server variables associated with this variable.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\ServerVariable, $this>\n     */\n    public function serverVariable(): HasMany\n    {\n        return $this->hasMany(ServerVariable::class, 'variable_id');\n    }\n}\n"
  },
  {
    "path": "app/Models/Filters/AdminServerFilter.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models\\Filters;\n\nuse Spatie\\QueryBuilder\\Filters\\Filter;\nuse Illuminate\\Database\\Eloquent\\Builder;\n\nclass AdminServerFilter implements Filter\n{\n    /**\n     * A multi-column filter for the servers table that allows an administrative user to search\n     * across UUID, name, owner username, and owner email.\n     *\n     * @param string $value\n     */\n    public function __invoke(Builder $query, $value, string $property)\n    {\n        if ($query->getQuery()->from !== 'servers') {\n            throw new \\BadMethodCallException('Cannot use the AdminServerFilter against a non-server model.');\n        }\n        $query\n            ->select('servers.*')\n            ->leftJoin('users', 'users.id', '=', 'servers.owner_id')\n            ->where(function (Builder $builder) use ($value) {\n                $builder->where('servers.uuid', $value)\n                    ->orWhere('servers.uuid', 'LIKE', \"$value%\")\n                    ->orWhere('servers.uuidShort', $value)\n                    ->orWhere('servers.external_id', $value)\n                    ->orWhereRaw('LOWER(users.username) LIKE ?', [\"%$value%\"])\n                    ->orWhereRaw('LOWER(users.email) LIKE ?', [\"$value%\"])\n                    ->orWhereRaw('LOWER(servers.name) LIKE ?', [\"%$value%\"]);\n            })\n            ->groupBy('servers.id');\n    }\n}\n"
  },
  {
    "path": "app/Models/Filters/MultiFieldServerFilter.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models\\Filters;\n\nuse Illuminate\\Support\\Str;\nuse Spatie\\QueryBuilder\\Filters\\Filter;\nuse Illuminate\\Database\\Eloquent\\Builder;\n\nclass MultiFieldServerFilter implements Filter\n{\n    /**\n     * If we detect that the value matches an IPv4 address we will use a different type of filtering\n     * to look at the allocations.\n     */\n    private const IPV4_REGEX = '/^(?:[0-9]{1,3}\\.){3}[0-9]{1,3}(\\:\\d{1,5})?$/';\n\n    /**\n     * A multi-column filter for the servers table that allows you to pass in a single value and\n     * search across multiple columns. This allows us to provide a very generic search ability for\n     * the frontend.\n     *\n     * @param string $value\n     */\n    public function __invoke(Builder $query, $value, string $property)\n    {\n        if ($query->getQuery()->from !== 'servers') {\n            throw new \\BadMethodCallException('Cannot use the MultiFieldServerFilter against a non-server model.');\n        }\n\n        if (preg_match(self::IPV4_REGEX, $value) || preg_match('/^:\\d{1,5}$/', $value)) {\n            $query\n                // Only select the server values, otherwise you'll end up merging the allocation and\n                // server objects together, resulting in incorrect behavior and returned values.\n                ->select('servers.*')\n                ->join('allocations', 'allocations.server_id', '=', 'servers.id')\n                ->where(function (Builder $builder) use ($value) {\n                    $parts = explode(':', $value);\n\n                    $builder->when(\n                        !Str::startsWith($value, ':'),\n                        // When the string does not start with a \":\" it means we're looking for an IP or IP:Port\n                        // combo, so use a query to handle that.\n                        function (Builder $builder) use ($parts) {\n                            $builder->orWhere('allocations.ip', $parts[0]);\n                            if (!is_null($parts[1] ?? null)) {\n                                $builder->where('allocations.port', 'LIKE', \"{$parts[1]}%\");\n                            }\n                        },\n                        // Otherwise, just try to search for that specific port in the allocations.\n                        function (Builder $builder) use ($value) {\n                            $builder->orWhere('allocations.port', 'LIKE', substr($value, 1) . '%');\n                        }\n                    );\n                })\n                ->groupBy('servers.id');\n\n            return;\n        }\n\n        $query\n            ->where(function (Builder $builder) use ($value) {\n                $builder->where('servers.uuid', $value)\n                    ->orWhere('servers.uuid', 'LIKE', \"$value%\")\n                    ->orWhere('servers.uuidShort', $value)\n                    ->orWhere('servers.external_id', $value)\n                    ->orWhereRaw('LOWER(servers.name) LIKE ?', [\"%$value%\"]);\n            });\n    }\n}\n"
  },
  {
    "path": "app/Models/Location.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasManyThrough;\n\n/**\n * @property int $id\n * @property string $short\n * @property string $long\n * @property \\Carbon\\Carbon $created_at\n * @property \\Carbon\\Carbon $updated_at\n * @property \\Pterodactyl\\Models\\Node[] $nodes\n * @property \\Pterodactyl\\Models\\Server[] $servers\n */\nclass Location extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\LocationFactory> */\n    use HasFactory;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'location';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'locations';\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $guarded = ['id', 'created_at', 'updated_at'];\n\n    /**\n     * Rules ensuring that the raw data stored in the database meets expectations.\n     */\n    public static array $validationRules = [\n        'short' => 'required|string|between:1,60|unique:locations,short',\n        'long' => 'string|nullable|between:1,191',\n    ];\n\n    public function getRouteKeyName(): string\n    {\n        return $this->getKeyName();\n    }\n\n    /**\n     * Gets the nodes in a specified location.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Node, $this>\n     */\n    public function nodes(): HasMany\n    {\n        return $this->hasMany(Node::class);\n    }\n\n    /**\n     * Gets the servers within a given location.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasManyThrough<\\Pterodactyl\\Models\\Server, \\Pterodactyl\\Models\\Node, $this>\n     */\n    public function servers(): HasManyThrough\n    {\n        return $this->hasManyThrough(Server::class, Node::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/Model.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Support\\Arr;\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Support\\Carbon;\nuse Illuminate\\Validation\\Rule;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Contracts\\Validation\\Validator;\nuse Illuminate\\Validation\\ValidationException;\nuse Pterodactyl\\Exceptions\\Model\\DataValidationException;\nuse Illuminate\\Database\\Eloquent\\Model as IlluminateModel;\nuse Illuminate\\Contracts\\Validation\\Factory as ValidationFactory;\n\nabstract class Model extends IlluminateModel\n{\n    /**\n     * Set to true to return immutable Carbon date instances from the model.\n     */\n    protected bool $immutableDates = false;\n\n    /**\n     * Determines if the model should undergo data validation before it is saved\n     * to the database.\n     */\n    protected bool $skipValidation = false;\n\n    protected static ValidationFactory $validatorFactory;\n\n    public static array $validationRules = [];\n\n    /**\n     * Listen for the model saving event and fire off the validation\n     * function before it is saved.\n     *\n     * @throws \\Illuminate\\Contracts\\Container\\BindingResolutionException\n     */\n    protected static function boot()\n    {\n        parent::boot();\n\n        static::$validatorFactory = Container::getInstance()->make(ValidationFactory::class);\n\n        static::saving(function (Model $model) {\n            try {\n                $model->validate();\n            } catch (ValidationException $exception) {\n                throw new DataValidationException($exception->validator, $model);\n            }\n\n            return true;\n        });\n    }\n\n    /**\n     * Returns the model key to use for route model binding. By default, we'll\n     * assume every model uses a UUID field for this. If the model does not have\n     * a UUID and is using a different key it should be specified on the model\n     * itself.\n     *\n     * You may also optionally override this on a per-route basis by declaring\n     * the key name in the URL definition, like \"{user:id}\".\n     */\n    public function getRouteKeyName(): string\n    {\n        return 'uuid';\n    }\n\n    /**\n     * Set the model to skip validation when saving.\n     */\n    public function skipValidation(): self\n    {\n        $this->skipValidation = true;\n\n        return $this;\n    }\n\n    /**\n     * Returns the validator instance used by this model.\n     */\n    public function getValidator(): \\Illuminate\\Validation\\Validator\n    {\n        $rules = $this->exists ? static::getRulesForUpdate($this) : static::getRules();\n\n        // @phpstan-ignore-next-line return.type\n        return static::$validatorFactory->make([], $rules);\n    }\n\n    /**\n     * Returns the rules associated with this model.\n     */\n    public static function getRules(): array\n    {\n        $rules = static::$validationRules;\n        foreach ($rules as $key => &$rule) {\n            $rule = is_array($rule) ? $rule : explode('|', $rule);\n        }\n\n        return $rules;\n    }\n\n    /**\n     * Returns the rules for a specific field. If the field is not found an empty\n     * array is returned.\n     */\n    public static function getRulesForField(string $field): array\n    {\n        return Arr::get(static::getRules(), $field) ?? [];\n    }\n\n    /**\n     * Returns the rules associated with the model, specifically for updating the given model\n     * rather than just creating it.\n     */\n    public static function getRulesForUpdate($model, string $column = 'id'): array\n    {\n        if ($model instanceof Model) {\n            [$id, $column] = [$model->getKey(), $model->getKeyName()];\n        }\n\n        $rules = static::getRules();\n        foreach ($rules as $key => &$data) {\n            // For each rule in a given field, iterate over it and confirm if the rule\n            // is one for a unique field. If that is the case, append the ID of the current\n            // working model, so we don't run into errors due to the way that field validation\n            // works.\n            foreach ($data as &$datum) {\n                if (!is_string($datum) || !Str::startsWith($datum, 'unique')) {\n                    continue;\n                }\n\n                [, $args] = explode(':', $datum);\n                $args = explode(',', $args);\n\n                $datum = Rule::unique($args[0], $args[1] ?? $key)->ignore($id ?? $model, $column);\n            }\n        }\n\n        return $rules;\n    }\n\n    /**\n     * Determines if the model is in a valid state or not.\n     *\n     * @throws ValidationException\n     */\n    public function validate(): void\n    {\n        if ($this->skipValidation) {\n            return;\n        }\n\n        $validator = $this->getValidator();\n        $validator->setData(\n            // Trying to do self::toArray() here will leave out keys based on the whitelist/blacklist\n            // for that model. Doing this will return all the attributes in a format that can\n            // properly be validated.\n            $this->addCastAttributesToArray(\n                $this->getAttributes(),\n                $this->getMutatedAttributes()\n            )\n        );\n\n        if (!$validator->passes()) {\n            throw new ValidationException($validator);\n        }\n    }\n\n    /**\n     * Return a timestamp as DateTime object.\n     */\n    protected function asDateTime($value): Carbon|CarbonImmutable\n    {\n        if (!$this->immutableDates) {\n            return parent::asDateTime($value);\n        }\n\n        return parent::asDateTime($value)->toImmutable();\n    }\n}\n"
  },
  {
    "path": "app/Models/Mount.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Validation\\Rules\\NotIn;\nuse Pterodactyl\\Contracts\\Models\\Identifiable;\nuse Pterodactyl\\Models\\Traits\\HasRealtimeIdentifier;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsToMany;\n\n/**\n * @property int $id\n * @property string $uuid\n * @property string $name\n * @property string $description\n * @property string $source\n * @property string $target\n * @property bool $read_only\n * @property bool $user_mountable\n * @property \\Pterodactyl\\Models\\Egg[]|\\Illuminate\\Database\\Eloquent\\Collection $eggs\n * @property \\Pterodactyl\\Models\\Node[]|\\Illuminate\\Database\\Eloquent\\Collection $nodes\n * @property \\Pterodactyl\\Models\\Server[]|\\Illuminate\\Database\\Eloquent\\Collection $servers\n */\n#[Attributes\\Identifiable('moun')]\nclass Mount extends Model implements Identifiable\n{\n    use HasRealtimeIdentifier;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'mount';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'mounts';\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $guarded = ['id', 'uuid'];\n\n    /**\n     * Default values for specific fields in the database.\n     */\n    protected $casts = [\n        'id' => 'int',\n        'read_only' => 'bool',\n        'user_mountable' => 'bool',\n    ];\n\n    /**\n     * Rules verifying that the data being stored matches the expectations of the database.\n     */\n    public static array $validationRules = [\n        'name' => 'required|string|min:2|max:64|unique:mounts,name',\n        'description' => 'nullable|string|max:191',\n        'source' => 'required|string',\n        'target' => 'required|string',\n        'read_only' => 'sometimes|boolean',\n        'user_mountable' => 'sometimes|boolean',\n    ];\n\n    /**\n     * Implement language verification by overriding Eloquence's gather\n     * rules function.\n     */\n    public static function getRules(): array\n    {\n        $rules = parent::getRules();\n\n        $rules['source'][] = new NotIn(Mount::$invalidSourcePaths);\n        $rules['target'][] = new NotIn(Mount::$invalidTargetPaths);\n\n        return $rules;\n    }\n\n    /**\n     * Disable timestamps on this model.\n     */\n    public $timestamps = false;\n\n    /**\n     * Blacklisted source paths.\n     */\n    public static $invalidSourcePaths = [\n        '/etc/pterodactyl',\n        '/var/lib/pterodactyl/volumes',\n        '/srv/daemon-data',\n    ];\n\n    /**\n     * Blacklisted target paths.\n     */\n    public static $invalidTargetPaths = [\n        '/home/container',\n    ];\n\n    /**\n     * Returns all eggs that have this mount assigned.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsToMany<\\Pterodactyl\\Models\\Egg, $this>\n     */\n    public function eggs(): BelongsToMany\n    {\n        return $this->belongsToMany(Egg::class);\n    }\n\n    /**\n     * Returns all nodes that have this mount assigned.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsToMany<\\Pterodactyl\\Models\\Node, $this>\n     */\n    public function nodes(): BelongsToMany\n    {\n        return $this->belongsToMany(Node::class);\n    }\n\n    /**\n     * Returns all servers that have this mount assigned.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsToMany<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function servers(): BelongsToMany\n    {\n        return $this->belongsToMany(Server::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/MountNode.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Model;\n\nclass MountNode extends Model\n{\n    protected $table = 'mount_node';\n\n    protected $primaryKey;\n\n    public $incrementing = false;\n}\n"
  },
  {
    "path": "app/Models/MountServer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Model;\n\nclass MountServer extends Model\n{\n    protected $table = 'mount_server';\n\n    public $timestamps = false;\n\n    protected $primaryKey;\n\n    public $incrementing = false;\n}\n"
  },
  {
    "path": "app/Models/Nest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\n\n/**\n * @property int $id\n * @property string $uuid\n * @property string $author\n * @property string $name\n * @property string|null $description\n * @property \\Carbon\\Carbon $created_at\n * @property \\Carbon\\Carbon $updated_at\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\Server[] $servers\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\Egg[] $eggs\n */\nclass Nest extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\NestFactory> */\n    use HasFactory;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'nest';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'nests';\n\n    /**\n     * Fields that are mass assignable.\n     */\n    protected $fillable = [\n        'name',\n        'description',\n    ];\n\n    public static array $validationRules = [\n        'author' => 'required|string|email',\n        'name' => 'required|string|max:191',\n        'description' => 'nullable|string',\n    ];\n\n    /**\n     * Gets all eggs associated with this service.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Egg, $this>\n     */\n    public function eggs(): HasMany\n    {\n        return $this->hasMany(Egg::class);\n    }\n\n    /**\n     * Gets all servers associated with this nest.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function servers(): HasMany\n    {\n        return $this->hasMany(Server::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/Node.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Support\\Str;\nuse Symfony\\Component\\Yaml\\Yaml;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Notifications\\Notifiable;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Contracts\\Models\\Identifiable;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Pterodactyl\\Models\\Traits\\HasRealtimeIdentifier;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasManyThrough;\n\n/**\n * @property int $id\n * @property string $uuid\n * @property bool $public\n * @property string $name\n * @property string|null $description\n * @property int $location_id\n * @property string $fqdn\n * @property string $scheme\n * @property bool $behind_proxy\n * @property bool $maintenance_mode\n * @property int $memory\n * @property int $memory_overallocate\n * @property int $disk\n * @property int $disk_overallocate\n * @property int $upload_size\n * @property string $daemon_token_id\n * @property string $daemon_token\n * @property int $daemonListen\n * @property int $daemonSFTP\n * @property string $daemonBase\n * @property \\Carbon\\Carbon $created_at\n * @property \\Carbon\\Carbon $updated_at\n * @property Location $location\n * @property \\Pterodactyl\\Models\\Mount[]|\\Illuminate\\Database\\Eloquent\\Collection $mounts\n * @property \\Pterodactyl\\Models\\Server[]|\\Illuminate\\Database\\Eloquent\\Collection $servers\n * @property \\Pterodactyl\\Models\\Allocation[]|\\Illuminate\\Database\\Eloquent\\Collection $allocations\n */\n#[Attributes\\Identifiable('node')]\nclass Node extends Model implements Identifiable\n{\n    /** @use HasFactory<\\Database\\Factories\\NodeFactory> */\n    use HasFactory;\n    use Notifiable;\n    use HasRealtimeIdentifier;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'node';\n\n    public const DAEMON_TOKEN_ID_LENGTH = 16;\n    public const DAEMON_TOKEN_LENGTH = 64;\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'nodes';\n\n    /**\n     * The attributes excluded from the model's JSON form.\n     */\n    protected $hidden = ['daemon_token_id', 'daemon_token'];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'location_id' => 'integer',\n        'memory' => 'integer',\n        'disk' => 'integer',\n        'daemonListen' => 'integer',\n        'daemonSFTP' => 'integer',\n        'behind_proxy' => 'boolean',\n        'public' => 'boolean',\n        'maintenance_mode' => 'boolean',\n    ];\n\n    /**\n     * Fields that are mass assignable.\n     */\n    protected $fillable = [\n        'public', 'name', 'location_id',\n        'description', 'fqdn', 'scheme', 'behind_proxy',\n        'memory', 'memory_overallocate', 'disk',\n        'disk_overallocate', 'upload_size', 'daemonBase',\n        'daemonSFTP', 'daemonListen',\n        'description', 'maintenance_mode',\n    ];\n\n    public static array $validationRules = [\n        'name' => 'required|regex:/^([\\w .-]{1,100})$/',\n        'description' => 'string|nullable',\n        'location_id' => 'required|exists:locations,id',\n        'public' => 'boolean',\n        'fqdn' => 'required|string',\n        'scheme' => 'required',\n        'behind_proxy' => 'boolean',\n        'memory' => 'required|numeric|min:1',\n        'memory_overallocate' => 'required|numeric|min:-1',\n        'disk' => 'required|numeric|min:1',\n        'disk_overallocate' => 'required|numeric|min:-1',\n        'daemonBase' => 'sometimes|required|regex:/^([\\/][\\d\\w.\\-\\/]+)$/',\n        'daemonSFTP' => 'required|numeric|between:1,65535',\n        'daemonListen' => 'required|numeric|between:1,65535',\n        'maintenance_mode' => 'boolean',\n        'upload_size' => 'int|min:1',\n    ];\n\n    /**\n     * Default values for specific columns that are generally not changed on base installs.\n     */\n    protected $attributes = [\n        'public' => true,\n        'behind_proxy' => false,\n        'memory_overallocate' => 0,\n        'disk_overallocate' => 0,\n        'daemonBase' => '/var/lib/pterodactyl/volumes',\n        'daemonSFTP' => 2022,\n        'daemonListen' => 8080,\n        'maintenance_mode' => false,\n    ];\n\n    /**\n     * Get the connection address to use when making calls to this node.\n     */\n    public function getConnectionAddress(): string\n    {\n        return sprintf('%s://%s:%s', $this->scheme, $this->fqdn, $this->daemonListen);\n    }\n\n    /**\n     * Returns the configuration as an array.\n     */\n    public function getConfiguration(): array\n    {\n        return [\n            'debug' => false,\n            'uuid' => $this->uuid,\n            'token_id' => $this->daemon_token_id,\n            'token' => Container::getInstance()->make(Encrypter::class)->decrypt($this->daemon_token),\n            'api' => [\n                'host' => '0.0.0.0',\n                'port' => $this->daemonListen,\n                'ssl' => [\n                    'enabled' => (!$this->behind_proxy && $this->scheme === 'https'),\n                    'cert' => '/etc/letsencrypt/live/' . Str::lower($this->fqdn) . '/fullchain.pem',\n                    'key' => '/etc/letsencrypt/live/' . Str::lower($this->fqdn) . '/privkey.pem',\n                ],\n                'upload_limit' => $this->upload_size,\n            ],\n            'system' => [\n                'data' => $this->daemonBase,\n                'sftp' => [\n                    'bind_port' => $this->daemonSFTP,\n                ],\n            ],\n            'allowed_mounts' => $this->mounts->pluck('source')->toArray(),\n            'remote' => route('index'),\n        ];\n    }\n\n    /**\n     * Returns the configuration in Yaml format.\n     */\n    public function getYamlConfiguration(): string\n    {\n        return Yaml::dump($this->getConfiguration(), 4, 2, Yaml::DUMP_EMPTY_ARRAY_AS_SEQUENCE);\n    }\n\n    /**\n     * Returns the configuration in JSON format.\n     */\n    public function getJsonConfiguration(bool $pretty = false): string\n    {\n        return json_encode($this->getConfiguration(), $pretty ? JSON_UNESCAPED_SLASHES | JSON_PRETTY_PRINT : JSON_UNESCAPED_SLASHES);\n    }\n\n    /**\n     * Helper function to return the decrypted key for a node.\n     */\n    public function getDecryptedKey(): string\n    {\n        return (string) Container::getInstance()->make(Encrypter::class)->decrypt(\n            $this->daemon_token\n        );\n    }\n\n    public function isUnderMaintenance(): bool\n    {\n        return $this->maintenance_mode;\n    }\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasManyThrough<\\Pterodactyl\\Models\\Mount, \\Pterodactyl\\Models\\MountNode, $this>\n     */\n    public function mounts(): HasManyThrough\n    {\n        return $this->hasManyThrough(Mount::class, MountNode::class, 'node_id', 'id', 'id', 'mount_id');\n    }\n\n    /**\n     * Gets the location associated with a node.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Location, $this>\n     */\n    public function location(): BelongsTo\n    {\n        return $this->belongsTo(Location::class);\n    }\n\n    /**\n     * Gets the servers associated with a node.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function servers(): HasMany\n    {\n        return $this->hasMany(Server::class);\n    }\n\n    /**\n     * Gets the allocations associated with a node.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Allocation, $this>\n     */\n    public function allocations(): HasMany\n    {\n        return $this->hasMany(Allocation::class);\n    }\n\n    /**\n     * Returns a boolean if the node is viable for an additional server to be placed on it.\n     */\n    public function isViable(int $memory, int $disk): bool\n    {\n        $memoryLimit = $this->memory * (1 + ($this->memory_overallocate / 100));\n        $diskLimit = $this->disk * (1 + ($this->disk_overallocate / 100));\n\n        // @phpstan-ignore-next-line property.notFound, property.notFound\n        return ($this->sum_memory + $memory) <= $memoryLimit && ($this->sum_disk + $disk) <= $diskLimit;\n    }\n}\n"
  },
  {
    "path": "app/Models/Objects/DeploymentObject.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models\\Objects;\n\nclass DeploymentObject\n{\n    private bool $dedicated = false;\n\n    private array $locations = [];\n\n    private array $ports = [];\n\n    public function isDedicated(): bool\n    {\n        return $this->dedicated;\n    }\n\n    public function setDedicated(bool $dedicated): self\n    {\n        $this->dedicated = $dedicated;\n\n        return $this;\n    }\n\n    public function getLocations(): array\n    {\n        return $this->locations;\n    }\n\n    public function setLocations(array $locations): self\n    {\n        $this->locations = $locations;\n\n        return $this;\n    }\n\n    public function getPorts(): array\n    {\n        return $this->ports;\n    }\n\n    public function setPorts(array $ports): self\n    {\n        $this->ports = $ports;\n\n        return $this;\n    }\n}\n"
  },
  {
    "path": "app/Models/Permission.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Support\\Collection;\n\nclass Permission extends Model\n{\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'subuser_permission';\n\n    /**\n     * Constants defining different permissions available.\n     */\n    public const ACTION_WEBSOCKET_CONNECT = 'websocket.connect';\n    public const ACTION_CONTROL_CONSOLE = 'control.console';\n    public const ACTION_CONTROL_START = 'control.start';\n    public const ACTION_CONTROL_STOP = 'control.stop';\n    public const ACTION_CONTROL_RESTART = 'control.restart';\n\n    public const ACTION_DATABASE_READ = 'database.read';\n    public const ACTION_DATABASE_CREATE = 'database.create';\n    public const ACTION_DATABASE_UPDATE = 'database.update';\n    public const ACTION_DATABASE_DELETE = 'database.delete';\n    public const ACTION_DATABASE_VIEW_PASSWORD = 'database.view_password';\n\n    public const ACTION_SCHEDULE_READ = 'schedule.read';\n    public const ACTION_SCHEDULE_CREATE = 'schedule.create';\n    public const ACTION_SCHEDULE_UPDATE = 'schedule.update';\n    public const ACTION_SCHEDULE_DELETE = 'schedule.delete';\n\n    public const ACTION_USER_READ = 'user.read';\n    public const ACTION_USER_CREATE = 'user.create';\n    public const ACTION_USER_UPDATE = 'user.update';\n    public const ACTION_USER_DELETE = 'user.delete';\n\n    public const ACTION_BACKUP_READ = 'backup.read';\n    public const ACTION_BACKUP_CREATE = 'backup.create';\n    public const ACTION_BACKUP_DELETE = 'backup.delete';\n    public const ACTION_BACKUP_DOWNLOAD = 'backup.download';\n    public const ACTION_BACKUP_RESTORE = 'backup.restore';\n\n    public const ACTION_ALLOCATION_READ = 'allocation.read';\n    public const ACTION_ALLOCATION_CREATE = 'allocation.create';\n    public const ACTION_ALLOCATION_UPDATE = 'allocation.update';\n    public const ACTION_ALLOCATION_DELETE = 'allocation.delete';\n\n    public const ACTION_FILE_READ = 'file.read';\n    public const ACTION_FILE_READ_CONTENT = 'file.read-content';\n    public const ACTION_FILE_CREATE = 'file.create';\n    public const ACTION_FILE_UPDATE = 'file.update';\n    public const ACTION_FILE_DELETE = 'file.delete';\n    public const ACTION_FILE_ARCHIVE = 'file.archive';\n    public const ACTION_FILE_SFTP = 'file.sftp';\n\n    public const ACTION_STARTUP_READ = 'startup.read';\n    public const ACTION_STARTUP_UPDATE = 'startup.update';\n    public const ACTION_STARTUP_DOCKER_IMAGE = 'startup.docker-image';\n    public const ACTION_STARTUP_EGG_CHANGE = 'startup.egg-change';\n\n    public const ACTION_SETTINGS_RENAME = 'settings.rename';\n    public const ACTION_SETTINGS_REINSTALL = 'settings.reinstall';\n\n    public const ACTION_ACTIVITY_READ = 'activity.read';\n\n    /**\n     * Should timestamps be used on this model.\n     */\n    public $timestamps = false;\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'permissions';\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $guarded = ['id', 'created_at', 'updated_at'];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'subuser_id' => 'integer',\n    ];\n\n    public static array $validationRules = [\n        'subuser_id' => 'required|numeric|min:1',\n        'permission' => 'required|string',\n    ];\n\n    /**\n     * All the permissions available on the system. You should use self::permissions()\n     * to retrieve them, and not directly access this array as it is subject to change.\n     *\n     * @see \\Pterodactyl\\Models\\Permission::permissions()\n     */\n    protected static array $permissions = [\n        'websocket' => [\n            'description' => '允许用户连接到服务器 websocket，让他们可以访问查看控制台输出和实时服务器统计信息。',\n            'keys' => [\n                'connect' => '允许用户连接到服务器的 websocket 实例以流式传输控制台。',\n            ],\n        ],\n\n        'control' => [\n            'description' => '控制用户控制服务器电源状态或发送命令的能力的权限。',\n            'keys' => [\n                'console' => '允许用户通过控制台向服务器发送命令。',\n                'start' => '允许用户在服务器停止时启动它。',\n                'stop' => '允许用户停止正在运行的服务器。',\n                'restart' => '允许用户执行服务器重启。这允许他们在脱机时启动服务器，但不会将服务器置于完全停止状态。',\n            ],\n        ],\n\n        'user' => [\n            'description' => '允许用户管理服务器上其他子用户的权限。他们将永远无法编辑自己的帐户，或分配他们自己没有的权限。',\n            'keys' => [\n                'create' => '允许用户为服务器创建新的子用户。',\n                'read' => '允许用户查看子用户及其对服务器的权限。',\n                'update' => '允许用户修改其他子用户。',\n                'delete' => '允许用户从服务器中删除子用户。',\n            ],\n        ],\n\n        'file' => [\n            'description' => '控制用户修改此服务器文件系统能力的权限。',\n            'keys' => [\n                'create' => '允许用户通过面板或直接上传创建其他文件和文件夹。',\n                'read' => '允许用户查看目录的内容，但不能查看或下载文件的内容。',\n                'read-content' => '允许用户查看给定文件的内容。这也将允许用户下载文件。',\n                'update' => '允许用户更新现有文件或目录的内容。',\n                'delete' => '允许用户删除文件或目录。',\n                'archive' => '允许用户压缩系统上的的文件以及解压系统上的现有压缩文件。',\n                'sftp' => '允许用户使用其他分配的文件权限连接到 SFTP 并管理服务器文件。',\n            ],\n        ],\n\n        'backup' => [\n            'description' => '控制用户创建和管理服务器备份的能力的权限。',\n            'keys' => [\n                'create' => '允许用户为此服务器创建新备份。',\n                'read' => '允许用户查看此服务器存在的所有备份。',\n                'delete' => '允许用户从系统中删除备份。',\n                'download' => '允许用户下载服务器的备份。这是个危险权限：这允许用户访问备份中服务器的所有文件。',\n                'restore' => '允许用户恢复服务器的备份。这是个危险权限：这允许用户删除服务器中的所有服务器文件。',\n            ],\n        ],\n\n        // Controls permissions for editing or viewing a server's allocations.\n        'allocation' => [\n            'description' => '控制用户修改此服务器端口分配能力的权限。',\n            'keys' => [\n                'read' => '允许用户查看当前分配给该服务器的所有分配。对该服务器具有任何访问级别的用户始终可以查看主要分配。',\n                'create' => '允许用户向服务器创建额外的分配。',\n                'update' => '允许用户更改主服务器分配并将注释附加到每个分配。',\n                'delete' => '允许用户从服务器中删除分配。',\n            ],\n        ],\n\n        // Controls permissions for editing or viewing a server's startup parameters.\n        'startup' => [\n            'description' => '控制用户查看此服务器启动参数的能力的权限。',\n            'keys' => [\n                'read' => '允许用户查看服务器的启动变量。',\n                'update' => '允许用户修改服务器的启动变量。',\n                'docker-image' => '允许用户修改运行服务器时使用的 Docker 镜像。',\n                'egg-change' => '允许用户切换服务器当前使用的预设（预设组/预设）。',\n            ],\n        ],\n\n        'database' => [\n            'description' => '控制用户访问此服务器的数据库管理的权限。',\n            'keys' => [\n                'create' => '允许用户为此服务器创建新数据库。',\n                'read' => '允许用户查看与此服务器关联的数据库。',\n                'update' => '允许用户重置数据库实例的密码。如果用户没有 view_password 权限，他们将看不到更新的密码。',\n                'delete' => '允许用户从此服务器中删除数据库实例。',\n                'view_password' => '允许用户查看与此服务器的数据库实例关联的密码。',\n            ],\n        ],\n\n        'schedule' => [\n            'description' => '控制用户访问此服务器计划系统的权限。',\n            'keys' => [\n                'create' => '允许用户为此服务器创建新计划。', // task.create-schedule\n                'read' => '允许用户查看此服务器的计划和与其关联的任务。', // task.view-schedule, task.list-schedules\n                'update' => '允许用户更新此服务器的计划和计划中的任务。', // task.edit-schedule, task.queue-schedule, task.toggle-schedule\n                'delete' => '允许用户删除此服务器的计划。', // task.delete-schedule\n            ],\n        ],\n\n        'settings' => [\n            'description' => '控制用户访问此服务器设置的权限。',\n            'keys' => [\n                'rename' => '允许用户重命名此服务器并更改其描述。',\n                'reinstall' => '允许用户触发重新安装此服务器。',\n            ],\n        ],\n\n        'activity' => [\n            'description' => '控制用户对服务器活动日志的访问的权限。',\n            'keys' => [\n                'read' => '允许用户查看服务器的活动日志。',\n            ],\n        ],\n    ];\n\n    /**\n     * Returns all the permissions available on the system for a user to\n     * have when controlling a server.\n     */\n    public static function permissions(): Collection\n    {\n        return Collection::make(self::$permissions);\n    }\n}\n"
  },
  {
    "path": "app/Models/RecoveryToken.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\n\n/**\n * @property int $id\n * @property int $user_id\n * @property string $token\n * @property \\Carbon\\CarbonImmutable $created_at\n * @property User $user\n */\nclass RecoveryToken extends Model\n{\n    /**\n     * There are no updates to this model, only inserts and deletes.\n     */\n    public const UPDATED_AT = null;\n\n    public $timestamps = true;\n\n    protected bool $immutableDates = true;\n\n    public static array $validationRules = [\n        'token' => 'required|string',\n    ];\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\User, $this>\n     */\n    public function user(): BelongsTo\n    {\n        return $this->belongsTo(User::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/Schedule.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Cron\\CronExpression;\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\nuse Pterodactyl\\Contracts\\Extensions\\HashidsInterface;\n\n/**\n * @property int $id\n * @property int $server_id\n * @property string $name\n * @property string $cron_day_of_week\n * @property string $cron_month\n * @property string $cron_day_of_month\n * @property string $cron_hour\n * @property string $cron_minute\n * @property bool $is_active\n * @property bool $is_processing\n * @property bool $only_when_online\n * @property \\Carbon\\Carbon|null $last_run_at\n * @property \\Carbon\\Carbon|null $next_run_at\n * @property \\Carbon\\Carbon $created_at\n * @property \\Carbon\\Carbon $updated_at\n * @property string $hashid\n * @property Server $server\n * @property \\Illuminate\\Database\\Eloquent\\Collection<int, \\Pterodactyl\\Models\\Task> $tasks\n */\nclass Schedule extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\ScheduleFactory> */\n    use HasFactory;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'server_schedule';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'schedules';\n\n    /**\n     * Always return the tasks associated with this schedule.\n     */\n    protected $with = ['tasks'];\n\n    /**\n     * Mass assignable attributes on this model.\n     */\n    protected $fillable = [\n        'server_id',\n        'name',\n        'cron_day_of_week',\n        'cron_month',\n        'cron_day_of_month',\n        'cron_hour',\n        'cron_minute',\n        'is_active',\n        'is_processing',\n        'only_when_online',\n        'last_run_at',\n        'next_run_at',\n    ];\n\n    protected $casts = [\n        'id' => 'integer',\n        'server_id' => 'integer',\n        'is_active' => 'boolean',\n        'is_processing' => 'boolean',\n        'only_when_online' => 'boolean',\n        'last_run_at' => 'datetime',\n        'next_run_at' => 'datetime',\n    ];\n\n    protected $attributes = [\n        'name' => null,\n        'cron_day_of_week' => '*',\n        'cron_month' => '*',\n        'cron_day_of_month' => '*',\n        'cron_hour' => '*',\n        'cron_minute' => '*',\n        'is_active' => true,\n        'is_processing' => false,\n        'only_when_online' => false,\n    ];\n\n    public static array $validationRules = [\n        'server_id' => 'required|exists:servers,id',\n        'name' => 'required|string|max:191',\n        'cron_day_of_week' => 'required|string',\n        'cron_month' => 'required|string',\n        'cron_day_of_month' => 'required|string',\n        'cron_hour' => 'required|string',\n        'cron_minute' => 'required|string',\n        'is_active' => 'boolean',\n        'is_processing' => 'boolean',\n        'only_when_online' => 'boolean',\n        'last_run_at' => 'nullable|date',\n        'next_run_at' => 'nullable|date',\n    ];\n\n    public function getRouteKeyName(): string\n    {\n        return $this->getKeyName();\n    }\n\n    /**\n     * Returns the schedule's execution crontab entry as a string.\n     *\n     * @throws \\Exception\n     */\n    public function getNextRunDate(): CarbonImmutable\n    {\n        $formatted = sprintf('%s %s %s %s %s', $this->cron_minute, $this->cron_hour, $this->cron_day_of_month, $this->cron_month, $this->cron_day_of_week);\n\n        return CarbonImmutable::instance((new CronExpression($formatted))->getNextRunDate());\n    }\n\n    /**\n     * Return a hashid encoded string to represent the ID of the schedule.\n     */\n    public function getHashidAttribute(): string\n    {\n        return Container::getInstance()->make(HashidsInterface::class)->encode($this->id);\n    }\n\n    /**\n     * Return tasks belonging to a schedule.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Task, $this>\n     */\n    public function tasks(): HasMany\n    {\n        return $this->hasMany(Task::class);\n    }\n\n    /**\n     * Return the server model that a schedule belongs to.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function server(): BelongsTo\n    {\n        return $this->belongsTo(Server::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/Server.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Notifications\\Notifiable;\nuse Illuminate\\Database\\Query\\JoinClause;\nuse Znck\\Eloquent\\Traits\\BelongsToThrough;\nuse Pterodactyl\\Contracts\\Models\\Identifiable;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasOne;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Pterodactyl\\Models\\Traits\\HasRealtimeIdentifier;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\nuse Illuminate\\Database\\Eloquent\\Relations\\MorphToMany;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasManyThrough;\nuse Pterodactyl\\Exceptions\\Http\\Server\\ServerStateConflictException;\n\n/**\n * \\Pterodactyl\\Models\\Server.\n *\n * @property int $id\n * @property string|null $external_id\n * @property string $uuid\n * @property string $uuidShort\n * @property int $node_id\n * @property string $name\n * @property string $description\n * @property string|null $status\n * @property bool $skip_scripts\n * @property int $owner_id\n * @property int $memory\n * @property int $swap\n * @property int $disk\n * @property int $io\n * @property int $cpu\n * @property string|null $threads\n * @property bool $oom_disabled\n * @property int $allocation_id\n * @property int $nest_id\n * @property int $egg_id\n * @property string $startup\n * @property string $image\n * @property int|null $allocation_limit\n * @property int|null $database_limit\n * @property int $backup_limit\n * @property \\Illuminate\\Support\\Carbon|null $created_at\n * @property \\Illuminate\\Support\\Carbon|null $updated_at\n * @property \\Illuminate\\Support\\Carbon|null $installed_at\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\ActivityLog[] $activity\n * @property int|null $activity_count\n * @property Allocation|null $allocation\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\Allocation[] $allocations\n * @property int|null $allocations_count\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\Backup[] $backups\n * @property int|null $backups_count\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\Database[] $databases\n * @property int|null $databases_count\n * @property Egg|null $egg\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\Mount[] $mounts\n * @property int|null $mounts_count\n * @property Nest $nest\n * @property Node $node\n * @property \\Illuminate\\Notifications\\DatabaseNotificationCollection|\\Illuminate\\Notifications\\DatabaseNotification[] $notifications\n * @property int|null $notifications_count\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\Schedule[] $schedules\n * @property int|null $schedules_count\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\Subuser[] $subusers\n * @property int|null $subusers_count\n * @property ServerTransfer|null $transfer\n * @property User $user\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\EggVariable[] $variables\n * @property int|null $variables_count\n *\n * @method static \\Database\\Factories\\ServerFactory factory(...$parameters)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server newModelQuery()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server newQuery()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server query()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereAllocationId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereAllocationLimit($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereBackupLimit($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereCpu($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereCreatedAt($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereDatabaseLimit($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereDescription($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereDisk($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereEggId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereExternalId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereImage($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereIo($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereMemory($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereName($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereNestId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereNodeId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereOomDisabled($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereOwnerId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereSkipScripts($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereStartup($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereStatus($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereSwap($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereThreads($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereUpdatedAt($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereUuid($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|Server whereUuidShort($value)\n *\n * @mixin \\Eloquent\n */\n#[Attributes\\Identifiable('serv')]\nclass Server extends Model implements Identifiable\n{\n    /** @use HasFactory<\\Database\\Factories\\ServerFactory> */\n    use HasFactory;\n    use BelongsToThrough;\n    use Notifiable;\n    use HasRealtimeIdentifier;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'server';\n    public const STATUS_INSTALLING = 'installing';\n    public const STATUS_INSTALL_FAILED = 'install_failed';\n    public const STATUS_REINSTALL_FAILED = 'reinstall_failed';\n    public const STATUS_SUSPENDED = 'suspended';\n    public const STATUS_RESTORING_BACKUP = 'restoring_backup';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'servers';\n\n    /**\n     * Default values when creating the model. We want to switch to disabling OOM killer\n     * on server instances unless the user specifies otherwise in the request.\n     */\n    protected $attributes = [\n        'status' => self::STATUS_INSTALLING,\n        'oom_disabled' => true,\n        'installed_at' => null,\n    ];\n\n    /**\n     * The default relationships to load for all server models.\n     */\n    protected $with = ['allocation'];\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $guarded = ['id', self::CREATED_AT, self::UPDATED_AT, 'deleted_at', 'installed_at'];\n\n    public static array $validationRules = [\n        'external_id' => 'sometimes|nullable|string|between:1,191|unique:servers',\n        'owner_id' => 'required|integer|exists:users,id',\n        'name' => 'required|string|min:1|max:191',\n        'node_id' => 'required|exists:nodes,id',\n        'description' => 'string',\n        'status' => 'nullable|string',\n        'memory' => 'required|numeric|min:0',\n        'swap' => 'required|numeric|min:-1',\n        'io' => 'required|numeric|between:10,1000',\n        'cpu' => 'required|numeric|min:0',\n        'threads' => 'nullable|regex:/^[0-9-,]+$/',\n        'oom_disabled' => 'sometimes|boolean',\n        'disk' => 'required|numeric|min:0',\n        'allocation_id' => 'required|bail|unique:servers|exists:allocations,id',\n        'nest_id' => 'required|exists:nests,id',\n        'egg_id' => 'required|exists:eggs,id',\n        'startup' => 'required|string',\n        'skip_scripts' => 'sometimes|boolean',\n        'image' => ['required', 'string', 'max:191'],\n        'database_limit' => 'present|nullable|integer|min:0',\n        'allocation_limit' => 'sometimes|nullable|integer|min:0',\n        'backup_limit' => 'present|nullable|integer|min:0',\n    ];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'node_id' => 'integer',\n        'skip_scripts' => 'boolean',\n        'owner_id' => 'integer',\n        'memory' => 'integer',\n        'swap' => 'integer',\n        'disk' => 'integer',\n        'io' => 'integer',\n        'cpu' => 'integer',\n        'oom_disabled' => 'boolean',\n        'allocation_id' => 'integer',\n        'nest_id' => 'integer',\n        'egg_id' => 'integer',\n        'database_limit' => 'integer',\n        'allocation_limit' => 'integer',\n        'backup_limit' => 'integer',\n        self::CREATED_AT => 'datetime',\n        self::UPDATED_AT => 'datetime',\n        'deleted_at' => 'datetime',\n        'installed_at' => 'datetime',\n    ];\n\n    /**\n     * Returns the format for server allocations when communicating with the Daemon.\n     */\n    public function getAllocationMappings(): array\n    {\n        return $this->allocations->where('node_id', $this->node_id)->groupBy('ip')->map(function ($item) {\n            return $item->pluck('port');\n        })->toArray();\n    }\n\n    public function isInstalled(): bool\n    {\n        return $this->status !== self::STATUS_INSTALLING && $this->status !== self::STATUS_INSTALL_FAILED;\n    }\n\n    public function isSuspended(): bool\n    {\n        return $this->status === self::STATUS_SUSPENDED;\n    }\n\n    /**\n     * Gets the user who owns the server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\User, $this>\n     */\n    public function user(): BelongsTo\n    {\n        return $this->belongsTo(User::class, 'owner_id');\n    }\n\n    /**\n     * Gets the subusers associated with a server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Subuser, $this>\n     */\n    public function subusers(): HasMany\n    {\n        return $this->hasMany(Subuser::class, 'server_id', 'id');\n    }\n\n    /**\n     * Gets the default allocation for a server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasOne<\\Pterodactyl\\Models\\Allocation, $this>\n     */\n    public function allocation(): HasOne\n    {\n        return $this->hasOne(Allocation::class, 'id', 'allocation_id');\n    }\n\n    /**\n     * Gets all allocations associated with this server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Allocation, $this>\n     */\n    public function allocations(): HasMany\n    {\n        return $this->hasMany(Allocation::class, 'server_id');\n    }\n\n    /**\n     * Gets information for the nest associated with this server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Nest, $this>\n     */\n    public function nest(): BelongsTo\n    {\n        return $this->belongsTo(Nest::class);\n    }\n\n    /**\n     * Gets information for the egg associated with this server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasOne<\\Pterodactyl\\Models\\Egg, $this>\n     */\n    public function egg(): HasOne\n    {\n        return $this->hasOne(Egg::class, 'id', 'egg_id');\n    }\n\n    /**\n     * Gets information for the service variables associated with this server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\EggVariable, $this>\n     */\n    public function variables(): HasMany\n    {\n        return $this->hasMany(EggVariable::class, 'egg_id', 'egg_id')\n            ->select(['egg_variables.*', 'server_variables.variable_value as server_value'])\n            ->leftJoin('server_variables', function (JoinClause $join) {\n                // Don't forget to join against the server ID as well since the way we're using this relationship\n                // would actually return all the variables and their values for _all_ servers using that egg,\n                // rather than only the server for this model.\n                //\n                // @see https://github.com/pterodactyl/panel/issues/2250\n                $join->on('server_variables.variable_id', 'egg_variables.id')\n                    ->where('server_variables.server_id', $this->id);\n            });\n    }\n\n    /**\n     * Gets information for the node associated with this server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Node, $this>\n     */\n    public function node(): BelongsTo\n    {\n        return $this->belongsTo(Node::class);\n    }\n\n    /**\n     * Gets information for the tasks associated with this server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Schedule, $this>\n     */\n    public function schedules(): HasMany\n    {\n        return $this->hasMany(Schedule::class);\n    }\n\n    /**\n     * Gets all databases associated with a server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Database, $this>\n     */\n    public function databases(): HasMany\n    {\n        return $this->hasMany(Database::class);\n    }\n\n    /**\n     * Returns the location that a server belongs to.\n     *\n     * @return \\Znck\\Eloquent\\Relations\\BelongsToThrough<\\Pterodactyl\\Models\\Location, \\Pterodactyl\\Models\\Node>\n     *\n     * @throws \\Exception\n     */\n    public function location(): \\Znck\\Eloquent\\Relations\\BelongsToThrough\n    {\n        return $this->belongsToThrough(Location::class, Node::class); // @phpstan-ignore return.type\n    }\n\n    /**\n     * Returns the associated server transfer.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasOne<\\Pterodactyl\\Models\\ServerTransfer, $this>\n     */\n    public function transfer(): HasOne\n    {\n        return $this->hasOne(ServerTransfer::class)->whereNull('successful')->orderByDesc('id');\n    }\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Backup, $this>\n     */\n    public function backups(): HasMany\n    {\n        return $this->hasMany(Backup::class);\n    }\n\n    /**\n     * Returns all mounts that have this server has mounted.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasManyThrough<\\Pterodactyl\\Models\\Mount, \\Pterodactyl\\Models\\MountServer, $this>\n     */\n    public function mounts(): HasManyThrough\n    {\n        return $this->hasManyThrough(Mount::class, MountServer::class, 'server_id', 'id', 'id', 'mount_id');\n    }\n\n    /**\n     * Returns all of the activity log entries where the server is the subject.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\MorphToMany<\\Pterodactyl\\Models\\ActivityLog, $this>\n     */\n    public function activity(): MorphToMany\n    {\n        return $this->morphToMany(ActivityLog::class, 'subject', 'activity_log_subjects');\n    }\n\n    /**\n     * Checks if the server is currently in a user-accessible state. If not, an\n     * exception is raised. This should be called whenever something needs to make\n     * sure the server is not in a weird state that should block user access.\n     *\n     * @throws ServerStateConflictException\n     */\n    public function validateCurrentState()\n    {\n        if (\n            $this->isSuspended()\n            || $this->node->isUnderMaintenance()\n            || !$this->isInstalled()\n            || $this->status === self::STATUS_RESTORING_BACKUP\n            || !is_null($this->transfer)\n        ) {\n            throw new ServerStateConflictException($this);\n        }\n    }\n\n    /**\n     * Checks if the server is currently in a transferable state. If not, an\n     * exception is raised. This should be called whenever something needs to make\n     * sure the server is able to be transferred and is not currently being transferred\n     * or installed.\n     */\n    public function validateTransferState()\n    {\n        if (\n            !$this->isInstalled()\n            || $this->status === self::STATUS_RESTORING_BACKUP\n            || !is_null($this->transfer)\n        ) {\n            throw new ServerStateConflictException($this);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Models/ServerTransfer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Relations\\HasOne;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\n\n/**\n * @property int $id\n * @property int $server_id\n * @property int $old_node\n * @property int $new_node\n * @property int $old_allocation\n * @property int $new_allocation\n * @property array|null $old_additional_allocations\n * @property array|null $new_additional_allocations\n * @property bool|null $successful\n * @property bool $archived\n * @property \\Carbon\\Carbon $created_at\n * @property \\Carbon\\Carbon $updated_at\n * @property Server $server\n * @property Node $oldNode\n * @property Node $newNode\n */\nclass ServerTransfer extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\ServerTransferFactory> */\n    use HasFactory;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'server_transfer';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'server_transfers';\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $guarded = ['id', 'created_at', 'updated_at'];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'server_id' => 'int',\n        'old_node' => 'int',\n        'new_node' => 'int',\n        'old_allocation' => 'int',\n        'new_allocation' => 'int',\n        'old_additional_allocations' => 'array',\n        'new_additional_allocations' => 'array',\n        'successful' => 'bool',\n        'archived' => 'bool',\n    ];\n\n    public static array $validationRules = [\n        'server_id' => 'required|numeric|exists:servers,id',\n        'old_node' => 'required|numeric',\n        'new_node' => 'required|numeric',\n        'old_allocation' => 'required|numeric',\n        'new_allocation' => 'required|numeric',\n        'old_additional_allocations' => 'nullable|array',\n        'old_additional_allocations.*' => 'numeric',\n        'new_additional_allocations' => 'nullable|array',\n        'new_additional_allocations.*' => 'numeric',\n        'successful' => 'sometimes|nullable|boolean',\n    ];\n\n    /**\n     * Gets the server associated with a server transfer.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function server(): BelongsTo\n    {\n        return $this->belongsTo(Server::class);\n    }\n\n    /**\n     * Gets the source node associated with a server transfer.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasOne<\\Pterodactyl\\Models\\Node, $this>\n     */\n    public function oldNode(): HasOne\n    {\n        return $this->hasOne(Node::class, 'id', 'old_node');\n    }\n\n    /**\n     * Gets the target node associated with a server transfer.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasOne<\\Pterodactyl\\Models\\Node, $this>\n     */\n    public function newNode(): HasOne\n    {\n        return $this->hasOne(Node::class, 'id', 'new_node');\n    }\n}\n"
  },
  {
    "path": "app/Models/ServerVariable.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\n\n/**\n * @property int $id\n * @property int $server_id\n * @property int $variable_id\n * @property string $variable_value\n * @property \\Carbon\\CarbonImmutable|null $created_at\n * @property \\Carbon\\CarbonImmutable|null $updated_at\n * @property EggVariable $variable\n * @property Server $server\n */\nclass ServerVariable extends Model\n{\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'server_variable';\n\n    protected bool $immutableDates = true;\n\n    protected $table = 'server_variables';\n\n    protected $guarded = ['id', 'created_at', 'updated_at'];\n\n    protected $casts = [\n        'server_id' => 'integer',\n        'variable_id' => 'integer',\n    ];\n\n    public static array $validationRules = [\n        'server_id' => 'required|int',\n        'variable_id' => 'required|int',\n        'variable_value' => 'string',\n    ];\n\n    /**\n     * Returns the server this variable is associated with.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function server(): BelongsTo\n    {\n        return $this->belongsTo(Server::class);\n    }\n\n    /**\n     * Returns information about a given variables parent.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\EggVariable, $this>\n     */\n    public function variable(): BelongsTo\n    {\n        return $this->belongsTo(EggVariable::class, 'variable_id');\n    }\n}\n"
  },
  {
    "path": "app/Models/Session.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Model;\n\nclass Session extends Model\n{\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'sessions';\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'id' => 'string',\n        'user_id' => 'integer',\n    ];\n}\n"
  },
  {
    "path": "app/Models/Setting.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\n/**\n * Pterodactyl\\Models\\Setting.\n *\n * @property int $id\n * @property string $key\n * @property string $value\n */\nclass Setting extends Model\n{\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'settings';\n\n    public $timestamps = false;\n\n    protected $fillable = ['key', 'value'];\n\n    public static array $validationRules = [\n        'key' => 'required|string|between:1,191',\n        'value' => 'string',\n    ];\n}\n"
  },
  {
    "path": "app/Models/Subuser.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Notifications\\Notifiable;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\n\n/**\n * @property int $id\n * @property int $user_id\n * @property int $server_id\n * @property array $permissions\n * @property \\Carbon\\Carbon $created_at\n * @property \\Carbon\\Carbon $updated_at\n * @property User $user\n * @property Server $server\n */\nclass Subuser extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\SubuserFactory> */\n    use HasFactory;\n    use Notifiable;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'server_subuser';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'subusers';\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $guarded = ['id', 'created_at', 'updated_at'];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'user_id' => 'int',\n        'server_id' => 'int',\n        'permissions' => 'array',\n    ];\n\n    public static array $validationRules = [\n        'user_id' => 'required|numeric|exists:users,id',\n        'server_id' => 'required|numeric|exists:servers,id',\n        'permissions' => 'nullable|array',\n        'permissions.*' => 'string',\n    ];\n\n    /**\n     * Return a hashid encoded string to represent the ID of the subuser.\n     */\n    public function getHashidAttribute(): string\n    {\n        return app()->make('hashids')->encode($this->id);\n    }\n\n    /**\n     * Gets the server associated with a subuser.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function server(): BelongsTo\n    {\n        return $this->belongsTo(Server::class);\n    }\n\n    /**\n     * Gets the user associated with a subuser.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\User, $this>\n     */\n    public function user(): BelongsTo\n    {\n        return $this->belongsTo(User::class);\n    }\n\n    /**\n     * Gets the permissions associated with a subuser.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Permission, $this>\n     */\n    public function permissions(): HasMany\n    {\n        return $this->hasMany(Permission::class);\n    }\n}\n"
  },
  {
    "path": "app/Models/Task.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Container\\Container;\nuse Znck\\Eloquent\\Traits\\BelongsToThrough;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\nuse Pterodactyl\\Contracts\\Extensions\\HashidsInterface;\n\n/**\n * @property int $id\n * @property int $schedule_id\n * @property int $sequence_id\n * @property string $action\n * @property string $payload\n * @property int $time_offset\n * @property bool $is_queued\n * @property bool $continue_on_failure\n * @property \\Carbon\\Carbon $created_at\n * @property \\Carbon\\Carbon $updated_at\n * @property string $hashid\n * @property Schedule $schedule\n * @property Server $server\n */\nclass Task extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\TaskFactory> */\n    use HasFactory;\n    use BelongsToThrough;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'schedule_task';\n\n    /**\n     * The default actions that can exist for a task in Pterodactyl.\n     */\n    public const ACTION_POWER = 'power';\n    public const ACTION_COMMAND = 'command';\n    public const ACTION_BACKUP = 'backup';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'tasks';\n\n    /**\n     * Relationships to be updated when this model is updated.\n     */\n    protected $touches = ['schedule'];\n\n    /**\n     * Fields that are mass assignable.\n     */\n    protected $fillable = [\n        'schedule_id',\n        'sequence_id',\n        'action',\n        'payload',\n        'time_offset',\n        'is_queued',\n        'continue_on_failure',\n    ];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'id' => 'integer',\n        'schedule_id' => 'integer',\n        'sequence_id' => 'integer',\n        'time_offset' => 'integer',\n        'is_queued' => 'boolean',\n        'continue_on_failure' => 'boolean',\n    ];\n\n    /**\n     * Default attributes when creating a new model.\n     */\n    protected $attributes = [\n        'time_offset' => 0,\n        'is_queued' => false,\n        'continue_on_failure' => false,\n    ];\n\n    public static array $validationRules = [\n        'schedule_id' => 'required|numeric|exists:schedules,id',\n        'sequence_id' => 'required|numeric|min:1',\n        'action' => 'required|string',\n        'payload' => 'required_unless:action,backup|string',\n        'time_offset' => 'required|numeric|between:0,900',\n        'is_queued' => 'boolean',\n        'continue_on_failure' => 'boolean',\n    ];\n\n    public function getRouteKeyName(): string\n    {\n        return $this->getKeyName();\n    }\n\n    /**\n     * Return a hashid encoded string to represent the ID of the task.\n     */\n    public function getHashidAttribute(): string\n    {\n        return Container::getInstance()->make(HashidsInterface::class)->encode($this->id);\n    }\n\n    /**\n     * Return the schedule that a task belongs to.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\Schedule, $this>\n     */\n    public function schedule(): BelongsTo\n    {\n        return $this->belongsTo(Schedule::class);\n    }\n\n    /**\n     * Return the server a task is assigned to, acts as a belongsToThrough.\n     *\n     * @return \\Znck\\Eloquent\\Relations\\BelongsToThrough<\\Pterodactyl\\Models\\Server, \\Pterodactyl\\Models\\Schedule>\n     */\n    public function server(): \\Znck\\Eloquent\\Relations\\BelongsToThrough\n    {\n        return $this->belongsToThrough(Server::class, Schedule::class); // @phpstan-ignore return.type\n    }\n}\n"
  },
  {
    "path": "app/Models/TaskLog.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\Model;\n\nclass TaskLog extends Model\n{\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'tasks_log';\n\n    /**\n     * Fields that are not mass assignable.\n     */\n    protected $guarded = ['id', 'created_at', 'updated_at'];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'id' => 'integer',\n        'task_id' => 'integer',\n        'run_status' => 'integer',\n        'run_time' => 'datetime',\n        'created_at' => 'datetime',\n        'updated_at' => 'datetime',\n    ];\n}\n"
  },
  {
    "path": "app/Models/Traits/HasAccessTokens.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models\\Traits;\n\nuse Illuminate\\Support\\Str;\nuse Laravel\\Sanctum\\Sanctum;\nuse Pterodactyl\\Models\\ApiKey;\nuse Laravel\\Sanctum\\HasApiTokens;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Pterodactyl\\Extensions\\Laravel\\Sanctum\\NewAccessToken;\n\n/**\n * @template TToken of \\Laravel\\Sanctum\\Contracts\\HasAbilities\n *\n * @mixin \\Pterodactyl\\Models\\Model\n */\ntrait HasAccessTokens\n{\n    /** @use \\Laravel\\Sanctum\\HasApiTokens<TToken> */\n    use HasApiTokens {\n        tokens as private _tokens;\n        createToken as private _createToken;\n    }\n\n    public function tokens(): HasMany\n    {\n        return $this->hasMany(Sanctum::$personalAccessTokenModel);\n    }\n\n    public function createToken(?string $memo, ?array $ips): NewAccessToken\n    {\n        /** @var ApiKey $token */\n        $token = $this->tokens()->forceCreate([\n            'user_id' => $this->id,\n            'key_type' => ApiKey::TYPE_ACCOUNT,\n            'identifier' => ApiKey::generateTokenIdentifier(ApiKey::TYPE_ACCOUNT),\n            'token' => encrypt($plain = Str::random(ApiKey::KEY_LENGTH)),\n            'memo' => $memo ?? '',\n            'allowed_ips' => $ips ?? [],\n        ]);\n\n        return new NewAccessToken($token, $plain);\n    }\n}\n"
  },
  {
    "path": "app/Models/Traits/HasRealtimeIdentifier.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models\\Traits;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Str;\nuse Webmozart\\Assert\\Assert;\nuse ParagonIE\\ConstantTime\\Base32;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Pterodactyl\\Models\\Attributes\\Identifiable;\nuse Illuminate\\Database\\Eloquent\\Casts\\Attribute;\n\n/**\n * Support realtime identifiers on models that do not track an \"identifier\" column in\n * the database. This allows us to make use of the existing data reliant on UUID columns\n * while still allowing for output and querying against a more human readable identifier\n * value.\n *\n * @property-read string $identifier\n *\n * @method static Builder whereIdentifier(string $identifier)\n *\n * @mixin \\Illuminate\\Database\\Eloquent\\Model\n */\ntrait HasRealtimeIdentifier\n{\n    private static string $identifierPrefix;\n\n    private static string $identifierDataColumn;\n\n    protected function identifier(): Attribute\n    {\n        return Attribute::get(function () {\n            $bytes = Uuid::fromString($this->getRawOriginal(static::$identifierDataColumn))->getBytes();\n\n            return sprintf('%s_%s', static::$identifierPrefix, Base32::encodeUnpadded($bytes));\n        });\n    }\n\n    public function scopeWhereIdentifier(Builder $builder, string $identifier): void\n    {\n        if (!str_starts_with($identifier, $prefix = self::$identifierPrefix . '_')) {\n            $builder->whereRaw('0 = 1');\n\n            return;\n        }\n\n        $bytes = rescue(fn () => Base32::decode(Str::replaceFirst($prefix, '', $identifier)), report: false);\n        if (empty($bytes)) {\n            $builder->whereRaw('0 = 1');\n\n            return;\n        }\n\n        $builder->where(self::$identifierDataColumn, Uuid::fromBytes($bytes)->toString());\n    }\n\n    protected static function bootHasRealtimeIdentifier(): void\n    {\n        $attrs = (new \\ReflectionClass(static::class))->getAttributes(Identifiable::class);\n\n        Assert::count(\n            $attrs,\n            1,\n            'The #[' . Identifiable::class . '] attribute must be set on ' . static::class . ' to use realtime identifiers.'\n        );\n\n        $instance = $attrs[0]->newInstance();\n\n        self::$identifierPrefix = $instance->prefix;\n        self::$identifierDataColumn = $instance->column;\n    }\n}\n"
  },
  {
    "path": "app/Models/User.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Pterodactyl\\Rules\\Username;\nuse Pterodactyl\\Facades\\Activity;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Validation\\Rules\\In;\nuse Illuminate\\Auth\\Authenticatable;\nuse Illuminate\\Notifications\\Notifiable;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Pterodactyl\\Contracts\\Models\\Identifiable;\nuse Pterodactyl\\Models\\Traits\\HasAccessTokens;\nuse Illuminate\\Auth\\Passwords\\CanResetPassword;\nuse Pterodactyl\\Traits\\Helpers\\AvailableLanguages;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\nuse Illuminate\\Foundation\\Auth\\Access\\Authorizable;\nuse Pterodactyl\\Models\\Traits\\HasRealtimeIdentifier;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\nuse Illuminate\\Database\\Eloquent\\Relations\\MorphToMany;\nuse Illuminate\\Contracts\\Auth\\Authenticatable as AuthenticatableContract;\nuse Illuminate\\Contracts\\Auth\\Access\\Authorizable as AuthorizableContract;\nuse Illuminate\\Contracts\\Auth\\CanResetPassword as CanResetPasswordContract;\nuse Pterodactyl\\Notifications\\SendPasswordReset as ResetPasswordNotification;\n\n/**\n * Pterodactyl\\Models\\User.\n *\n * @property int $id\n * @property string|null $external_id\n * @property string $uuid\n * @property string $username\n * @property string $email\n * @property string|null $name_first\n * @property string|null $name_last\n * @property string $password\n * @property string|null $remember_token\n * @property string $language\n * @property bool $root_admin\n * @property bool $use_totp\n * @property string|null $totp_secret\n * @property \\Illuminate\\Support\\Carbon|null $totp_authenticated_at\n * @property bool $gravatar\n * @property \\Illuminate\\Support\\Carbon|null $created_at\n * @property \\Illuminate\\Support\\Carbon|null $updated_at\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\ApiKey[] $apiKeys\n * @property int|null $api_keys_count\n * @property string $name\n * @property \\Illuminate\\Notifications\\DatabaseNotificationCollection|\\Illuminate\\Notifications\\DatabaseNotification[] $notifications\n * @property int|null $notifications_count\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\RecoveryToken[] $recoveryTokens\n * @property int|null $recovery_tokens_count\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\Server[] $servers\n * @property int|null $servers_count\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\UserSSHKey[] $sshKeys\n * @property int|null $ssh_keys_count\n * @property \\Illuminate\\Database\\Eloquent\\Collection|\\Pterodactyl\\Models\\ApiKey[] $tokens\n * @property int|null $tokens_count\n *\n * @method static \\Database\\Factories\\UserFactory factory(...$parameters)\n * @method static Builder|User newModelQuery()\n * @method static Builder|User newQuery()\n * @method static Builder|User query()\n * @method static Builder|User whereCreatedAt($value)\n * @method static Builder|User whereEmail($value)\n * @method static Builder|User whereExternalId($value)\n * @method static Builder|User whereGravatar($value)\n * @method static Builder|User whereId($value)\n * @method static Builder|User whereLanguage($value)\n * @method static Builder|User whereNameFirst($value)\n * @method static Builder|User whereNameLast($value)\n * @method static Builder|User wherePassword($value)\n * @method static Builder|User whereRememberToken($value)\n * @method static Builder|User whereRootAdmin($value)\n * @method static Builder|User whereTotpAuthenticatedAt($value)\n * @method static Builder|User whereTotpSecret($value)\n * @method static Builder|User whereUpdatedAt($value)\n * @method static Builder|User whereUseTotp($value)\n * @method static Builder|User whereUsername($value)\n * @method static Builder|User whereUuid($value)\n *\n * @mixin \\Eloquent\n */\n#[Attributes\\Identifiable('user')]\nclass User extends Model implements\n    AuthenticatableContract,\n    AuthorizableContract,\n    CanResetPasswordContract,\n    Identifiable\n{\n    use Authenticatable;\n    use Authorizable;\n    use AvailableLanguages;\n    use CanResetPassword;\n    /** @use \\Pterodactyl\\Models\\Traits\\HasAccessTokens<\\Pterodactyl\\Models\\ApiKey> */\n    use HasAccessTokens;\n    use Notifiable;\n    /** @use \\Illuminate\\Database\\Eloquent\\Factories\\HasFactory<\\Database\\Factories\\UserFactory> */\n    use HasFactory;\n    use HasRealtimeIdentifier;\n\n    public const USER_LEVEL_USER = 0;\n    public const USER_LEVEL_ADMIN = 1;\n\n    /**\n     * The resource name for this model when it is transformed into an\n     * API representation using fractal.\n     */\n    public const RESOURCE_NAME = 'user';\n\n    /**\n     * Level of servers to display when using access() on a user.\n     */\n    protected string $accessLevel = 'all';\n\n    /**\n     * The table associated with the model.\n     */\n    protected $table = 'users';\n\n    /**\n     * A list of mass-assignable variables.\n     */\n    protected $fillable = [\n        'external_id',\n        'username',\n        'email',\n        'name_first',\n        'name_last',\n        'password',\n        'language',\n        'use_totp',\n        'totp_secret',\n        'totp_authenticated_at',\n        'gravatar',\n        'root_admin',\n    ];\n\n    /**\n     * Cast values to correct type.\n     */\n    protected $casts = [\n        'root_admin' => 'boolean',\n        'use_totp' => 'boolean',\n        'gravatar' => 'boolean',\n        'totp_authenticated_at' => 'datetime',\n    ];\n\n    /**\n     * The attributes excluded from the model's JSON form.\n     */\n    protected $hidden = ['password', 'remember_token', 'totp_secret', 'totp_authenticated_at'];\n\n    /**\n     * Default values for specific fields in the database.\n     */\n    protected $attributes = [\n        'external_id' => null,\n        'root_admin' => false,\n        'language' => 'zh',\n        'use_totp' => false,\n        'totp_secret' => null,\n    ];\n\n    /**\n     * Rules verifying that the data being stored matches the expectations of the database.\n     */\n    public static array $validationRules = [\n        'uuid' => 'required|string|size:36|unique:users,uuid',\n        'email' => 'required|email|between:1,191|unique:users,email',\n        'external_id' => 'sometimes|nullable|string|max:191|unique:users,external_id',\n        'username' => 'required|between:1,191|unique:users,username',\n        'name_first' => 'required|string|between:1,191',\n        'name_last' => 'required|string|between:1,191',\n        'password' => 'sometimes|nullable|string',\n        'root_admin' => 'boolean',\n        'language' => 'string',\n        'use_totp' => 'boolean',\n        'totp_secret' => 'nullable|string',\n    ];\n\n    /**\n     * Implement language verification by overriding Eloquence's gather\n     * rules function.\n     */\n    public static function getRules(): array\n    {\n        $rules = parent::getRules();\n\n        $rules['language'][] = new In(array_keys((new self())->getAvailableLanguages()));\n        $rules['username'][] = new Username();\n\n        return $rules;\n    }\n\n    /**\n     * Return the user model in a format that can be passed over to Vue templates.\n     */\n    public function toVueObject(): array\n    {\n        return Collection::make($this->toArray())->except(['id', 'external_id'])\n            ->merge(['identifier' => $this->identifier])\n            ->toArray();\n    }\n\n    /**\n     * Send the password reset notification.\n     *\n     * @param string $token\n     */\n    public function sendPasswordResetNotification($token)\n    {\n        Activity::event('auth:reset-password')\n            ->withRequestMetadata()\n            ->subject($this)\n            ->log('sending password reset email');\n\n        $this->notify(new ResetPasswordNotification($token));\n    }\n\n    /**\n     * Store the username as a lowercase string.\n     */\n    public function setUsernameAttribute(string $value)\n    {\n        $this->attributes['username'] = mb_strtolower($value);\n    }\n\n    /**\n     * Return a concatenated result for the accounts full name.\n     */\n    public function getNameAttribute(): string\n    {\n        return trim($this->name_first . ' ' . $this->name_last);\n    }\n\n    /**\n     * Returns all servers that a user owns.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Server, $this>\n     */\n    public function servers(): HasMany\n    {\n        return $this->hasMany(Server::class, 'owner_id');\n    }\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\ApiKey, $this>\n     */\n    public function apiKeys(): HasMany\n    {\n        return $this->hasMany(ApiKey::class)\n            ->where('key_type', ApiKey::TYPE_ACCOUNT);\n    }\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\RecoveryToken, $this>\n     */\n    public function recoveryTokens(): HasMany\n    {\n        return $this->hasMany(RecoveryToken::class);\n    }\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\UserSSHKey, $this>\n     */\n    public function sshKeys(): HasMany\n    {\n        return $this->hasMany(UserSSHKey::class);\n    }\n\n    /**\n     * Returns all the activity logs where this user is the subject — not to\n     * be confused by activity logs where this user is the _actor_.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\MorphToMany<\\Pterodactyl\\Models\\ActivityLog, $this>\n     */\n    public function activity(): MorphToMany\n    {\n        return $this->morphToMany(ActivityLog::class, 'subject', 'activity_log_subjects');\n    }\n\n    /**\n     * Returns all the servers that a user can access by way of being the owner of the\n     * server, or because they are assigned as a subuser for that server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Builder<\\Pterodactyl\\Models\\Server>\n     */\n    public function accessibleServers(): Builder\n    {\n        return Server::query()\n            ->select('servers.*')\n            ->leftJoin('subusers', 'subusers.server_id', '=', 'servers.id')\n            ->where(function (Builder $builder) {\n                $builder->where('servers.owner_id', $this->id)->orWhere('subusers.user_id', $this->id);\n            })\n            ->groupBy('servers.id');\n    }\n}\n"
  },
  {
    "path": "app/Models/UserSSHKey.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Models;\n\nuse Illuminate\\Database\\Eloquent\\SoftDeletes;\nuse Illuminate\\Database\\Eloquent\\Relations\\BelongsTo;\nuse Illuminate\\Database\\Eloquent\\Factories\\HasFactory;\n\n/**\n * \\Pterodactyl\\Models\\UserSSHKey.\n *\n * @property int $id\n * @property int $user_id\n * @property string $name\n * @property string $fingerprint\n * @property string $public_key\n * @property \\Illuminate\\Support\\Carbon|null $created_at\n * @property \\Illuminate\\Support\\Carbon|null $updated_at\n * @property \\Illuminate\\Support\\Carbon|null $deleted_at\n * @property User $user\n *\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey newModelQuery()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey newQuery()\n * @method static \\Illuminate\\Database\\Query\\Builder|UserSSHKey onlyTrashed()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey query()\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey whereCreatedAt($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey whereDeletedAt($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey whereFingerprint($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey whereId($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey whereName($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey wherePublicKey($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey whereUpdatedAt($value)\n * @method static \\Illuminate\\Database\\Eloquent\\Builder|UserSSHKey whereUserId($value)\n * @method static \\Illuminate\\Database\\Query\\Builder|UserSSHKey withTrashed()\n * @method static \\Illuminate\\Database\\Query\\Builder|UserSSHKey withoutTrashed()\n * @method static \\Database\\Factories\\UserSSHKeyFactory factory(...$parameters)\n *\n * @mixin \\Eloquent\n */\nclass UserSSHKey extends Model\n{\n    /** @use HasFactory<\\Database\\Factories\\UserSSHKeyFactory> */\n    use HasFactory;\n    use SoftDeletes;\n\n    public const RESOURCE_NAME = 'ssh_key';\n\n    protected $table = 'user_ssh_keys';\n\n    protected $fillable = [\n        'name',\n        'public_key',\n        'fingerprint',\n    ];\n\n    public static array $validationRules = [\n        'name' => ['required', 'string'],\n        'fingerprint' => ['required', 'string'],\n        'public_key' => ['required', 'string'],\n    ];\n\n    /**\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\BelongsTo<\\Pterodactyl\\Models\\User, $this>\n     */\n    public function user(): BelongsTo\n    {\n        return $this->belongsTo(User::class);\n    }\n}\n"
  },
  {
    "path": "app/Notifications/AccountCreated.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Notifications;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Bus\\Queueable;\nuse Illuminate\\Notifications\\Notification;\nuse Illuminate\\Contracts\\Queue\\ShouldQueue;\nuse Illuminate\\Notifications\\Messages\\MailMessage;\n\nclass AccountCreated extends Notification implements ShouldQueue\n{\n    use Queueable;\n\n    /**\n     * Create a new notification instance.\n     */\n    public function __construct(public User $user, public ?string $token = null)\n    {\n    }\n\n    /**\n     * Get the notification's delivery channels.\n     */\n    public function via(): array\n    {\n        return ['mail'];\n    }\n\n    /**\n     * Get the mail representation of the notification.\n     */\n    public function toMail(): MailMessage\n    {\n        $message = (new MailMessage())\n            ->subject('已创建帐户')\n            ->greeting('你好 ' . $this->user->name . '!')\n            ->line('您收到这封电子邮件是因为已经为您创建了一个帐户于 ' . config('app.name') . '.')\n            ->line('账户名称: ' . $this->user->username)\n            ->line('账户电子邮箱: ' . $this->user->email);\n\n        if (!is_null($this->token)) {\n            return $message->action('点此设置您的帐户', url('/auth/password/reset/' . $this->token . '?email=' . urlencode($this->user->email)));\n        }\n\n        return $message;\n    }\n}\n"
  },
  {
    "path": "app/Notifications/AddedToServer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Notifications;\n\nuse Illuminate\\Bus\\Queueable;\nuse Illuminate\\Notifications\\Notification;\nuse Illuminate\\Contracts\\Queue\\ShouldQueue;\nuse Illuminate\\Notifications\\Messages\\MailMessage;\n\nclass AddedToServer extends Notification implements ShouldQueue\n{\n    use Queueable;\n\n    public object $server;\n\n    /**\n     * Create a new notification instance.\n     */\n    public function __construct(array $server)\n    {\n        $this->server = (object) $server;\n    }\n\n    /**\n     * Get the notification's delivery channels.\n     */\n    public function via(): array\n    {\n        return ['mail'];\n    }\n\n    /**\n     * Get the mail representation of the notification.\n     */\n    public function toMail(): MailMessage\n    {\n        return (new MailMessage())\n            ->subject('已被添加为子用户')\n            ->greeting('你好 ' . $this->server->user . '!')\n            ->line('您已被添加为以下服务器的子用户，允许您对服务器进行一定的控制。')\n            ->line('服务器名称: ' . $this->server->name)\n            ->action('点此浏览服务器', url('/server/' . $this->server->uuidShort));\n    }\n}\n"
  },
  {
    "path": "app/Notifications/MailTested.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Notifications;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Notifications\\Notification;\nuse Illuminate\\Notifications\\Messages\\MailMessage;\n\nclass MailTested extends Notification\n{\n    public function __construct(private User $user)\n    {\n    }\n\n    public function via(): array\n    {\n        return ['mail'];\n    }\n\n    public function toMail(): MailMessage\n    {\n        return (new MailMessage())\n            ->subject('翼龙面板邮件测试信息')\n            ->greeting('你好 ' . $this->user->name . '!')\n            ->line('这里是翼龙面板邮件系统，如果你收到这份邮件，说明邮件系统可以正常运行了!');\n    }\n}\n"
  },
  {
    "path": "app/Notifications/RemovedFromServer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Notifications;\n\nuse Illuminate\\Bus\\Queueable;\nuse Illuminate\\Notifications\\Notification;\nuse Illuminate\\Contracts\\Queue\\ShouldQueue;\nuse Illuminate\\Notifications\\Messages\\MailMessage;\n\nclass RemovedFromServer extends Notification implements ShouldQueue\n{\n    use Queueable;\n\n    public object $server;\n\n    /**\n     * Create a new notification instance.\n     */\n    public function __construct(array $server)\n    {\n        $this->server = (object) $server;\n    }\n\n    /**\n     * Get the notification's delivery channels.\n     */\n    public function via(): array\n    {\n        return ['mail'];\n    }\n\n    /**\n     * Get the mail representation of the notification.\n     */\n    public function toMail(): MailMessage\n    {\n        return (new MailMessage())\n            ->error()\n            ->subject('已被移除子用户')\n            ->greeting('你好 ' . $this->server->user . '.')\n            ->line('您已作为以下服务器的子用户被删除,并失去其控制权限。')\n            ->line('服务器名称: ' . $this->server->name)\n            ->action('点此浏览面板', route('index'));\n    }\n}\n"
  },
  {
    "path": "app/Notifications/SendPasswordReset.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Notifications;\n\nuse Illuminate\\Bus\\Queueable;\nuse Illuminate\\Notifications\\Notification;\nuse Illuminate\\Contracts\\Queue\\ShouldQueue;\nuse Illuminate\\Notifications\\Messages\\MailMessage;\n\nclass SendPasswordReset extends Notification implements ShouldQueue\n{\n    use Queueable;\n\n    /**\n     * Create a new notification instance.\n     */\n    public function __construct(public string $token)\n    {\n    }\n\n    /**\n     * Get the notification's delivery channels.\n     */\n    public function via(): array\n    {\n        return ['mail'];\n    }\n\n    /**\n     * Get the mail representation of the notification.\n     */\n    public function toMail(mixed $notifiable): MailMessage\n    {\n        return (new MailMessage())\n            ->subject('密码重置')\n            ->line('您收到这封电子邮件是因为我们收到了您帐户的密码重置请求。')\n            ->action('点此重置密码', url('/auth/password/reset/' . $this->token . '?email=' . urlencode($notifiable->email)))\n            ->line('如果您没有请求重置密码，则无需采取进一步措施。');\n    }\n}\n"
  },
  {
    "path": "app/Notifications/ServerInstalled.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Notifications;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Bus\\Queueable;\nuse Pterodactyl\\Events\\Event;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Container\\Container;\nuse Pterodactyl\\Events\\Server\\Installed;\nuse Illuminate\\Notifications\\Notification;\nuse Illuminate\\Contracts\\Queue\\ShouldQueue;\nuse Pterodactyl\\Contracts\\Core\\ReceivesEvents;\nuse Illuminate\\Contracts\\Notifications\\Dispatcher;\nuse Illuminate\\Notifications\\Messages\\MailMessage;\n\nclass ServerInstalled extends Notification implements ShouldQueue, ReceivesEvents\n{\n    use Queueable;\n\n    public Server $server;\n\n    public User $user;\n\n    /**\n     * Handle a direct call to this notification from the server installed event. This is configured\n     * in the event service provider.\n     *\n     * @phpstan-param Installed $event\n     */\n    public function handle(Event|Installed $event): void\n    {\n        $event->server->loadMissing('user');\n\n        $this->server = $event->server;\n        $this->user = $event->server->user;\n\n        // Since we are calling this notification directly from an event listener we need to fire off the dispatcher\n        // to send the email now. Don't use send() or you'll end up firing off two different events.\n        Container::getInstance()->make(Dispatcher::class)->sendNow($this->user, $this);\n    }\n\n    /**\n     * Get the notification's delivery channels.\n     */\n    public function via(): array\n    {\n        return ['mail'];\n    }\n\n    /**\n     * Get the mail representation of the notification.\n     */\n    public function toMail(): MailMessage\n    {\n        return (new MailMessage())\n            ->subject('服务器已安装')\n            ->greeting('你好 ' . $this->user->username . '.')\n            ->line('您的服务器已完成安装，现在可以使用了。')\n            ->line('服务器名称: ' . $this->server->name)\n            ->action('点此登入并开始使用', route('index'));\n    }\n}\n"
  },
  {
    "path": "app/Observers/EggVariableObserver.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Observers;\n\nuse Pterodactyl\\Models\\EggVariable;\n\nclass EggVariableObserver\n{\n    public function creating(EggVariable $variable): void\n    {\n        // @phpstan-ignore-next-line property.notFound\n        if ($variable->field_type) {\n            unset($variable->field_type);\n        }\n    }\n\n    public function updating(EggVariable $variable): void\n    {\n        // @phpstan-ignore-next-line property.notFound\n        if ($variable->field_type) {\n            unset($variable->field_type);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Observers/ServerObserver.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Observers;\n\nuse Pterodactyl\\Events;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Foundation\\Bus\\DispatchesJobs;\n\nclass ServerObserver\n{\n    use DispatchesJobs;\n\n    /**\n     * Listen to the Server creating event.\n     */\n    public function creating(Server $server): void\n    {\n        event(new Events\\Server\\Creating($server));\n    }\n\n    /**\n     * Listen to the Server created event.\n     */\n    public function created(Server $server): void\n    {\n        event(new Events\\Server\\Created($server));\n    }\n\n    /**\n     * Listen to the Server deleting event.\n     */\n    public function deleting(Server $server): void\n    {\n        event(new Events\\Server\\Deleting($server));\n    }\n\n    /**\n     * Listen to the Server deleted event.\n     */\n    public function deleted(Server $server): void\n    {\n        event(new Events\\Server\\Deleted($server));\n    }\n\n    /**\n     * Listen to the Server saving event.\n     */\n    public function saving(Server $server): void\n    {\n        event(new Events\\Server\\Saving($server));\n    }\n\n    /**\n     * Listen to the Server saved event.\n     */\n    public function saved(Server $server): void\n    {\n        event(new Events\\Server\\Saved($server));\n    }\n\n    /**\n     * Listen to the Server updating event.\n     */\n    public function updating(Server $server): void\n    {\n        event(new Events\\Server\\Updating($server));\n    }\n\n    /**\n     * Listen to the Server saved event.\n     */\n    public function updated(Server $server): void\n    {\n        event(new Events\\Server\\Updated($server));\n    }\n}\n"
  },
  {
    "path": "app/Observers/SubuserObserver.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Observers;\n\nuse Pterodactyl\\Events;\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Notifications\\AddedToServer;\nuse Pterodactyl\\Notifications\\RemovedFromServer;\n\nclass SubuserObserver\n{\n    /**\n     * Listen to the Subuser creating event.\n     */\n    public function creating(Subuser $subuser): void\n    {\n        event(new Events\\Subuser\\Creating($subuser));\n    }\n\n    /**\n     * Listen to the Subuser created event.\n     */\n    public function created(Subuser $subuser): void\n    {\n        event(new Events\\Subuser\\Created($subuser));\n\n        $subuser->user->notify(new AddedToServer([\n            'user' => $subuser->user->name_first,\n            'name' => $subuser->server->name,\n            'uuidShort' => $subuser->server->uuidShort,\n        ]));\n    }\n\n    /**\n     * Listen to the Subuser deleting event.\n     */\n    public function deleting(Subuser $subuser): void\n    {\n        event(new Events\\Subuser\\Deleting($subuser));\n    }\n\n    /**\n     * Listen to the Subuser deleted event.\n     */\n    public function deleted(Subuser $subuser): void\n    {\n        event(new Events\\Subuser\\Deleted($subuser));\n\n        $subuser->user->notify(new RemovedFromServer([\n            'user' => $subuser->user->name_first,\n            'name' => $subuser->server->name,\n        ]));\n    }\n}\n"
  },
  {
    "path": "app/Observers/UserObserver.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Observers;\n\nuse Pterodactyl\\Events;\nuse Pterodactyl\\Models\\User;\n\nclass UserObserver\n{\n    protected string $uuid;\n\n    /**\n     * Listen to the User creating event.\n     */\n    public function creating(User $user): void\n    {\n        event(new Events\\User\\Creating($user));\n    }\n\n    /**\n     * Listen to the User created event.\n     */\n    public function created(User $user): void\n    {\n        event(new Events\\User\\Created($user));\n    }\n\n    /**\n     * Listen to the User deleting event.\n     */\n    public function deleting(User $user): void\n    {\n        event(new Events\\User\\Deleting($user));\n    }\n\n    /**\n     * Listen to the User deleted event.\n     */\n    public function deleted(User $user): void\n    {\n        event(new Events\\User\\Deleted($user));\n    }\n}\n"
  },
  {
    "path": "app/Policies/.gitkeep",
    "content": ""
  },
  {
    "path": "app/Policies/ServerPolicy.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Policies;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\n\nclass ServerPolicy\n{\n    /**\n     * Checks if the user has the given permission on/for the server.\n     */\n    protected function checkPermission(User $user, Server $server, string $permission): bool\n    {\n        $subuser = $server->subusers->where('user_id', $user->id)->first();\n        if (!$subuser || empty($permission)) {\n            return false;\n        }\n\n        return in_array($permission, $subuser->permissions);\n    }\n\n    /**\n     * Runs before any of the functions are called. Used to determine if user is root admin, if so, ignore permissions.\n     */\n    public function before(User $user, string $ability, Server $server): bool\n    {\n        if ($user->root_admin || $server->owner_id === $user->id) {\n            return true;\n        }\n\n        return $this->checkPermission($user, $server, $ability);\n    }\n\n    /**\n     * This is a horrendous hack to avoid Laravel's \"smart\" behavior that does\n     * not call the before() function if there isn't a function matching the\n     * policy permission.\n     */\n    public function __call(string $name, mixed $arguments)\n    {\n        // do nothing\n    }\n}\n"
  },
  {
    "path": "app/Providers/ActivityLogServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Illuminate\\Support\\ServiceProvider;\nuse Pterodactyl\\Services\\Activity\\ActivityLogBatchService;\nuse Pterodactyl\\Services\\Activity\\ActivityLogTargetableService;\n\nclass ActivityLogServiceProvider extends ServiceProvider\n{\n    /**\n     * Registers the necessary activity logger singletons scoped to the individual\n     * request instances.\n     */\n    public function register()\n    {\n        $this->app->scoped(ActivityLogBatchService::class);\n        $this->app->scoped(ActivityLogTargetableService::class);\n    }\n}\n"
  },
  {
    "path": "app/Providers/AppServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Pterodactyl\\Models;\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Support\\Facades\\URL;\nuse Illuminate\\Pagination\\Paginator;\nuse Illuminate\\Support\\Facades\\View;\nuse Illuminate\\Support\\Facades\\Cache;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Support\\ServiceProvider;\nuse Pterodactyl\\Extensions\\Themes\\Theme;\nuse Illuminate\\Database\\Eloquent\\Relations\\Relation;\n\nclass AppServiceProvider extends ServiceProvider\n{\n    /**\n     * Bootstrap any application services.\n     */\n    public function boot(): void\n    {\n        Schema::defaultStringLength(191);\n\n        View::share('appVersion', $this->versionData()['version'] ?? 'undefined');\n        View::share('appIsGit', $this->versionData()['is_git'] ?? false);\n\n        Paginator::useBootstrap();\n\n        // If the APP_URL value is set with https:// make sure we force it here. Theoretically\n        // this should just work with the proxy logic, but there are a lot of cases where it\n        // doesn't, and it triggers a lot of support requests, so lets just head it off here.\n        //\n        // @see https://github.com/pterodactyl/panel/issues/3623\n        if (Str::startsWith(config('app.url') ?? '', 'https://')) {\n            URL::forceScheme('https');\n        }\n\n        Relation::enforceMorphMap([\n            'allocation' => Models\\Allocation::class,\n            'api_key' => Models\\ApiKey::class,\n            'backup' => Models\\Backup::class,\n            'database' => Models\\Database::class,\n            'egg' => Models\\Egg::class,\n            'egg_variable' => Models\\EggVariable::class,\n            'schedule' => Models\\Schedule::class,\n            'server' => Models\\Server::class,\n            'ssh_key' => Models\\UserSSHKey::class,\n            'task' => Models\\Task::class,\n            'user' => Models\\User::class,\n        ]);\n    }\n\n    /**\n     * Register application service providers.\n     */\n    public function register(): void\n    {\n        // Only load the settings service provider if the environment\n        // is configured to allow it.\n        if (!config('pterodactyl.load_environment_only', false) && $this->app->environment() !== 'testing') {\n            $this->app->register(SettingsServiceProvider::class);\n        }\n\n        $this->app->singleton('extensions.themes', function () {\n            return new Theme();\n        });\n    }\n\n    /**\n     * Return version information for the footer.\n     */\n    protected function versionData(): array\n    {\n        return Cache::remember('git-version', 5, function () {\n            if (file_exists(base_path('.git/HEAD'))) {\n                $head = explode(' ', file_get_contents(base_path('.git/HEAD')));\n\n                if (array_key_exists(1, $head)) {\n                    $path = base_path('.git/' . trim($head[1]));\n                }\n            }\n\n            if (isset($path) && file_exists($path)) {\n                return [\n                    'version' => substr(file_get_contents($path), 0, 8),\n                    'is_git' => true,\n                ];\n            }\n\n            return [\n                'version' => config('app.version'),\n                'is_git' => false,\n            ];\n        });\n    }\n}\n"
  },
  {
    "path": "app/Providers/AuthServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Laravel\\Sanctum\\Sanctum;\nuse Pterodactyl\\Models\\ApiKey;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Policies\\ServerPolicy;\nuse Illuminate\\Foundation\\Support\\Providers\\AuthServiceProvider as ServiceProvider;\n\nclass AuthServiceProvider extends ServiceProvider\n{\n    /**\n     * The model to policy mappings for the application.\n     */\n    protected $policies = [\n        Server::class => ServerPolicy::class,\n    ];\n\n    public function boot(): void\n    {\n        Sanctum::usePersonalAccessTokenModel(ApiKey::class);\n    }\n}\n"
  },
  {
    "path": "app/Providers/BackupsServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Illuminate\\Support\\ServiceProvider;\nuse Pterodactyl\\Extensions\\Backups\\BackupManager;\nuse Illuminate\\Contracts\\Support\\DeferrableProvider;\n\nclass BackupsServiceProvider extends ServiceProvider implements DeferrableProvider\n{\n    /**\n     * Register the S3 backup disk.\n     */\n    public function register(): void\n    {\n        $this->app->singleton(BackupManager::class, function ($app) {\n            return new BackupManager($app);\n        });\n    }\n\n    public function provides(): array\n    {\n        return [BackupManager::class];\n    }\n}\n"
  },
  {
    "path": "app/Providers/BladeServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Illuminate\\Support\\ServiceProvider;\n\nclass BladeServiceProvider extends ServiceProvider\n{\n    /**\n     * Perform post-registration booting of services.\n     */\n    public function boot(): void\n    {\n        $this->app->make('blade.compiler')\n            ->directive('datetimeHuman', function ($expression) {\n                return \"<?php echo \\Carbon\\CarbonImmutable::createFromFormat(\\Carbon\\CarbonImmutable::DEFAULT_TO_STRING_FORMAT, $expression)->setTimezone(config('app.timezone'))->toDateTimeString(); ?>\";\n            });\n    }\n}\n"
  },
  {
    "path": "app/Providers/BroadcastServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Illuminate\\Support\\ServiceProvider;\nuse Illuminate\\Support\\Facades\\Broadcast;\n\nclass BroadcastServiceProvider extends ServiceProvider\n{\n    /**\n     * Bootstrap any application services.\n     */\n    public function boot(): void\n    {\n        Broadcast::routes();\n\n        /*\n         * Authenticate the user's personal channel...\n         */\n        Broadcast::channel('App.User.*', function ($user, $userId) {\n            return (int) $user->id === (int) $userId;\n        });\n    }\n}\n"
  },
  {
    "path": "app/Providers/EventServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\EggVariable;\nuse Pterodactyl\\Observers\\UserObserver;\nuse Pterodactyl\\Observers\\ServerObserver;\nuse Pterodactyl\\Observers\\SubuserObserver;\nuse Pterodactyl\\Listeners\\TwoFactorListener;\nuse Pterodactyl\\Listeners\\RevocationListener;\nuse Pterodactyl\\Observers\\EggVariableObserver;\nuse Pterodactyl\\Listeners\\AuthenticationListener;\nuse Pterodactyl\\Events\\Server\\Installed as ServerInstalledEvent;\nuse Pterodactyl\\Notifications\\ServerInstalled as ServerInstalledNotification;\nuse Illuminate\\Foundation\\Support\\Providers\\EventServiceProvider as ServiceProvider;\n\nclass EventServiceProvider extends ServiceProvider\n{\n    /**\n     * The event to listener mappings for the application.\n     */\n    protected $listen = [\n        ServerInstalledEvent::class => [ServerInstalledNotification::class],\n    ];\n\n    protected $subscribe = [\n        AuthenticationListener::class,\n        RevocationListener::class,\n        TwoFactorListener::class,\n    ];\n\n    protected static $shouldDiscoverEvents = false;\n\n    /**\n     * Register any events for your application.\n     */\n    public function boot(): void\n    {\n        parent::boot();\n\n        User::observe(UserObserver::class);\n        Server::observe(ServerObserver::class);\n        Subuser::observe(SubuserObserver::class);\n        EggVariable::observe(EggVariableObserver::class);\n    }\n}\n"
  },
  {
    "path": "app/Providers/HashidsServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Pterodactyl\\Extensions\\Hashids;\nuse Illuminate\\Support\\ServiceProvider;\nuse Pterodactyl\\Contracts\\Extensions\\HashidsInterface;\n\nclass HashidsServiceProvider extends ServiceProvider\n{\n    /**\n     * Register the ability to use Hashids.\n     */\n    public function register(): void\n    {\n        $this->app->singleton(HashidsInterface::class, function () {\n            /** @var \\Illuminate\\Contracts\\Config\\Repository $config */\n            $config = $this->app['config'];\n\n            return new Hashids(\n                $config->get('hashids.salt', ''),\n                $config->get('hashids.length', 0),\n                $config->get('hashids.alphabet', 'abcdefghijkmlnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890')\n            );\n        });\n\n        $this->app->alias(HashidsInterface::class, 'hashids');\n    }\n}\n"
  },
  {
    "path": "app/Providers/RepositoryServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Illuminate\\Support\\ServiceProvider;\nuse Pterodactyl\\Repositories\\Eloquent\\EggRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\NestRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\NodeRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\TaskRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\UserRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\ApiKeyRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\SessionRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\SubuserRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\DatabaseRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\LocationRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\ScheduleRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\SettingsRepository;\nuse Pterodactyl\\Repositories\\Eloquent\\AllocationRepository;\nuse Pterodactyl\\Contracts\\Repository\\EggRepositoryInterface;\nuse Pterodactyl\\Repositories\\Eloquent\\EggVariableRepository;\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\NodeRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\TaskRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\UserRepositoryInterface;\nuse Pterodactyl\\Repositories\\Eloquent\\DatabaseHostRepository;\nuse Pterodactyl\\Contracts\\Repository\\ApiKeyRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\ServerRepositoryInterface;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerVariableRepository;\nuse Pterodactyl\\Contracts\\Repository\\SessionRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\SubuserRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\LocationRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\ScheduleRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\SettingsRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\AllocationRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\EggVariableRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseHostRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\ServerVariableRepositoryInterface;\n\nclass RepositoryServiceProvider extends ServiceProvider\n{\n    /**\n     * Register all the repository bindings.\n     */\n    public function register(): void\n    {\n        // Eloquent Repositories\n        $this->app->bind(AllocationRepositoryInterface::class, AllocationRepository::class);\n        $this->app->bind(ApiKeyRepositoryInterface::class, ApiKeyRepository::class);\n        $this->app->bind(DatabaseRepositoryInterface::class, DatabaseRepository::class);\n        $this->app->bind(DatabaseHostRepositoryInterface::class, DatabaseHostRepository::class);\n        $this->app->bind(EggRepositoryInterface::class, EggRepository::class);\n        $this->app->bind(EggVariableRepositoryInterface::class, EggVariableRepository::class);\n        $this->app->bind(LocationRepositoryInterface::class, LocationRepository::class);\n        $this->app->bind(NestRepositoryInterface::class, NestRepository::class);\n        $this->app->bind(NodeRepositoryInterface::class, NodeRepository::class);\n        $this->app->bind(ScheduleRepositoryInterface::class, ScheduleRepository::class);\n        $this->app->bind(ServerRepositoryInterface::class, ServerRepository::class);\n        $this->app->bind(ServerVariableRepositoryInterface::class, ServerVariableRepository::class);\n        $this->app->bind(SessionRepositoryInterface::class, SessionRepository::class);\n        $this->app->bind(SettingsRepositoryInterface::class, SettingsRepository::class);\n        $this->app->bind(SubuserRepositoryInterface::class, SubuserRepository::class);\n        $this->app->bind(TaskRepositoryInterface::class, TaskRepository::class);\n        $this->app->bind(UserRepositoryInterface::class, UserRepository::class);\n    }\n}\n"
  },
  {
    "path": "app/Providers/RouteServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Enum\\ResourceLimit;\nuse Illuminate\\Support\\Facades\\Route;\nuse Illuminate\\Cache\\RateLimiting\\Limit;\nuse Illuminate\\Support\\Facades\\RateLimiter;\nuse Pterodactyl\\Http\\Middleware\\TrimStrings;\nuse Pterodactyl\\Http\\Middleware\\AdminAuthenticate;\nuse Pterodactyl\\Http\\Middleware\\RequireTwoFactorAuthentication;\nuse Illuminate\\Foundation\\Support\\Providers\\RouteServiceProvider as ServiceProvider;\n\nclass RouteServiceProvider extends ServiceProvider\n{\n    protected const FILE_PATH_REGEX = '/^\\/api\\/client\\/servers\\/([a-z0-9-]{36})\\/files(\\/?$|\\/(.)*$)/i';\n\n    /**\n     * Define your route model bindings, pattern filters, etc.\n     */\n    public function boot(): void\n    {\n        $this->configureRateLimiting();\n\n        // Disable trimming string values when requesting file information — it isn't helpful\n        // and messes up the ability to actually open a directory that ends with a space.\n        TrimStrings::skipWhen(function (Request $request) {\n            return preg_match(self::FILE_PATH_REGEX, $request->getPathInfo()) === 1;\n        });\n\n        // This is needed to make use of the \"resolveRouteBinding\" functionality in the\n        // model. Without it you'll never trigger that logic flow thus resulting in a 404\n        // error because we request databases with a HashID, and not with a normal ID.\n        Route::model('database', Database::class);\n\n        $this->routes(function () {\n            Route::middleware('web')->group(function () {\n                Route::middleware(['auth.session', RequireTwoFactorAuthentication::class])\n                    ->group(base_path('routes/base.php'));\n\n                Route::middleware(['auth.session', RequireTwoFactorAuthentication::class, AdminAuthenticate::class])\n                    ->prefix('/admin')\n                    ->group(base_path('routes/admin.php'));\n\n                Route::middleware('guest')->prefix('/auth')->group(base_path('routes/auth.php'));\n            });\n\n            Route::middleware(['api', RequireTwoFactorAuthentication::class])->group(function () {\n                Route::middleware(['application-api', 'throttle:api.application'])\n                    ->prefix('/api/application')\n                    ->scopeBindings()\n                    ->group(base_path('routes/api-application.php'));\n\n                Route::middleware(['client-api', 'throttle:api.client'])\n                    ->prefix('/api/client')\n                    ->scopeBindings()\n                    ->group(base_path('routes/api-client.php'));\n            });\n\n            Route::middleware('daemon')\n                ->prefix('/api/remote')\n                ->scopeBindings()\n                ->group(base_path('routes/api-remote.php'));\n        });\n    }\n\n    /**\n     * Configure the rate limiters for the application.\n     */\n    protected function configureRateLimiting(): void\n    {\n        // Authentication rate limiting. For login and checkpoint endpoints we'll apply\n        // a limit of 10 requests per minute, for the forgot password endpoint apply a\n        // limit of two per minute for the requester so that there is less ability to\n        // trigger email spam.\n        RateLimiter::for('authentication', function (Request $request) {\n            if ($request->route()->named('auth.post.forgot-password')) {\n                return Limit::perMinute(2)->by($request->ip());\n            }\n\n            return Limit::perMinute(10);\n        });\n\n        // Configure the throttles for both the application and client APIs below.\n        // This is configurable per-instance in \"config/http.php\". By default this\n        // limiter will be tied to the specific request user, and falls back to the\n        // request IP if there is no request user present for the key.\n        //\n        // This means that an authenticated API user cannot use IP switching to get\n        // around the limits.\n        RateLimiter::for('api.client', function (Request $request) {\n            $key = optional($request->user())->uuid ?: $request->ip();\n\n            return Limit::perMinutes(\n                config('http.rate_limit.client_period'),\n                config('http.rate_limit.client')\n            )->by($key);\n        });\n\n        RateLimiter::for('api.application', function (Request $request) {\n            $key = optional($request->user())->uuid ?: $request->ip();\n\n            return Limit::perMinutes(\n                config('http.rate_limit.application_period'),\n                config('http.rate_limit.application')\n            )->by($key);\n        });\n\n        ResourceLimit::boot();\n    }\n}\n"
  },
  {
    "path": "app/Providers/SettingsServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Psr\\Log\\LoggerInterface as Log;\nuse Illuminate\\Database\\QueryException;\nuse Illuminate\\Support\\ServiceProvider;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Illuminate\\Contracts\\Encryption\\DecryptException;\nuse Illuminate\\Contracts\\Config\\Repository as ConfigRepository;\nuse Pterodactyl\\Contracts\\Repository\\SettingsRepositoryInterface;\n\nclass SettingsServiceProvider extends ServiceProvider\n{\n    /**\n     * An array of configuration keys to override with database values\n     * if they exist.\n     */\n    protected array $keys = [\n        'app:name',\n        'app:locale',\n        'logo:title',\n        'logo:favicon',\n        'logo:auth',\n        'icp:enabled',\n        'icp:record',\n        'icp:security_record',\n        'recaptcha:enabled',\n        'recaptcha:secret_key',\n        'recaptcha:website_key',\n        'pterodactyl:guzzle:timeout',\n        'pterodactyl:guzzle:connect_timeout',\n        'pterodactyl:console:count',\n        'pterodactyl:console:frequency',\n        'pterodactyl:auth:2fa_required',\n        'pterodactyl:client_features:allocations:enabled',\n        'pterodactyl:client_features:allocations:range_start',\n        'pterodactyl:client_features:allocations:range_end',\n        'pterodactyl:client_features:allocations:consecutive_enabled',\n        'pterodactyl:client_features:allocations:consecutive_limit',\n        'pterodactyl:client_features:egg_change:mode',\n    ];\n\n    /**\n     * Keys specific to the mail driver that are only grabbed from the database\n     * when using the SMTP driver.\n     */\n    protected array $emailKeys = [\n        'mail:mailers:smtp:host',\n        'mail:mailers:smtp:port',\n        'mail:mailers:smtp:encryption',\n        'mail:mailers:smtp:username',\n        'mail:mailers:smtp:password',\n        'mail:from:address',\n        'mail:from:name',\n    ];\n\n    /**\n     * Keys that are encrypted and should be decrypted when set in the\n     * configuration array.\n     */\n    protected static array $encrypted = [\n        'mail:mailers:smtp:password',\n    ];\n\n    /**\n     * Boot the service provider.\n     */\n    public function boot(ConfigRepository $config, Encrypter $encrypter, Log $log, SettingsRepositoryInterface $settings): void\n    {\n        // Only set the email driver settings from the database if we\n        // are configured using SMTP as the driver.\n        if ($config->get('mail.default') === 'smtp') {\n            $this->keys = array_merge($this->keys, $this->emailKeys);\n        }\n\n        try {\n            $values = $settings->all()->mapWithKeys(function ($setting) {\n                return [$setting->key => $setting->value];\n            })->toArray();\n        } catch (QueryException $exception) {\n            $log->notice('尝试从数据库加载设置时遇到查询异常: ' . $exception->getMessage());\n\n            return;\n        }\n\n        foreach ($this->keys as $key) {\n            $value = array_get($values, 'settings::' . $key, $config->get(str_replace(':', '.', $key)));\n            if (in_array($key, self::$encrypted)) {\n                try {\n                    $value = $encrypter->decrypt($value);\n                } catch (DecryptException $exception) {\n                }\n            }\n\n            switch (strtolower($value)) {\n                case 'true':\n                case '(true)':\n                    $value = true;\n                    break;\n                case 'false':\n                case '(false)':\n                    $value = false;\n                    break;\n                case 'empty':\n                case '(empty)':\n                    $value = '';\n                    break;\n                case 'null':\n                case '(null)':\n                    $value = null;\n            }\n\n            $config->set(str_replace(':', '.', $key), $value);\n        }\n    }\n\n    public static function getEncryptedKeys(): array\n    {\n        return self::$encrypted;\n    }\n}\n"
  },
  {
    "path": "app/Providers/ViewComposerServiceProvider.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Providers;\n\nuse Illuminate\\Support\\ServiceProvider;\nuse Pterodactyl\\Http\\ViewComposers\\AssetComposer;\n\nclass ViewComposerServiceProvider extends ServiceProvider\n{\n    /**\n     * Register bindings in the container.\n     */\n    public function boot(): void\n    {\n        $this->app->make('view')->composer('*', AssetComposer::class);\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/AllocationRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Allocation;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Pterodactyl\\Contracts\\Repository\\AllocationRepositoryInterface;\n\nclass AllocationRepository extends EloquentRepository implements AllocationRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Allocation::class;\n    }\n\n    /**\n     * Return all the allocations that exist for a node that are not currently\n     * allocated.\n     */\n    public function getUnassignedAllocationIds(int $node): array\n    {\n        return Allocation::query()->select('id')\n            ->whereNull('server_id')\n            ->where('node_id', $node)\n            ->get()\n            ->pluck('id')\n            ->toArray();\n    }\n\n    /**\n     * Return a concatenated result set of node ips that already have at least one\n     * server assigned to that IP. This allows for filtering out sets for\n     * dedicated allocation IPs.\n     *\n     * If an array of nodes is passed the results will be limited to allocations\n     * in those nodes.\n     */\n    protected function getDiscardableDedicatedAllocations(array $nodes = []): array\n    {\n        $query = Allocation::query()->selectRaw('CONCAT_WS(\"-\", node_id, ip) as result');\n\n        if (!empty($nodes)) {\n            $query->whereIn('node_id', $nodes);\n        }\n\n        return $query->whereNotNull('server_id')\n            ->groupByRaw('CONCAT(node_id, ip)')\n            ->get()\n            ->pluck('result')\n            ->toArray();\n    }\n\n    /**\n     * Return a single allocation from those meeting the requirements.\n     */\n    public function getRandomAllocation(array $nodes, array $ports, bool $dedicated = false): ?Allocation\n    {\n        $query = Allocation::query()->whereNull('server_id');\n\n        if (!empty($nodes)) {\n            $query->whereIn('node_id', $nodes);\n        }\n\n        if (!empty($ports)) {\n            $query->where(function (Builder $inner) use ($ports) {\n                $whereIn = [];\n                foreach ($ports as $port) {\n                    if (is_array($port)) {\n                        $inner->orWhereBetween('port', $port);\n                        continue;\n                    }\n\n                    $whereIn[] = $port;\n                }\n\n                if (!empty($whereIn)) {\n                    $inner->orWhereIn('port', $whereIn);\n                }\n            });\n        }\n\n        // If this allocation should not be shared with any other servers get\n        // the data and modify the query as necessary,\n        if ($dedicated) {\n            $discard = $this->getDiscardableDedicatedAllocations($nodes);\n\n            if (!empty($discard)) {\n                $query->whereNotIn(\n                    $this->getBuilder()->raw('CONCAT_WS(\"-\", node_id, ip)'),\n                    $discard\n                );\n            }\n        }\n\n        return $query->inRandomOrder()->first();\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/ApiKeyRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\ApiKey;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Contracts\\Repository\\ApiKeyRepositoryInterface;\n\nclass ApiKeyRepository extends EloquentRepository implements ApiKeyRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return ApiKey::class;\n    }\n\n    /**\n     * Get all the account API keys that exist for a specific user.\n     */\n    public function getAccountKeys(User $user): Collection\n    {\n        return $this->getBuilder()->where('user_id', $user->id)\n            ->where('key_type', ApiKey::TYPE_ACCOUNT)\n            ->get($this->getColumns());\n    }\n\n    /**\n     * Delete an account API key from the panel for a specific user.\n     */\n    public function deleteAccountKey(User $user, string $identifier): int\n    {\n        return $this->getBuilder()->where('user_id', $user->id)\n            ->where('key_type', ApiKey::TYPE_ACCOUNT)\n            ->where('identifier', $identifier)\n            ->delete();\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/BackupRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Carbon\\Carbon;\nuse Pterodactyl\\Models\\Backup;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Database\\Eloquent\\Relations\\HasMany;\n\nclass BackupRepository extends EloquentRepository\n{\n    public function model(): string\n    {\n        return Backup::class;\n    }\n\n    /**\n     * Determines if too many backups have been generated by the server.\n     */\n    public function getBackupsGeneratedDuringTimespan(int $server, int $seconds = 600): array|Collection\n    {\n        return $this->getBuilder()\n            ->withTrashed()\n            ->where('server_id', $server)\n            ->where(function ($query) {\n                $query->whereNull('completed_at')\n                    ->orWhere('is_successful', '=', true);\n            })\n            ->where('created_at', '>=', Carbon::now()->subSeconds($seconds)->toDateTimeString())\n            ->get()\n            ->toBase();\n    }\n\n    /**\n     * Returns a query filtering only non-failed backups for a specific server.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Relations\\HasMany<\\Pterodactyl\\Models\\Backup, \\Pterodactyl\\Models\\Server>\n     */\n    public function getNonFailedBackups(Server $server): HasMany\n    {\n        return $server->backups()->where(function ($query) {\n            $query->whereNull('completed_at')\n                ->orWhere('is_successful', true);\n        });\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/DatabaseHostRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseHostRepositoryInterface;\n\nclass DatabaseHostRepository extends EloquentRepository implements DatabaseHostRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return DatabaseHost::class;\n    }\n\n    /**\n     * Return database hosts with a count of databases and the node\n     * information for which it is attached.\n     */\n    public function getWithViewDetails(): Collection\n    {\n        return $this->getBuilder()->withCount('databases')->with('node')->get();\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/DatabaseRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Database;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Foundation\\Application;\nuse Illuminate\\Database\\DatabaseManager;\nuse Illuminate\\Contracts\\Pagination\\LengthAwarePaginator;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseRepositoryInterface;\n\nclass DatabaseRepository extends EloquentRepository implements DatabaseRepositoryInterface\n{\n    protected string $connection = self::DEFAULT_CONNECTION_NAME;\n\n    /**\n     * DatabaseRepository constructor.\n     */\n    public function __construct(Application $application, private DatabaseManager $database)\n    {\n        parent::__construct($application);\n    }\n\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Database::class;\n    }\n\n    /**\n     * Return the connection to execute statements against.\n     */\n    public function getConnection(): string\n    {\n        return $this->connection;\n    }\n\n    /**\n     * Set the connection name to execute statements against.\n     */\n    public function setConnection(string $connection): self\n    {\n        $this->connection = $connection;\n\n        return $this;\n    }\n\n    /**\n     * Return all the databases belonging to a server.\n     */\n    public function getDatabasesForServer(int $server): Collection\n    {\n        return $this->getBuilder()->with('host')->where('server_id', $server)->get($this->getColumns());\n    }\n\n    /**\n     * Return all the databases for a given host with the server relationship loaded.\n     */\n    public function getDatabasesForHost(int $host, int $count = 25): LengthAwarePaginator\n    {\n        return $this->getBuilder()->with('server')\n            ->where('database_host_id', $host)\n            ->paginate($count, $this->getColumns());\n    }\n\n    /**\n     * Create a new database on a given connection.\n     */\n    public function createDatabase(string $database): bool\n    {\n        return $this->run(sprintf('CREATE DATABASE IF NOT EXISTS `%s`', $database));\n    }\n\n    /**\n     * Create a new database user on a given connection.\n     */\n    public function createUser(string $username, string $remote, string $password, ?int $max_connections): bool\n    {\n        $args = [$username, $remote, $password];\n        $command = 'CREATE USER `%s`@`%s` IDENTIFIED BY \\'%s\\'';\n\n        if (!empty($max_connections)) {\n            $args[] = $max_connections;\n            $command .= ' WITH MAX_USER_CONNECTIONS %s';\n        }\n\n        return $this->run(sprintf($command, ...$args));\n    }\n\n    /**\n     * Give a specific user access to a given database.\n     */\n    public function assignUserToDatabase(string $database, string $username, string $remote): bool\n    {\n        return $this->run(sprintf(\n            'GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, ALTER, REFERENCES, INDEX, LOCK TABLES, CREATE ROUTINE, ALTER ROUTINE, EXECUTE, CREATE TEMPORARY TABLES, CREATE VIEW, SHOW VIEW, EVENT, TRIGGER ON `%s`.* TO `%s`@`%s`',\n            $database,\n            $username,\n            $remote\n        ));\n    }\n\n    /**\n     * Flush the privileges for a given connection.\n     */\n    public function flush(): bool\n    {\n        return $this->run('FLUSH PRIVILEGES');\n    }\n\n    /**\n     * Drop a given database on a specific connection.\n     */\n    public function dropDatabase(string $database): bool\n    {\n        return $this->run(sprintf('DROP DATABASE IF EXISTS `%s`', $database));\n    }\n\n    /**\n     * Drop a given user on a specific connection.\n     */\n    public function dropUser(string $username, string $remote): bool\n    {\n        return $this->run(sprintf('DROP USER IF EXISTS `%s`@`%s`', $username, $remote));\n    }\n\n    /**\n     * Run the provided statement against the database on a given connection.\n     */\n    private function run(string $statement): bool\n    {\n        return $this->database->connection($this->getConnection())->statement($statement);\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/EggRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Egg;\nuse Webmozart\\Assert\\Assert;\nuse Illuminate\\Database\\Eloquent\\Collection;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Pterodactyl\\Contracts\\Repository\\EggRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\n\nclass EggRepository extends EloquentRepository implements EggRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Egg::class;\n    }\n\n    /**\n     * Return an egg with the variables relation attached.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getWithVariables(int $id): Egg\n    {\n        try {\n            return $this->getBuilder()->with('variables')->findOrFail($id, $this->getColumns());\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n\n    /**\n     * Return all eggs and their relations to be used in the daemon API.\n     */\n    public function getAllWithCopyAttributes(): Collection\n    {\n        return $this->getBuilder()->with('scriptFrom', 'configFrom')->get($this->getColumns());\n    }\n\n    /**\n     * Return an egg with the scriptFrom and configFrom relations loaded onto the model.\n     *\n     * @param int|string $value\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getWithCopyAttributes($value, string $column = 'id'): Egg\n    {\n        Assert::true(is_digit($value) || is_string($value), 'First argument passed to getWithCopyAttributes must be an integer or string, received %s.');\n\n        try {\n            return $this->getBuilder()->with('scriptFrom', 'configFrom')->where($column, '=', $value)->firstOrFail($this->getColumns());\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n\n    /**\n     * Return all the data needed to export a service.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getWithExportAttributes(int $id): Egg\n    {\n        try {\n            return $this->getBuilder()->with('scriptFrom', 'configFrom', 'variables')->findOrFail($id, $this->getColumns());\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n\n    /**\n     * Confirm a copy script belongs to the same nest as the item trying to use it.\n     */\n    public function isCopyableScript(int $copyFromId, int $service): bool\n    {\n        return $this->getBuilder()->whereNull('copy_script_from')\n            ->where('id', '=', $copyFromId)\n            ->where('nest_id', '=', $service)\n            ->exists();\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/EggVariableRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Models\\EggVariable;\nuse Pterodactyl\\Contracts\\Repository\\EggVariableRepositoryInterface;\n\nclass EggVariableRepository extends EloquentRepository implements EggVariableRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return EggVariable::class;\n    }\n\n    /**\n     * Return editable variables for a given egg. Editable variables must be set to\n     * user viewable in order to be picked up by this function.\n     */\n    public function getEditableVariables(int $egg): Collection\n    {\n        return $this->getBuilder()->where([\n            ['egg_id', '=', $egg],\n            ['user_viewable', '=', 1],\n            ['user_editable', '=', 1],\n        ])->get($this->getColumns());\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/EloquentRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Illuminate\\Http\\Request;\nuse Webmozart\\Assert\\Assert;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Database\\Eloquent\\Model;\nuse Pterodactyl\\Repositories\\Repository;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Illuminate\\Database\\Query\\Expression;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Illuminate\\Contracts\\Pagination\\LengthAwarePaginator;\nuse Pterodactyl\\Contracts\\Repository\\RepositoryInterface;\nuse Pterodactyl\\Exceptions\\Model\\DataValidationException;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\n\nabstract class EloquentRepository extends Repository implements RepositoryInterface\n{\n    protected bool $useRequestFilters = false;\n\n    /**\n     * Determines if the repository function should use filters off the request object\n     * present when returning results. This allows repository methods to be called in API\n     * context's such that we can pass through ?filter[name]=Dane&sort=desc for example.\n     */\n    public function usingRequestFilters(bool $usingFilters = true): self\n    {\n        $this->useRequestFilters = $usingFilters;\n\n        return $this;\n    }\n\n    /**\n     * Returns the request instance.\n     */\n    protected function request(): Request\n    {\n        return $this->app->make(Request::class);\n    }\n\n    /**\n     * Paginate the response data based on the page para.\n     */\n    protected function paginate(Builder $instance, int $default = 50): LengthAwarePaginator\n    {\n        if (!$this->useRequestFilters) {\n            return $instance->paginate($default);\n        }\n\n        return $instance->paginate($this->request()->query('per_page', $default));\n    }\n\n    /**\n     * Return an instance of the eloquent model bound to this\n     * repository instance.\n     */\n    public function getModel(): Model\n    {\n        return $this->model;\n    }\n\n    /**\n     * Return an instance of the builder to use for this repository.\n     */\n    public function getBuilder(): Builder\n    {\n        return $this->getModel()->newQuery();\n    }\n\n    /**\n     * Create a new record in the database and return the associated model.\n     *\n     * @throws DataValidationException\n     */\n    public function create(array $fields, bool $validate = true, bool $force = false): Model|bool\n    {\n        $instance = $this->getBuilder()->newModelInstance();\n        ($force) ? $instance->forceFill($fields) : $instance->fill($fields);\n\n        if (!$validate) {\n            $saved = $instance->skipValidation()->save();\n        } else {\n            if (!$saved = $instance->save()) {\n                throw new DataValidationException($instance->getValidator(), $instance);\n            }\n        }\n\n        return ($this->withFresh) ? $instance->fresh() : $saved;\n    }\n\n    /**\n     * Find a model that has the specific ID passed.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function find(int $id): Model\n    {\n        try {\n            return $this->getBuilder()->findOrFail($id, $this->getColumns());\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n\n    /**\n     * Find a model matching an array of where clauses.\n     */\n    public function findWhere(array $fields): Collection\n    {\n        return $this->getBuilder()->where($fields)->get($this->getColumns());\n    }\n\n    /**\n     * Find and return the first matching instance for the given fields.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function findFirstWhere(array $fields): Model\n    {\n        try {\n            return $this->getBuilder()->where($fields)->firstOrFail($this->getColumns());\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n\n    /**\n     * Return a count of records matching the passed arguments.\n     */\n    public function findCountWhere(array $fields): int\n    {\n        return $this->getBuilder()->where($fields)->count($this->getColumns());\n    }\n\n    /**\n     * Delete a given record from the database.\n     */\n    public function delete(int $id, bool $destroy = false): int\n    {\n        return $this->deleteWhere(['id' => $id], $destroy);\n    }\n\n    /**\n     * Delete records matching the given attributes.\n     */\n    public function deleteWhere(array $attributes, bool $force = false): int\n    {\n        $instance = $this->getBuilder()->where($attributes);\n\n        return ($force) ? $instance->forceDelete() : $instance->delete();\n    }\n\n    /**\n     * Update a given ID with the passed array of fields.\n     *\n     * @throws DataValidationException\n     * @throws RecordNotFoundException\n     */\n    public function update(int $id, array $fields, bool $validate = true, bool $force = false): Model|bool\n    {\n        try {\n            $instance = $this->getBuilder()->where('id', $id)->firstOrFail();\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n\n        ($force) ? $instance->forceFill($fields) : $instance->fill($fields);\n\n        if (!$validate) {\n            $saved = $instance->skipValidation()->save();\n        } else {\n            if (!$saved = $instance->save()) {\n                throw new DataValidationException($instance->getValidator(), $instance);\n            }\n        }\n\n        return ($this->withFresh) ? $instance->fresh() : $saved;\n    }\n\n    /**\n     * Update a model using the attributes passed.\n     */\n    public function updateWhere(array $attributes, array $values): int\n    {\n        return $this->getBuilder()->where($attributes)->update($values);\n    }\n\n    /**\n     * Perform a mass update where matching records are updated using whereIn.\n     * This does not perform any model data validation.\n     */\n    public function updateWhereIn(string $column, array $values, array $fields): int\n    {\n        Assert::notEmpty($column, 'First argument passed to updateWhereIn must be a non-empty string.');\n\n        return $this->getBuilder()->whereIn($column, $values)->update($fields);\n    }\n\n    /**\n     * Update a record if it exists in the database, otherwise create it.\n     *\n     * @throws DataValidationException\n     * @throws RecordNotFoundException\n     */\n    public function updateOrCreate(array $where, array $fields, bool $validate = true, bool $force = false): Model|bool\n    {\n        foreach ($where as $item) {\n            Assert::true(is_scalar($item) || is_null($item), 'First argument passed to updateOrCreate should be an array of scalar or null values, received an array value of %s.');\n        }\n\n        try {\n            $instance = $this->setColumns('id')->findFirstWhere($where);\n        } catch (RecordNotFoundException) {\n            return $this->create(array_merge($where, $fields), $validate, $force);\n        }\n\n        return $this->update($instance->id, $fields, $validate, $force);\n    }\n\n    /**\n     * Return all records associated with the given model.\n     *\n     * @deprecated Just use the model\n     */\n    public function all(): Collection\n    {\n        return $this->getBuilder()->get($this->getColumns());\n    }\n\n    /**\n     * Return a paginated result set using a search term if set on the repository.\n     */\n    public function paginated(int $perPage): LengthAwarePaginator\n    {\n        return $this->getBuilder()->paginate($perPage, $this->getColumns());\n    }\n\n    /**\n     * Insert a single or multiple records into the database at once skipping\n     * validation and mass assignment checking.\n     */\n    public function insert(array $data): bool\n    {\n        return $this->getBuilder()->insert($data);\n    }\n\n    /**\n     * Insert multiple records into the database and ignore duplicates.\n     */\n    public function insertIgnore(array $values): bool\n    {\n        if (empty($values)) {\n            return true;\n        }\n\n        foreach ($values as $key => $value) {\n            ksort($value);\n            $values[$key] = $value;\n        }\n\n        $bindings = array_values(array_filter(array_flatten($values, 1), function ($binding) {\n            return !$binding instanceof Expression;\n        }));\n\n        $grammar = $this->getBuilder()->toBase()->getGrammar();\n        $table = $grammar->wrapTable($this->getModel()->getTable());\n        $columns = $grammar->columnize(array_keys(reset($values)));\n\n        $parameters = collect($values)->map(function ($record) use ($grammar) {\n            return sprintf('(%s)', $grammar->parameterize($record));\n        })->implode(', ');\n\n        $statement = \"insert ignore into $table ($columns) values $parameters\";\n\n        return $this->getBuilder()->getConnection()->statement($statement, $bindings);\n    }\n\n    /**\n     * Get the amount of entries in the database.\n     *\n     * @deprecated just use the count method off a model\n     */\n    public function count(): int\n    {\n        return $this->getBuilder()->count();\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/LocationRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Location;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\nuse Pterodactyl\\Contracts\\Repository\\LocationRepositoryInterface;\n\nclass LocationRepository extends EloquentRepository implements LocationRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Location::class;\n    }\n\n    /**\n     * Return locations with a count of nodes and servers attached to it.\n     */\n    public function getAllWithDetails(): Collection\n    {\n        return $this->getBuilder()->withCount('nodes', 'servers')->get($this->getColumns());\n    }\n\n    /**\n     * Return all the available locations with the nodes as a relationship.\n     */\n    public function getAllWithNodes(): Collection\n    {\n        return $this->getBuilder()->with('nodes')->get($this->getColumns());\n    }\n\n    /**\n     * Return all the nodes and their respective count of servers for a location.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getWithNodes(int $id): Location\n    {\n        try {\n            return $this->getBuilder()->with('nodes.servers')->findOrFail($id, $this->getColumns());\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n\n    /**\n     * Return a location and the count of nodes in that location.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getWithNodeCount(int $id): Location\n    {\n        try {\n            return $this->getBuilder()->withCount('nodes')->findOrFail($id, $this->getColumns());\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/MountRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Mount;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\n\nclass MountRepository extends EloquentRepository\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Mount::class;\n    }\n\n    /**\n     * Return mounts with a count of eggs, nodes, and servers attached to it.\n     */\n    public function getAllWithDetails(): Collection\n    {\n        return $this->getBuilder()->withCount('eggs', 'nodes')->get($this->getColumns());\n    }\n\n    /**\n     * Return all the mounts and their respective relations.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getWithRelations(string $id): Mount\n    {\n        try {\n            return $this->getBuilder()->with('eggs', 'nodes')->findOrFail($id, $this->getColumns());\n        } catch (ModelNotFoundException $exception) {\n            throw new RecordNotFoundException();\n        }\n    }\n\n    /**\n     * Return mounts available to a server (ignoring if they are or are not mounted).\n     */\n    public function getMountListForServer(Server $server): Collection\n    {\n        return $this->getBuilder()\n            ->whereHas('eggs', function ($q) use ($server) {\n                $q->where('id', '=', $server->egg_id);\n            })\n            ->whereHas('nodes', function ($q) use ($server) {\n                $q->where('id', '=', $server->node_id);\n            })\n            ->get($this->getColumns());\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/NestRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Nest;\nuse Illuminate\\Database\\Eloquent\\Collection;\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\n\nclass NestRepository extends EloquentRepository implements NestRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Nest::class;\n    }\n\n    /**\n     * Return a nest or all nests with their associated eggs and variables.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Collection<int, \\Pterodactyl\\Models\\Nest>|\\Pterodactyl\\Models\\Nest\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getWithEggs(?int $id = null): Collection|Nest\n    {\n        $instance = $this->getBuilder()->with('eggs', 'eggs.variables');\n\n        if (!is_null($id)) {\n            $instance = $instance->find($id, $this->getColumns());\n            if (!$instance) {\n                throw new RecordNotFoundException();\n            }\n\n            return $instance;\n        }\n\n        return $instance->get($this->getColumns());\n    }\n\n    /**\n     * Return a nest or all nests and the count of eggs and servers for that nest.\n     *\n     * @return \\Illuminate\\Database\\Eloquent\\Collection<int, \\Pterodactyl\\Models\\Nest>|\\Pterodactyl\\Models\\Nest\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getWithCounts(?int $id = null): Collection|Nest\n    {\n        $instance = $this->getBuilder()->withCount(['eggs', 'servers']);\n\n        if (!is_null($id)) {\n            $instance = $instance->find($id, $this->getColumns());\n            if (!$instance) {\n                throw new RecordNotFoundException();\n            }\n\n            return $instance;\n        }\n\n        return $instance->get($this->getColumns());\n    }\n\n    /**\n     * Return a nest along with its associated eggs and the servers relation on those eggs.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getWithEggServers(int $id): Nest\n    {\n        $instance = $this->getBuilder()->with('eggs.servers')->find($id, $this->getColumns());\n        if (!$instance) {\n            throw new RecordNotFoundException();\n        }\n\n        return $instance; // @phpstan-ignore return.type\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/NodeRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Contracts\\Repository\\NodeRepositoryInterface;\n\nclass NodeRepository extends EloquentRepository implements NodeRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Node::class;\n    }\n\n    /**\n     * Return the usage stats for a single node.\n     */\n    public function getUsageStats(Node $node): array\n    {\n        $stats = $this->getBuilder()\n            ->selectRaw('IFNULL(SUM(servers.memory), 0) as sum_memory, IFNULL(SUM(servers.disk), 0) as sum_disk')\n            ->join('servers', 'servers.node_id', '=', 'nodes.id')\n            ->where('node_id', '=', $node->id)\n            ->first();\n\n        return Collection::make(['disk' => $stats->sum_disk, 'memory' => $stats->sum_memory])\n            ->mapWithKeys(function ($value, $key) use ($node) {\n                $maxUsage = $node->{$key};\n                if ($node->{$key . '_overallocate'} > 0) {\n                    $maxUsage = $node->{$key} * (1 + ($node->{$key . '_overallocate'} / 100));\n                }\n\n                $percent = ($value / $maxUsage) * 100;\n\n                return [\n                    $key => [\n                        'value' => number_format($value),\n                        'max' => number_format($maxUsage),\n                        'percent' => $percent,\n                        'css' => ($percent <= self::THRESHOLD_PERCENTAGE_LOW) ? 'green' : (($percent > self::THRESHOLD_PERCENTAGE_MEDIUM) ? 'red' : 'yellow'),\n                    ],\n                ];\n            })\n            ->toArray();\n    }\n\n    /**\n     * Return the usage stats for a single node.\n     */\n    public function getUsageStatsRaw(Node $node): array\n    {\n        $stats = $this->getBuilder()->select(\n            $this->getBuilder()->raw('IFNULL(SUM(servers.memory), 0) as sum_memory, IFNULL(SUM(servers.disk), 0) as sum_disk')\n        )->join('servers', 'servers.node_id', '=', 'nodes.id')->where('node_id', $node->id)->first();\n\n        return collect(['disk' => $stats->sum_disk, 'memory' => $stats->sum_memory])->mapWithKeys(function ($value, $key) use ($node) {\n            $maxUsage = $node->{$key};\n            if ($node->{$key . '_overallocate'} > 0) {\n                $maxUsage = $node->{$key} * (1 + ($node->{$key . '_overallocate'} / 100));\n            }\n\n            return [\n                $key => [\n                    'value' => $value,\n                    'max' => $maxUsage,\n                ],\n            ];\n        })->toArray();\n    }\n\n    /**\n     * Return a single node with location and server information.\n     */\n    public function loadLocationAndServerCount(Node $node, bool $refresh = false): Node\n    {\n        if (!$node->relationLoaded('location') || $refresh) {\n            $node->load('location');\n        }\n\n        // This is quite ugly and can probably be improved down the road.\n        // And by probably, I mean it should.\n        if (is_null($node->servers_count) || $refresh) {\n            $node->load('servers');\n            $node->setRelation('servers_count', count($node->getRelation('servers')));\n            unset($node->servers);\n        }\n\n        return $node;\n    }\n\n    /**\n     * Attach a paginated set of allocations to a node mode including\n     * any servers that are also attached to those allocations.\n     */\n    public function loadNodeAllocations(Node $node, bool $refresh = false): Node\n    {\n        $node->setRelation(\n            'allocations',\n            $node->allocations()\n                ->orderByRaw('server_id IS NOT NULL DESC, server_id IS NULL')\n                ->orderByRaw('INET_ATON(ip) ASC')\n                ->orderBy('port')\n                ->with('server:id,name')\n                ->paginate(50)\n        );\n\n        return $node;\n    }\n\n    /**\n     * Return a collection of nodes for all locations to use in server creation UI.\n     */\n    public function getNodesForServerCreation(): Collection\n    {\n        return $this->getBuilder()->with('allocations')->get()->map(function (Node $item) {\n            $filtered = $item->getRelation('allocations')->where('server_id', null)->map(function ($map) {\n                return collect($map)->only(['id', 'ip', 'port']);\n            });\n\n            $item->ports = $filtered->map(function ($map) {\n                return [\n                    'id' => $map['id'],\n                    'text' => sprintf('%s:%s', $map['ip'], $map['port']),\n                ];\n            })->values();\n\n            return [\n                'id' => $item->id,\n                'text' => $item->name,\n                'allocations' => $item->ports,\n            ];\n        })->values();\n    }\n\n    /**\n     * Returns a node with the given id with the Node's resource usage.\n     */\n    public function getNodeWithResourceUsage(int $node_id): Node\n    {\n        $instance = $this->getBuilder()\n            ->select(['nodes.id', 'nodes.fqdn', 'nodes.scheme', 'nodes.daemon_token', 'nodes.daemonListen', 'nodes.memory', 'nodes.disk', 'nodes.memory_overallocate', 'nodes.disk_overallocate'])\n            ->selectRaw('IFNULL(SUM(servers.memory), 0) as sum_memory, IFNULL(SUM(servers.disk), 0) as sum_disk')\n            ->leftJoin('servers', 'servers.node_id', '=', 'nodes.id')\n            ->where('nodes.id', $node_id);\n\n        return $instance->first();\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/PermissionRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Contracts\\Repository\\PermissionRepositoryInterface;\n\nclass PermissionRepository extends EloquentRepository implements PermissionRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     *\n     * @throws \\Exception\n     */\n    public function model(): string\n    {\n        throw new \\Exception('This functionality is not implemented.');\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/RecoveryTokenRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\RecoveryToken;\n\nclass RecoveryTokenRepository extends EloquentRepository\n{\n    public function model(): string\n    {\n        return RecoveryToken::class;\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/ScheduleRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Schedule;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\nuse Pterodactyl\\Contracts\\Repository\\ScheduleRepositoryInterface;\n\nclass ScheduleRepository extends EloquentRepository implements ScheduleRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Schedule::class;\n    }\n\n    /**\n     * Return all the schedules for a given server.\n     */\n    public function findServerSchedules(int $server): Collection\n    {\n        return $this->getBuilder()->withCount('tasks')->where('server_id', '=', $server)->get($this->getColumns());\n    }\n\n    /**\n     * Return a schedule model with all the associated tasks as a relationship.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getScheduleWithTasks(int $schedule): Schedule\n    {\n        try {\n            return $this->getBuilder()->with('tasks')->findOrFail($schedule, $this->getColumns());\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/ServerRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Database\\Eloquent\\Builder;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Illuminate\\Contracts\\Pagination\\LengthAwarePaginator;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\nuse Pterodactyl\\Contracts\\Repository\\ServerRepositoryInterface;\n\nclass ServerRepository extends EloquentRepository implements ServerRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Server::class;\n    }\n\n    /**\n     * Load the egg relations onto the server model.\n     */\n    public function loadEggRelations(Server $server, bool $refresh = false): Server\n    {\n        if (!$server->relationLoaded('egg') || $refresh) {\n            $server->load('egg.scriptFrom');\n        }\n\n        return $server;\n    }\n\n    /**\n     * Return a collection of servers with their associated data for rebuild operations.\n     */\n    public function getDataForRebuild(?int $server = null, ?int $node = null): Collection\n    {\n        $instance = $this->getBuilder()->with(['allocation', 'allocations', 'egg', 'node']);\n\n        if (!is_null($server) && is_null($node)) {\n            $instance = $instance->where('id', '=', $server);\n        } elseif (is_null($server) && !is_null($node)) {\n            $instance = $instance->where('node_id', '=', $node);\n        }\n\n        return $instance->get($this->getColumns());\n    }\n\n    /**\n     * Return a collection of servers with their associated data for reinstall operations.\n     */\n    public function getDataForReinstall(?int $server = null, ?int $node = null): Collection\n    {\n        $instance = $this->getBuilder()->with(['allocation', 'allocations', 'egg', 'node']);\n\n        if (!is_null($server) && is_null($node)) {\n            $instance = $instance->where('id', '=', $server);\n        } elseif (is_null($server) && !is_null($node)) {\n            $instance = $instance->where('node_id', '=', $node);\n        }\n\n        return $instance->get($this->getColumns());\n    }\n\n    /**\n     * Return a server model and all variables associated with the server.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function findWithVariables(int $id): Server\n    {\n        try {\n            return $this->getBuilder()->with('egg.variables', 'variables')\n                ->where($this->getModel()->getKeyName(), '=', $id)\n                ->firstOrFail($this->getColumns());\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n\n    /**\n     * Get the primary allocation for a given server. If a model is passed into\n     * the function, load the allocation relationship onto it. Otherwise, find and\n     * return the server from the database.\n     */\n    public function getPrimaryAllocation(Server $server, bool $refresh = false): Server\n    {\n        if (!$server->relationLoaded('allocation') || $refresh) {\n            $server->load('allocation');\n        }\n\n        return $server;\n    }\n\n    /**\n     * Return enough data to be used for the creation of a server via the daemon.\n     */\n    public function getDataForCreation(Server $server, bool $refresh = false): Server\n    {\n        foreach (['allocation', 'allocations', 'egg'] as $relation) {\n            if (!$server->relationLoaded($relation) || $refresh) {\n                $server->load($relation);\n            }\n        }\n\n        return $server;\n    }\n\n    /**\n     * Load associated databases onto the server model.\n     */\n    public function loadDatabaseRelations(Server $server, bool $refresh = false): Server\n    {\n        if (!$server->relationLoaded('databases') || $refresh) {\n            $server->load('databases.host');\n        }\n\n        return $server;\n    }\n\n    /**\n     * Get data for use when updating a server on the Daemon. Returns an array of\n     * the egg which is used for build and rebuild. Only loads relations\n     * if they are missing, or refresh is set to true.\n     */\n    public function getDaemonServiceData(Server $server, bool $refresh = false): array\n    {\n        if (!$server->relationLoaded('egg') || $refresh) {\n            $server->load('egg');\n        }\n\n        return [\n            'egg' => $server->getRelation('egg')->uuid,\n        ];\n    }\n\n    /**\n     * Return a server by UUID.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getByUuid(string $uuid): Server\n    {\n        try {\n            /** @var Server $model */\n            $model = $this->getBuilder()\n                ->with('nest', 'node')\n                ->where(function (Builder $query) use ($uuid) {\n                    $query->where('uuidShort', $uuid)->orWhere('uuid', $uuid);\n                })\n                ->firstOrFail($this->getColumns());\n\n            return $model;\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n\n    /**\n     * Check if a given UUID and UUID-Short string are unique to a server.\n     */\n    public function isUniqueUuidCombo(string $uuid, string $short): bool\n    {\n        return !$this->getBuilder()->where('uuid', '=', $uuid)->orWhere('uuidShort', '=', $short)->exists();\n    }\n\n    /**\n     * Returns all the servers that exist for a given node in a paginated response.\n     */\n    public function loadAllServersForNode(int $node, int $limit): LengthAwarePaginator\n    {\n        return $this->getBuilder()\n            ->with(['user', 'nest', 'egg'])\n            ->where('node_id', '=', $node)\n            ->paginate($limit);\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/ServerVariableRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\ServerVariable;\nuse Pterodactyl\\Contracts\\Repository\\ServerVariableRepositoryInterface;\n\nclass ServerVariableRepository extends EloquentRepository implements ServerVariableRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return ServerVariable::class;\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/SessionRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Session;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Contracts\\Repository\\SessionRepositoryInterface;\n\nclass SessionRepository extends EloquentRepository implements SessionRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Session::class;\n    }\n\n    /**\n     * Return all the active sessions for a user.\n     */\n    public function getUserSessions(int $user): Collection\n    {\n        return $this->getBuilder()->where('user_id', $user)->get($this->getColumns());\n    }\n\n    /**\n     * Delete a session for a given user.\n     */\n    public function deleteUserSession(int $user, string $session): ?int\n    {\n        return $this->getBuilder()->where('user_id', $user)->where('id', $session)->delete();\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/SettingsRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Setting;\nuse Pterodactyl\\Contracts\\Repository\\SettingsRepositoryInterface;\n\nclass SettingsRepository extends EloquentRepository implements SettingsRepositoryInterface\n{\n    private static array $cache = [];\n\n    private static array $databaseMiss = [];\n\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Setting::class;\n    }\n\n    /**\n     * Store a new persistent setting in the database.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function set(string $key, ?string $value = null)\n    {\n        // Clear item from the cache.\n        $this->clearCache($key);\n        $this->withoutFreshModel()->updateOrCreate(['key' => $key], ['value' => $value ?? '']);\n\n        self::$cache[$key] = $value;\n    }\n\n    /**\n     * Retrieve a persistent setting from the database.\n     */\n    public function get(string $key, mixed $default = null): mixed\n    {\n        // If item has already been requested return it from the cache. If\n        // we already know it is missing, immediately return the default value.\n        if (array_key_exists($key, self::$cache)) {\n            return self::$cache[$key];\n        } elseif (array_key_exists($key, self::$databaseMiss)) {\n            return value($default);\n        }\n\n        $instance = $this->getBuilder()->where('key', $key)->first();\n        if (is_null($instance)) {\n            self::$databaseMiss[$key] = true;\n\n            return value($default);\n        }\n\n        return self::$cache[$key] = $instance->value;\n    }\n\n    /**\n     * Remove a key from the database cache.\n     */\n    public function forget(string $key)\n    {\n        $this->clearCache($key);\n        $this->deleteWhere(['key' => $key]);\n    }\n\n    /**\n     * Remove a key from the cache.\n     */\n    private function clearCache(string $key)\n    {\n        unset(self::$cache[$key], self::$databaseMiss[$key]);\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/SubuserRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\nuse Pterodactyl\\Contracts\\Repository\\SubuserRepositoryInterface;\n\nclass SubuserRepository extends EloquentRepository implements SubuserRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Subuser::class;\n    }\n\n    /**\n     * Return a subuser with the associated server relationship.\n     */\n    public function loadServerAndUserRelations(Subuser $subuser, bool $refresh = false): Subuser\n    {\n        if (!$subuser->relationLoaded('server') || $refresh) {\n            $subuser->load('server');\n        }\n\n        if (!$subuser->relationLoaded('user') || $refresh) {\n            $subuser->load('user');\n        }\n\n        return $subuser;\n    }\n\n    /**\n     * Return a subuser with the associated permissions relationship.\n     */\n    public function getWithPermissions(Subuser $subuser, bool $refresh = false): Subuser\n    {\n        if (!$subuser->relationLoaded('permissions') || $refresh) {\n            $subuser->load('permissions');\n        }\n\n        if (!$subuser->relationLoaded('user') || $refresh) {\n            $subuser->load('user');\n        }\n\n        return $subuser;\n    }\n\n    /**\n     * Return a subuser and associated permissions given a user_id and server_id.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getWithPermissionsUsingUserAndServer(int $user, int $server): Subuser\n    {\n        $instance = $this->getBuilder()->with('permissions')->where([\n            ['user_id', '=', $user],\n            ['server_id', '=', $server],\n        ])->first();\n\n        if (is_null($instance)) {\n            throw new RecordNotFoundException();\n        }\n\n        return $instance;\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/TaskRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\Task;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Pterodactyl\\Contracts\\Repository\\TaskRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\n\nclass TaskRepository extends EloquentRepository implements TaskRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return Task::class;\n    }\n\n    /**\n     * Get a task and the server relationship for that task.\n     *\n     * @throws RecordNotFoundException\n     */\n    public function getTaskForJobProcess(int $id): Task\n    {\n        try {\n            return $this->getBuilder()->with('server.user', 'schedule')->findOrFail($id, $this->getColumns());\n        } catch (ModelNotFoundException) {\n            throw new RecordNotFoundException();\n        }\n    }\n\n    /**\n     * Returns the next task in a schedule.\n     */\n    public function getNextTask(int $schedule, int $index): ?Task\n    {\n        return $this->getBuilder()->where('schedule_id', '=', $schedule)\n            ->orderBy('sequence_id')\n            ->where('sequence_id', '>', $index)\n            ->first($this->getColumns());\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Eloquent/UserRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Eloquent;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Contracts\\Repository\\UserRepositoryInterface;\n\nclass UserRepository extends EloquentRepository implements UserRepositoryInterface\n{\n    /**\n     * Return the model backing this repository.\n     */\n    public function model(): string\n    {\n        return User::class;\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Repository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories;\n\nuse Illuminate\\Foundation\\Application;\nuse Illuminate\\Database\\Eloquent\\Model;\nuse Pterodactyl\\Contracts\\Repository\\RepositoryInterface;\n\nabstract class Repository implements RepositoryInterface\n{\n    protected array $columns = ['*'];\n\n    protected Model $model;\n\n    protected bool $withFresh = true;\n\n    /**\n     * Repository constructor.\n     */\n    public function __construct(protected Application $app)\n    {\n        $this->initializeModel($this->model());\n    }\n\n    /**\n     * Return the model backing this repository.\n     */\n    abstract public function model(): string;\n\n    /**\n     * Return the model being used for this repository.\n     */\n    public function getModel(): Model\n    {\n        return $this->model;\n    }\n\n    /**\n     * Setup column selection functionality.\n     *\n     * @param array|string $columns\n     */\n    public function setColumns($columns = ['*']): self\n    {\n        $clone = clone $this;\n        $clone->columns = is_array($columns) ? $columns : func_get_args();\n\n        return $clone;\n    }\n\n    /**\n     * Return the columns to be selected in the repository call.\n     */\n    public function getColumns(): array\n    {\n        return $this->columns;\n    }\n\n    /**\n     * Stop repository update functions from returning a fresh\n     * model when changes are committed.\n     */\n    public function withoutFreshModel(): self\n    {\n        return $this->setFreshModel(false);\n    }\n\n    /**\n     * Return a fresh model with a repository updates a model.\n     */\n    public function withFreshModel(): self\n    {\n        return $this->setFreshModel();\n    }\n\n    /**\n     * Set whether the repository should return a fresh model\n     * when changes are committed.\n     */\n    public function setFreshModel(bool $fresh = true): self\n    {\n        $clone = clone $this;\n        $clone->withFresh = $fresh;\n\n        return $clone;\n    }\n\n    /**\n     * Take the provided model and make it accessible to the rest of the repository.\n     */\n    protected function initializeModel(string ...$model): mixed\n    {\n        switch (count($model)) {\n            case 1:\n                return $this->model = $this->app->make($model[0]);\n            case 2:\n                return $this->model = call_user_func([$this->app->make($model[0]), $model[1]]);\n            default:\n                throw new \\InvalidArgumentException('Model must be a FQDN or an array with a count of two.');\n        }\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Wings/DaemonBackupRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Wings;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Backup;\nuse Pterodactyl\\Models\\Server;\nuse Psr\\Http\\Message\\ResponseInterface;\nuse GuzzleHttp\\Exception\\TransferException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\n/**\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonBackupRepository setNode(\\Pterodactyl\\Models\\Node $node)\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonBackupRepository setServer(\\Pterodactyl\\Models\\Server $server)\n */\nclass DaemonBackupRepository extends DaemonRepository\n{\n    protected ?string $adapter;\n\n    /**\n     * Sets the backup adapter for this execution instance.\n     */\n    public function setBackupAdapter(string $adapter): self\n    {\n        $this->adapter = $adapter;\n\n        return $this;\n    }\n\n    /**\n     * Tells the remote Daemon to begin generating a backup for the server.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function backup(Backup $backup): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/backup', $this->server->uuid),\n                [\n                    'json' => [\n                        'adapter' => $this->adapter ?? config('backups.default'),\n                        'uuid' => $backup->uuid,\n                        'ignore' => implode(\"\\n\", $backup->ignored_files),\n                    ],\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Sends a request to Wings to begin restoring a backup for a server.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function restore(Backup $backup, ?string $url = null, bool $truncate = false): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/backup/%s/restore', $this->server->uuid, $backup->uuid),\n                [\n                    'json' => [\n                        'adapter' => $backup->disk,\n                        'truncate_directory' => $truncate,\n                        'download_url' => $url ?? '',\n                    ],\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Deletes a backup from the daemon.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function delete(Backup $backup): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->delete(\n                sprintf('/api/servers/%s/backup/%s', $this->server->uuid, $backup->uuid)\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Wings/DaemonCommandRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Wings;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Psr\\Http\\Message\\ResponseInterface;\nuse GuzzleHttp\\Exception\\TransferException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\n/**\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonCommandRepository setNode(\\Pterodactyl\\Models\\Node $node)\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonCommandRepository setServer(\\Pterodactyl\\Models\\Server $server)\n */\nclass DaemonCommandRepository extends DaemonRepository\n{\n    /**\n     * Sends a command or multiple commands to a running server instance.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function send(array|string $command): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/commands', $this->server->uuid),\n                [\n                    'json' => ['commands' => is_array($command) ? $command : [$command]],\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Wings/DaemonConfigurationRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Wings;\n\nuse Pterodactyl\\Models\\Node;\nuse Psr\\Http\\Message\\ResponseInterface;\nuse GuzzleHttp\\Exception\\TransferException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\n/**\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonConfigurationRepository setNode(\\Pterodactyl\\Models\\Node $node)\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonConfigurationRepository setServer(\\Pterodactyl\\Models\\Server $server)\n */\nclass DaemonConfigurationRepository extends DaemonRepository\n{\n    /**\n     * Returns system information from the wings instance.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function getSystemInformation(?int $version = null): array\n    {\n        try {\n            $response = $this->getHttpClient()->get('/api/system' . (!is_null($version) ? '?v=' . $version : ''));\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n\n        return json_decode($response->getBody()->__toString(), true);\n    }\n\n    /**\n     * Updates the configuration information for a daemon. Updates the information for\n     * this instance using a passed-in model. This allows us to change plenty of information\n     * in the model, and still use the old, pre-update model to actually make the HTTP request.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function update(Node $node): ResponseInterface\n    {\n        try {\n            return $this->getHttpClient()->post(\n                '/api/update',\n                ['json' => $node->getConfiguration()]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Wings/DaemonFileRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Wings;\n\nuse Illuminate\\Support\\Arr;\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Psr\\Http\\Message\\ResponseInterface;\nuse GuzzleHttp\\Exception\\ClientException;\nuse GuzzleHttp\\Exception\\TransferException;\nuse Pterodactyl\\Exceptions\\Http\\Server\\FileSizeTooLargeException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\n/**\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonFileRepository setNode(\\Pterodactyl\\Models\\Node $node)\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonFileRepository setServer(\\Pterodactyl\\Models\\Server $server)\n */\nclass DaemonFileRepository extends DaemonRepository\n{\n    /**\n     * Return the contents of a given file.\n     *\n     * @param int|null $notLargerThan the maximum content length in bytes\n     *\n     * @throws TransferException\n     * @throws FileSizeTooLargeException\n     * @throws DaemonConnectionException\n     */\n    public function getContent(string $path, ?int $notLargerThan = null): string\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            $response = $this->getHttpClient()->get(\n                sprintf('/api/servers/%s/files/contents', $this->server->uuid),\n                [\n                    'query' => ['file' => $path],\n                ]\n            );\n        } catch (ClientException|TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n\n        $length = (int) Arr::get($response->getHeader('Content-Length'), 0, 0);\n        if ($notLargerThan && $length > $notLargerThan) {\n            throw new FileSizeTooLargeException();\n        }\n\n        return $response->getBody()->__toString();\n    }\n\n    /**\n     * Save new contents to a given file. This works for both creating and updating\n     * a file.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function putContent(string $path, string $content): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/files/write', $this->server->uuid),\n                [\n                    'query' => ['file' => $path],\n                    'body' => $content,\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Return a directory listing for a given path.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function getDirectory(string $path): array\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            $response = $this->getHttpClient()->get(\n                sprintf('/api/servers/%s/files/list-directory', $this->server->uuid),\n                [\n                    'query' => ['directory' => $path],\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n\n        return json_decode($response->getBody(), true);\n    }\n\n    /**\n     * Creates a new directory for the server in the given $path.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function createDirectory(string $name, string $path): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/files/create-directory', $this->server->uuid),\n                [\n                    'json' => [\n                        'name' => $name,\n                        'path' => $path,\n                    ],\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Renames or moves a file on the remote machine.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function renameFiles(?string $root, array $files): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->put(\n                sprintf('/api/servers/%s/files/rename', $this->server->uuid),\n                [\n                    'json' => [\n                        'root' => $root ?? '/',\n                        'files' => $files,\n                    ],\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Copy a given file and give it a unique name.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function copyFile(string $location): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/files/copy', $this->server->uuid),\n                [\n                    'json' => [\n                        'location' => $location,\n                    ],\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Delete a file or folder for the server.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function deleteFiles(?string $root, array $files): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/files/delete', $this->server->uuid),\n                [\n                    'json' => [\n                        'root' => $root ?? '/',\n                        'files' => $files,\n                    ],\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Compress the given files or folders in the given root.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function compressFiles(?string $root, array $files): array\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            $response = $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/files/compress', $this->server->uuid),\n                [\n                    'json' => [\n                        'root' => $root ?? '/',\n                        'files' => $files,\n                    ],\n                    // Wait for up to 15 minutes for the archive to be completed when calling this endpoint\n                    // since it will likely take quite awhile for large directories.\n                    'timeout' => 60 * 15,\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n\n        return json_decode($response->getBody(), true);\n    }\n\n    /**\n     * Decompresses a given archive file.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function decompressFile(?string $root, string $file): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/files/decompress', $this->server->uuid),\n                [\n                    'json' => [\n                        'root' => $root ?? '/',\n                        'file' => $file,\n                    ],\n                    // Wait for up to 15 minutes for the decompress to be completed when calling this endpoint\n                    // since it will likely take quite awhile for large directories.\n                    'timeout' => 60 * 15,\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Chmods the given files.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function chmodFiles(?string $root, array $files): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/files/chmod', $this->server->uuid),\n                [\n                    'json' => [\n                        'root' => $root ?? '/',\n                        'files' => $files,\n                    ],\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Pulls a file from the given URL and saves it to the disk.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function pull(string $url, ?string $directory, array $params = []): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        $attributes = [\n            'url' => $url,\n            'root' => $directory ?? '/',\n            'file_name' => $params['filename'] ?? null,\n            'use_header' => $params['use_header'] ?? null,\n            'foreground' => $params['foreground'] ?? null,\n        ];\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/files/pull', $this->server->uuid),\n                [\n                    'json' => array_filter($attributes, fn ($value) => !is_null($value)),\n                ]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Wings/DaemonPowerRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Wings;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Psr\\Http\\Message\\ResponseInterface;\nuse GuzzleHttp\\Exception\\TransferException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\n/**\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonPowerRepository setNode(\\Pterodactyl\\Models\\Node $node)\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonPowerRepository setServer(\\Pterodactyl\\Models\\Server $server)\n */\nclass DaemonPowerRepository extends DaemonRepository\n{\n    /**\n     * Sends a power action to the server instance.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function send(string $action): ResponseInterface\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            return $this->getHttpClient()->post(\n                sprintf('/api/servers/%s/power', $this->server->uuid),\n                ['json' => ['action' => $action]]\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Wings/DaemonRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Wings;\n\nuse GuzzleHttp\\Client;\nuse Pterodactyl\\Models\\Node;\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Contracts\\Foundation\\Application;\n\nabstract class DaemonRepository\n{\n    protected ?Server $server;\n\n    protected ?Node $node;\n\n    /**\n     * DaemonRepository constructor.\n     */\n    public function __construct(protected Application $app)\n    {\n    }\n\n    /**\n     * Set the server model this request is stemming from.\n     */\n    public function setServer(Server $server): self\n    {\n        $this->server = $server;\n\n        $this->setNode($this->server->node);\n\n        return $this;\n    }\n\n    /**\n     * Set the node model this request is stemming from.\n     */\n    public function setNode(Node $node): self\n    {\n        $this->node = $node;\n\n        return $this;\n    }\n\n    /**\n     * Return an instance of the Guzzle HTTP Client to be used for requests.\n     */\n    public function getHttpClient(array $headers = []): Client\n    {\n        Assert::isInstanceOf($this->node, Node::class);\n\n        return new Client([\n            'verify' => $this->app->environment('production'),\n            'base_uri' => $this->node->getConnectionAddress(),\n            'timeout' => config('pterodactyl.guzzle.timeout'),\n            'connect_timeout' => config('pterodactyl.guzzle.connect_timeout'),\n            'headers' => array_merge($headers, [\n                'Authorization' => 'Bearer ' . $this->node->getDecryptedKey(),\n                'Accept' => 'application/json',\n                'Content-Type' => 'application/json',\n            ]),\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Wings/DaemonRevocationRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Wings;\n\nuse GuzzleHttp\\Exception\\TransferException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass DaemonRevocationRepository extends DaemonRepository\n{\n    /**\n     * Deauthorizes a user (disconnects websockets and SFTP) on the Wings instance for\n     * the provided servers. If no servers are provided, the user is deauthorized on all\n     * servers on the instance.\n     *\n     * @param string[] $servers\n     */\n    public function deauthorize(string $user, array $servers = []): void\n    {\n        try {\n            $this->getHttpClient()->post('/api/deauthorize-user', [\n                'json' => ['user' => $user, 'servers' => $servers],\n            ]);\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Wings/DaemonServerRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Wings;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse GuzzleHttp\\Exception\\GuzzleException;\nuse GuzzleHttp\\Exception\\TransferException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\n/**\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonServerRepository setNode(\\Pterodactyl\\Models\\Node $node)\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonServerRepository setServer(\\Pterodactyl\\Models\\Server $server)\n */\nclass DaemonServerRepository extends DaemonRepository\n{\n    /**\n     * Returns details about a server from the Daemon instance.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function getDetails(): array\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            $response = $this->getHttpClient()->get(\n                sprintf('/api/servers/%s', $this->server->uuid)\n            );\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception, false);\n        }\n\n        return json_decode($response->getBody()->__toString(), true);\n    }\n\n    /**\n     * Creates a new server on the Wings daemon.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function create(bool $startOnCompletion = true): void\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            $this->getHttpClient()->post('/api/servers', [\n                'json' => [\n                    'uuid' => $this->server->uuid,\n                    'start_on_completion' => $startOnCompletion,\n                ],\n            ]);\n        } catch (GuzzleException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Triggers a server sync on Wings.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function sync(): void\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            $this->getHttpClient()->post(\"/api/servers/{$this->server->uuid}/sync\");\n        } catch (GuzzleException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Delete a server from the daemon, forcibly if passed.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function delete(): void\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            $this->getHttpClient()->delete('/api/servers/' . $this->server->uuid);\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Reinstall a server on the daemon.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function reinstall(): void\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            $this->getHttpClient()->post(sprintf(\n                '/api/servers/%s/reinstall',\n                $this->server->uuid\n            ));\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Requests the daemon to create a full archive of the server. Once the daemon is finished\n     * they will send a POST request to \"/api/remote/servers/{uuid}/archive\" with a boolean.\n     *\n     * @throws DaemonConnectionException\n     */\n    public function requestArchive(): void\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            $this->getHttpClient()->post(sprintf(\n                '/api/servers/%s/archive',\n                $this->server->uuid\n            ));\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n\n    /**\n     * Revokes a single user's JTI by using their ID. This is simply a helper function to\n     * make it easier to revoke tokens on the fly. This ensures that the JTI key is formatted\n     * correctly and avoids any costly mistakes in the codebase.\n     *\n     * @deprecated\n     * @see \\Pterodactyl\\Repositories\\Wings\\DaemonRevocationRepository::deauthorize()\n     *\n     * @throws DaemonConnectionException\n     */\n    public function revokeUserJTI(int $id): void\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        $this->revokeJTIs([md5($id . $this->server->uuid)]);\n    }\n\n    /**\n     * Revokes an array of JWT JTI's by marking any token generated before the current time on\n     * the Wings instance as being invalid.\n     *\n     * @throws DaemonConnectionException\n     */\n    protected function revokeJTIs(array $jtis): void\n    {\n        Assert::isInstanceOf($this->server, Server::class);\n\n        try {\n            $this->getHttpClient()\n                ->post(sprintf('/api/servers/%s/ws/deny', $this->server->uuid), [\n                    'json' => ['jtis' => $jtis],\n                ]);\n        } catch (TransferException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Repositories/Wings/DaemonTransferRepository.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Repositories\\Wings;\n\nuse Pterodactyl\\Models\\Node;\nuse Lcobucci\\JWT\\Token\\Plain;\nuse GuzzleHttp\\Exception\\GuzzleException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\n/**\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonTransferRepository setNode(\\Pterodactyl\\Models\\Node $node)\n * @method \\Pterodactyl\\Repositories\\Wings\\DaemonTransferRepository setServer(\\Pterodactyl\\Models\\Server $server)\n */\nclass DaemonTransferRepository extends DaemonRepository\n{\n    /**\n     * @throws DaemonConnectionException\n     */\n    public function notify(Node $targetNode, Plain $token): void\n    {\n        try {\n            $this->getHttpClient()->post(sprintf('/api/servers/%s/transfer', $this->server->uuid), [\n                'json' => [\n                    'server_id' => $this->server->uuid,\n                    'url' => $targetNode->getConnectionAddress() . '/api/transfers',\n                    'token' => 'Bearer ' . $token->toString(),\n                    'server' => [\n                        'uuid' => $this->server->uuid,\n                        'start_on_completion' => false,\n                    ],\n                ],\n            ]);\n        } catch (GuzzleException $exception) {\n            throw new DaemonConnectionException($exception);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Rules/Fqdn.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Rules;\n\nuse Illuminate\\Support\\Arr;\nuse Illuminate\\Contracts\\Validation\\Rule;\nuse Illuminate\\Contracts\\Validation\\DataAwareRule;\n\nclass Fqdn implements Rule, DataAwareRule\n{\n    protected array $data = [];\n    protected string $message = '';\n    protected ?string $schemeField = null;\n\n    /**\n     * @param array $data\n     */\n    public function setData($data): self\n    {\n        $this->data = $data;\n\n        return $this;\n    }\n\n    /**\n     * Validates that the value provided resolves to an IP address. If a scheme is\n     * specified when this rule is created additional checks will be applied.\n     *\n     * @param string $attribute\n     */\n    public function passes($attribute, $value): bool\n    {\n        if (filter_var($value, FILTER_VALIDATE_IP)) {\n            // Check if the scheme is set to HTTPS.\n            //\n            // Unless someone owns their IP blocks and decides to pay who knows how much for a\n            // custom SSL cert, IPs will not be able to use HTTPS.  This should prevent most\n            // home users from making this mistake and wondering why their node is not working.\n            if ($this->schemeField && Arr::get($this->data, $this->schemeField) === 'https') {\n                $this->message = '启用 HTTPS 时 :attribute 不能是 IP 地址。';\n\n                return false;\n            }\n\n            return true;\n        }\n\n        // Lookup A and AAAA DNS records for the FQDN. Note, this function will also resolve CNAMEs\n        // for us automatically, there is no need to manually resolve them here.\n        //\n        // The error suppression is intentional, see https://bugs.php.net/bug.php?id=73149\n        $records = @dns_get_record($value, DNS_A + DNS_AAAA);\n        // If no records were returned fall back to trying to resolve the value using the hosts DNS\n        // resolution. This will not work for IPv6 which is why we prefer to use `dns_get_record`\n        // first.\n        if (!empty($records) || filter_var(gethostbyname($value), FILTER_VALIDATE_IP)) {\n            return true;\n        }\n\n        $this->message = ':attribute 无法解析为有效的 IP 地址。';\n\n        return false;\n    }\n\n    public function message(): string\n    {\n        return $this->message;\n    }\n\n    /**\n     * Returns a new instance of the rule with a defined scheme set.\n     */\n    public static function make(?string $schemeField = null): self\n    {\n        return tap(new self(), function ($fqdn) use ($schemeField) {\n            $fqdn->schemeField = $schemeField;\n        });\n    }\n}\n"
  },
  {
    "path": "app/Rules/Username.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Rules;\n\nuse Illuminate\\Contracts\\Validation\\Rule;\n\nclass Username implements Rule\n{\n    /**\n     * Regex to use when validating usernames.\n     */\n    public const VALIDATION_REGEX = '/^[a-z0-9]([\\w\\.-]+)[a-z0-9]$/';\n\n    /**\n     * Validate that a username contains only the allowed characters and starts/ends\n     * with alphanumeric characters.\n     *\n     * Allowed characters: a-z0-9_-.\n     *\n     * @param string $attribute\n     */\n    public function passes($attribute, $value): bool\n    {\n        return preg_match(self::VALIDATION_REGEX, mb_strtolower($value));\n    }\n\n    /**\n     * Return a validation message for use when this rule fails.\n     */\n    public function message(): string\n    {\n        return ':attribute 只能以字母或数字开头和结尾，且只能包含字母、数字、破折号、下划线和英文句号。';\n    }\n\n    /**\n     * Convert the rule to a validation string. This is necessary to avoid\n     * issues with Eloquence which tries to use this rule as a string.\n     */\n    public function __toString(): string\n    {\n        return 'p_username';\n    }\n}\n"
  },
  {
    "path": "app/Services/Acl/Api/AdminAcl.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Acl\\Api;\n\nuse Pterodactyl\\Models\\ApiKey;\n\nclass AdminAcl\n{\n    /**\n     * Resource permission columns in the api_keys table begin\n     * with this identifier.\n     */\n    public const COLUMN_IDENTIFIER = 'r_';\n\n    /**\n     * The different types of permissions available for API keys. This\n     * implements a read/write/none permissions scheme for all endpoints.\n     */\n    public const NONE = 0;\n    public const READ = 1;\n    public const WRITE = 2;\n\n    /**\n     * Resources that are available on the API and can contain a permissions\n     * set for each key. These are stored in the database as r_{resource}.\n     */\n    public const RESOURCE_SERVERS = 'servers';\n    public const RESOURCE_NODES = 'nodes';\n    public const RESOURCE_ALLOCATIONS = 'allocations';\n    public const RESOURCE_USERS = 'users';\n    public const RESOURCE_LOCATIONS = 'locations';\n    public const RESOURCE_NESTS = 'nests';\n    public const RESOURCE_EGGS = 'eggs';\n    public const RESOURCE_DATABASE_HOSTS = 'database_hosts';\n    public const RESOURCE_SERVER_DATABASES = 'server_databases';\n\n    /**\n     * Determine if an API key has permission to perform a specific read/write operation.\n     */\n    public static function can(int $permission, int $action = self::READ): bool\n    {\n        if ($permission & $action) {\n            return true;\n        }\n\n        return false;\n    }\n\n    /**\n     * Determine if an API Key model has permission to access a given resource\n     * at a specific action level.\n     */\n    public static function check(ApiKey $key, string $resource, int $action = self::READ): bool\n    {\n        return self::can(data_get($key, self::COLUMN_IDENTIFIER . $resource, self::NONE), $action);\n    }\n\n    /**\n     * Return a list of all resource constants defined in this ACL.\n     *\n     * @throws \\ReflectionException\n     */\n    public static function getResourceList(): array\n    {\n        $reflect = new \\ReflectionClass(__CLASS__);\n\n        return collect($reflect->getConstants())->filter(function ($value, $key) {\n            return substr($key, 0, 9) === 'RESOURCE_';\n        })->values()->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Services/Activity/ActivityLogBatchService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Activity;\n\nuse Ramsey\\Uuid\\Uuid;\n\nclass ActivityLogBatchService\n{\n    protected int $transaction = 0;\n    protected ?string $uuid = null;\n\n    /**\n     * Returns the UUID of the batch, or null if there is not a batch currently\n     * being executed.\n     */\n    public function uuid(): ?string\n    {\n        return $this->uuid;\n    }\n\n    /**\n     * Starts a new batch transaction. If there is already a transaction present\n     * this will be nested.\n     */\n    public function start(): void\n    {\n        if ($this->transaction === 0) {\n            $this->uuid = Uuid::uuid4()->toString();\n        }\n\n        ++$this->transaction;\n    }\n\n    /**\n     * Ends a batch transaction, if this is the last transaction in the stack\n     * the UUID will be cleared out.\n     */\n    public function end(): void\n    {\n        $this->transaction = max(0, $this->transaction - 1);\n\n        if ($this->transaction === 0) {\n            $this->uuid = null;\n        }\n    }\n\n    /**\n     * Executes the logic provided within the callback in the scope of an activity\n     * log batch transaction.\n     */\n    public function transaction(\\Closure $callback): mixed\n    {\n        $this->start();\n        $result = $callback($this->uuid());\n        $this->end();\n\n        return $result;\n    }\n}\n"
  },
  {
    "path": "app/Services/Activity/ActivityLogService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Activity;\n\nuse Illuminate\\Support\\Arr;\nuse Webmozart\\Assert\\Assert;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Support\\Facades\\Log;\nuse Pterodactyl\\Models\\ActivityLog;\nuse Illuminate\\Database\\Eloquent\\Model;\nuse Illuminate\\Support\\Facades\\Request;\nuse Pterodactyl\\Models\\ActivityLogSubject;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Illuminate\\Contracts\\Auth\\Factory as AuthFactory;\n\nclass ActivityLogService\n{\n    protected ?ActivityLog $activity = null;\n\n    protected array $subjects = [];\n\n    public function __construct(\n        protected AuthFactory $manager,\n        protected ActivityLogBatchService $batch,\n        protected ActivityLogTargetableService $targetable,\n        protected ConnectionInterface $connection,\n    ) {\n    }\n\n    /**\n     * Sets the activity logger as having been caused by an anonymous\n     * user type.\n     */\n    public function anonymous(): self\n    {\n        $this->getActivity()->actor_id = null;\n        $this->getActivity()->actor_type = null;\n        $this->getActivity()->setRelation('actor', null);\n\n        return $this;\n    }\n\n    /**\n     * Sets the action for this activity log.\n     */\n    public function event(string $action): self\n    {\n        $this->getActivity()->event = $action;\n\n        return $this;\n    }\n\n    /**\n     * Set the description for this activity.\n     */\n    public function description(?string $description): self\n    {\n        $this->getActivity()->description = $description;\n\n        return $this;\n    }\n\n    /**\n     * Sets the subject model instance.\n     *\n     * @template T extends \\Illuminate\\Database\\Eloquent\\Model|\\Illuminate\\Contracts\\Auth\\Authenticatable\n     *\n     * @param T|T[]|null $subjects\n     */\n    public function subject(...$subjects): self\n    {\n        foreach (Arr::wrap($subjects) as $subject) {\n            if (is_null($subject)) {\n                continue;\n            }\n\n            foreach ($this->subjects as $entry) {\n                // If this subject is already tracked in our array of subjects just skip over\n                // it and move on to the next one in the list.\n                if ($entry->is($subject)) {\n                    continue 2;\n                }\n            }\n\n            $this->subjects[] = $subject;\n        }\n\n        return $this;\n    }\n\n    /**\n     * Sets the actor model instance.\n     */\n    public function actor(Model $actor): self\n    {\n        $this->getActivity()->actor()->associate($actor);\n\n        return $this;\n    }\n\n    /**\n     * Sets a custom property on the activity log instance.\n     *\n     * @param string|array $key\n     */\n    public function property($key, $value = null): self\n    {\n        $properties = $this->getActivity()->properties;\n        $this->activity->properties = is_array($key)\n            ? $properties->merge($key)\n            : $properties->put($key, $value);\n\n        return $this;\n    }\n\n    /**\n     * Attaches the instance request metadata to the activity log event.\n     */\n    public function withRequestMetadata(): self\n    {\n        return $this->property([\n            'ip' => Request::getClientIp(),\n            'useragent' => Request::userAgent(),\n        ]);\n    }\n\n    /**\n     * Logs an activity log entry with the set values and then returns the\n     * model instance to the caller. If there is an exception encountered while\n     * performing this action it will be logged to the disk but will not interrupt\n     * the code flow.\n     */\n    public function log(?string $description = null): ActivityLog\n    {\n        $activity = $this->getActivity();\n\n        if (!is_null($description)) {\n            $activity->description = $description;\n        }\n\n        try {\n            return $this->save();\n        } catch (\\Throwable $exception) {\n            if (config('app.env') !== 'production') {\n                /* @noinspection PhpUnhandledExceptionInspection */\n                throw $exception;\n            }\n\n            Log::error($exception);\n        }\n\n        return $activity;\n    }\n\n    /**\n     * Returns a cloned instance of the service allowing for the creation of a base\n     * activity log with the ability to change values on the fly without impact.\n     */\n    public function clone(): self\n    {\n        return clone $this;\n    }\n\n    /**\n     * Executes the provided callback within the scope of a database transaction\n     * and will only save the activity log entry if everything else successfully\n     * settles.\n     *\n     * @param \\Closure($this): mixed $callback\n     *\n     * @throws \\Throwable\n     */\n    public function transaction(\\Closure $callback)\n    {\n        return $this->connection->transaction(function () use ($callback) {\n            $response = $callback($this);\n\n            $this->save();\n\n            return $response;\n        });\n    }\n\n    /**\n     * Resets the instance and clears out the log.\n     */\n    public function reset(): void\n    {\n        $this->activity = null;\n        $this->subjects = [];\n    }\n\n    /**\n     * Returns the current activity log instance.\n     */\n    protected function getActivity(): ActivityLog\n    {\n        if ($this->activity) {\n            return $this->activity;\n        }\n\n        $this->activity = new ActivityLog([\n            'ip' => Request::ip(),\n            'batch' => $this->batch->uuid(),\n            'properties' => Collection::make([]),\n            'api_key_id' => $this->targetable->apiKeyId(),\n        ]);\n\n        if ($subject = $this->targetable->subject()) {\n            $this->subject($subject);\n        }\n\n        if ($actor = $this->targetable->actor()) {\n            $this->actor($actor);\n        } elseif (! is_null($user = $this->manager->guard()->user())) {\n            $this->actor($user);\n        }\n\n        return $this->activity;\n    }\n\n    /**\n     * Saves the activity log instance and attaches all of the subject models.\n     *\n     * @throws \\Throwable\n     */\n    protected function save(): ActivityLog\n    {\n        Assert::notNull($this->activity);\n\n        $response = $this->connection->transaction(function () {\n            $this->activity->save();\n\n            $subjects = Collection::make($this->subjects)\n                ->map(fn (Model $subject) => [\n                    'activity_log_id' => $this->activity->id,\n                    'subject_id' => $subject->getKey(),\n                    'subject_type' => $subject->getMorphClass(),\n                ])\n                ->values()\n                ->toArray();\n\n            ActivityLogSubject::insert($subjects);\n\n            return $this->activity;\n        });\n\n        $this->activity = null;\n        $this->subjects = [];\n\n        return $response;\n    }\n}\n"
  },
  {
    "path": "app/Services/Activity/ActivityLogTargetableService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Activity;\n\nuse Illuminate\\Database\\Eloquent\\Model;\n\nclass ActivityLogTargetableService\n{\n    protected ?Model $actor = null;\n\n    protected ?Model $subject = null;\n\n    protected ?int $apiKeyId = null;\n\n    public function setActor(Model $actor): void\n    {\n        $this->actor = $actor;\n    }\n\n    public function setSubject(Model $subject): void\n    {\n        $this->subject = $subject;\n    }\n\n    public function setApiKeyId(?int $apiKeyId): void\n    {\n        $this->apiKeyId = $apiKeyId;\n    }\n\n    public function actor(): ?Model\n    {\n        return $this->actor;\n    }\n\n    public function subject(): ?Model\n    {\n        return $this->subject;\n    }\n\n    public function apiKeyId(): ?int\n    {\n        return $this->apiKeyId;\n    }\n\n    public function reset(): void\n    {\n        $this->actor = null;\n        $this->subject = null;\n        $this->apiKeyId = null;\n    }\n}\n"
  },
  {
    "path": "app/Services/Allocations/AllocationDeletionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Allocations;\n\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Contracts\\Repository\\AllocationRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\Allocation\\ServerUsingAllocationException;\n\nclass AllocationDeletionService\n{\n    /**\n     * AllocationDeletionService constructor.\n     */\n    public function __construct(private AllocationRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Delete an allocation from the database only if it does not have a server\n     * that is actively attached to it.\n     *\n     * @throws ServerUsingAllocationException\n     */\n    public function handle(Allocation $allocation): int\n    {\n        if (!is_null($allocation->server_id)) {\n            throw new ServerUsingAllocationException(trans('exceptions.allocations.server_using'));\n        }\n\n        return $this->repository->delete($allocation->id);\n    }\n}\n"
  },
  {
    "path": "app/Services/Allocations/AssignmentService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Allocations;\n\nuse IPTools\\Network;\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Contracts\\Repository\\AllocationRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\Allocation\\CidrOutOfRangeException;\nuse Pterodactyl\\Exceptions\\Service\\Allocation\\PortOutOfRangeException;\nuse Pterodactyl\\Exceptions\\Service\\Allocation\\InvalidPortMappingException;\nuse Pterodactyl\\Exceptions\\Service\\Allocation\\TooManyPortsInRangeException;\n\nclass AssignmentService\n{\n    public const CIDR_MAX_BITS = 25;\n    public const CIDR_MIN_BITS = 32;\n    public const PORT_FLOOR = 1024;\n    public const PORT_CEIL = 65535;\n    public const PORT_RANGE_LIMIT = 1000;\n    public const PORT_RANGE_REGEX = '/^(\\d{4,5})-(\\d{4,5})$/';\n\n    /**\n     * AssignmentService constructor.\n     */\n    public function __construct(protected AllocationRepositoryInterface $repository, protected ConnectionInterface $connection)\n    {\n    }\n\n    /**\n     * Insert allocations into the database and link them to a specific node.\n     *\n     * @throws DisplayException\n     * @throws CidrOutOfRangeException\n     * @throws InvalidPortMappingException\n     * @throws PortOutOfRangeException\n     * @throws TooManyPortsInRangeException\n     */\n    public function handle(Node $node, array $data): void\n    {\n        $explode = explode('/', $data['allocation_ip']);\n        if (count($explode) !== 1) {\n            if (!ctype_digit($explode[1]) || ($explode[1] > self::CIDR_MIN_BITS || $explode[1] < self::CIDR_MAX_BITS)) {\n                throw new CidrOutOfRangeException();\n            }\n        }\n\n        try {\n            // TODO: how should we approach supporting IPv6 with this?\n            // gethostbyname only supports IPv4, but the alternative (dns_get_record) returns\n            // an array of records, which is not ideal for this use case, we need a SINGLE\n            // IP to use, not multiple.\n            $underlying = gethostbyname($data['allocation_ip']);\n            $parsed = Network::parse($underlying);\n        } catch (\\Exception $exception) {\n            // @phpstan-ignore-next-line variable.undefined\n            throw new DisplayException(\"Could not parse provided allocation IP address ({$underlying}): {$exception->getMessage()}\", $exception);\n        }\n\n        $this->connection->beginTransaction();\n        foreach ($parsed as $ip) {\n            foreach ($data['allocation_ports'] as $port) {\n                if (!is_digit($port) && !preg_match(self::PORT_RANGE_REGEX, $port)) {\n                    throw new InvalidPortMappingException($port);\n                }\n\n                $insertData = [];\n                if (preg_match(self::PORT_RANGE_REGEX, $port, $matches)) {\n                    $block = range($matches[1], $matches[2]);\n\n                    if (count($block) > self::PORT_RANGE_LIMIT) {\n                        throw new TooManyPortsInRangeException();\n                    }\n\n                    if ((int) $matches[1] <= self::PORT_FLOOR || (int) $matches[2] > self::PORT_CEIL) {\n                        throw new PortOutOfRangeException();\n                    }\n\n                    foreach ($block as $unit) {\n                        $insertData[] = [\n                            'node_id' => $node->id,\n                            'ip' => $ip->__toString(),\n                            'port' => (int) $unit,\n                            'ip_alias' => array_get($data, 'allocation_alias'),\n                            'server_id' => null,\n                        ];\n                    }\n                } else {\n                    if ((int) $port <= self::PORT_FLOOR || (int) $port > self::PORT_CEIL) {\n                        throw new PortOutOfRangeException();\n                    }\n\n                    $insertData[] = [\n                        'node_id' => $node->id,\n                        'ip' => $ip->__toString(),\n                        'port' => (int) $port,\n                        'ip_alias' => array_get($data, 'allocation_alias'),\n                        'server_id' => null,\n                    ];\n                }\n\n                $this->repository->insertIgnore($insertData);\n            }\n        }\n\n        $this->connection->commit();\n    }\n}\n"
  },
  {
    "path": "app/Services/Allocations/FindAssignableAllocationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Allocations;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Exceptions\\Service\\Allocation\\AutoAllocationNotEnabledException;\nuse Pterodactyl\\Exceptions\\Service\\Allocation\\NoAutoAllocationSpaceAvailableException;\n\nclass FindAssignableAllocationService\n{\n    /**\n     * FindAssignableAllocationService constructor.\n     */\n    public function __construct(private AssignmentService $service)\n    {\n    }\n\n    /**\n     * Finds an existing unassigned allocation and attempts to assign it to the given server. If\n     * no allocation can be found, a new one will be created with a random port between the defined\n     * range from the configuration.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\CidrOutOfRangeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\InvalidPortMappingException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\PortOutOfRangeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\TooManyPortsInRangeException\n     */\n    public function handle(Server $server): Allocation\n    {\n        if (!config('pterodactyl.client_features.allocations.enabled')) {\n            throw new AutoAllocationNotEnabledException();\n        }\n\n        // Attempt to find a given available allocation for a server. If one cannot be found\n        // we will fall back to attempting to create a new allocation that can be used for the\n        // server.\n        /** @var Allocation|null $allocation */\n        $allocation = $server->node->allocations()\n            ->lockForUpdate()\n            ->where('ip', $server->allocation->ip)\n            ->whereNull('server_id')\n            ->inRandomOrder()\n            ->first();\n\n        $allocation = $allocation ?? $this->createNewAllocation($server);\n\n        $allocation->update(['server_id' => $server->id]);\n\n        return $allocation->refresh();\n    }\n\n    /**\n     * Finds or creates a set of consecutive (sequential) unassigned allocations and assigns\n     * them all to the given server.\n     *\n     * @return Allocation[]\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws AutoAllocationNotEnabledException\n     * @throws NoAutoAllocationSpaceAvailableException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\CidrOutOfRangeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\InvalidPortMappingException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\PortOutOfRangeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\TooManyPortsInRangeException\n     */\n    public function handleConsecutive(Server $server, int $count): array\n    {\n        if (!config('pterodactyl.client_features.allocations.enabled')) {\n            throw new AutoAllocationNotEnabledException();\n        }\n\n        $start = config('pterodactyl.client_features.allocations.range_start', null);\n        $end = config('pterodactyl.client_features.allocations.range_end', null);\n\n        if (!$start || !$end) {\n            throw new NoAutoAllocationSpaceAvailableException();\n        }\n\n        Assert::integerish($start);\n        Assert::integerish($end);\n\n        $ip = $server->allocation->ip;\n\n        // Get all ports already assigned to any server on this node/ip within the range.\n        // Unassigned allocations (server_id = null) are still considered available.\n        $usedPorts = $server->node->allocations()\n            ->where('ip', $ip)\n            ->whereBetween('port', [$start, $end])\n            ->whereNotNull('server_id')\n            ->pluck('port')\n            ->toArray();\n\n        $available = array_values(array_diff(range((int) $start, (int) $end), $usedPorts));\n\n        // Build a set of available ports for O(1) lookup, then shuffle the ports so that\n        // the starting candidate is chosen randomly — mirroring how single-port allocation\n        // uses array_rand to avoid always picking from the beginning of the range.\n        $availableSet = array_flip($available);\n        shuffle($available);\n\n        $consecutiveStart = null;\n        foreach ($available as $candidate) {\n            $valid = true;\n            for ($j = 1; $j < $count; ++$j) {\n                if (!isset($availableSet[$candidate + $j])) {\n                    $valid = false;\n                    break;\n                }\n            }\n            if ($valid) {\n                $consecutiveStart = $candidate;\n                break;\n            }\n        }\n\n        if ($consecutiveStart === null) {\n            throw new NoAutoAllocationSpaceAvailableException();\n        }\n\n        $ports = range($consecutiveStart, $consecutiveStart + $count - 1);\n\n        // Create any ports in the range that don't already exist as allocations.\n        $existingPorts = $server->node->allocations()\n            ->where('ip', $ip)\n            ->whereIn('port', $ports)\n            ->pluck('port')\n            ->toArray();\n\n        $newPorts = array_values(array_diff($ports, $existingPorts));\n\n        if (!empty($newPorts)) {\n            $this->service->handle($server->node, [\n                'allocation_ip' => $ip,\n                'allocation_ports' => $newPorts,\n            ]);\n        }\n\n        // Assign all the consecutive allocations to the server.\n        $allocations = $server->node->allocations()\n            ->where('ip', $ip)\n            ->whereIn('port', $ports)\n            ->whereNull('server_id')\n            ->get();\n\n        if ($allocations->count() !== $count) {\n            throw new NoAutoAllocationSpaceAvailableException();\n        }\n\n        $allocations->each(function (Allocation $allocation) use ($server) {\n            $allocation->update(['server_id' => $server->id]);\n        });\n\n        return $allocations->map(fn (Allocation $a) => $a->refresh())->all();\n    }\n\n    /**\n     * Create a new allocation on the server's node with a random port from the defined range\n     * in the settings. If there are no matches in that range, or something is wrong with the\n     * range information provided an exception will be raised.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\CidrOutOfRangeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\InvalidPortMappingException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\PortOutOfRangeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Allocation\\TooManyPortsInRangeException\n     */\n    protected function createNewAllocation(Server $server): Allocation\n    {\n        $start = config('pterodactyl.client_features.allocations.range_start', null);\n        $end = config('pterodactyl.client_features.allocations.range_end', null);\n\n        if (!$start || !$end) {\n            throw new NoAutoAllocationSpaceAvailableException();\n        }\n\n        Assert::integerish($start);\n        Assert::integerish($end);\n\n        // Get all of the currently allocated ports for the node so that we can figure out\n        // which port might be available.\n        $ports = $server->node->allocations()\n            ->where('ip', $server->allocation->ip)\n            ->whereBetween('port', [$start, $end])\n            ->pluck('port');\n\n        // Compute the difference of the range and the currently created ports, finding\n        // any port that does not already exist in the database. We will then use this\n        // array of ports to create a new allocation to assign to the server.\n        $available = array_diff(range($start, $end), $ports->toArray());\n\n        // If we've already allocated all of the ports, just abort.\n        if (empty($available)) {\n            throw new NoAutoAllocationSpaceAvailableException();\n        }\n\n        // Pick a random port out of the remaining available ports.\n        /** @var int $port */\n        $port = $available[array_rand($available)];\n\n        $this->service->handle($server->node, [\n            'allocation_ip' => $server->allocation->ip,\n            'allocation_ports' => [$port],\n        ]);\n\n        /** @var Allocation $allocation */\n        $allocation = $server->node->allocations()\n            ->lockForUpdate()\n            ->where('ip', $server->allocation->ip)\n            ->where('port', $port)\n            ->firstOrFail();\n\n        return $allocation;\n    }\n}\n"
  },
  {
    "path": "app/Services/Api/KeyCreationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Api;\n\nuse Pterodactyl\\Models\\ApiKey;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Contracts\\Repository\\ApiKeyRepositoryInterface;\n\nclass KeyCreationService\n{\n    private int $keyType = ApiKey::TYPE_NONE;\n\n    /**\n     * ApiKeyService constructor.\n     */\n    public function __construct(private ApiKeyRepositoryInterface $repository, private Encrypter $encrypter)\n    {\n    }\n\n    /**\n     * Set the type of key that should be created. By default an orphaned key will be\n     * created. These keys cannot be used for anything, and will not render in the UI.\n     */\n    public function setKeyType(int $type): self\n    {\n        $this->keyType = $type;\n\n        return $this;\n    }\n\n    /**\n     * Create a new API key for the Panel using the permissions passed in the data request.\n     * This will automatically generate an identifier and an encrypted token that are\n     * stored in the database.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function handle(array $data, array $permissions = []): ApiKey\n    {\n        $data = array_merge($data, [\n            'key_type' => $this->keyType,\n            'identifier' => ApiKey::generateTokenIdentifier($this->keyType),\n            'token' => $this->encrypter->encrypt(str_random(ApiKey::KEY_LENGTH)),\n        ]);\n\n        if ($this->keyType === ApiKey::TYPE_APPLICATION) {\n            $data = array_merge($data, $permissions);\n        }\n\n        return $this->repository->create($data, true, true);\n    }\n}\n"
  },
  {
    "path": "app/Services/Backups/DeleteBackupService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Backups;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Backup;\nuse GuzzleHttp\\Exception\\ClientException;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Extensions\\Backups\\BackupManager;\nuse Pterodactyl\\Repositories\\Wings\\DaemonBackupRepository;\nuse Pterodactyl\\Exceptions\\Service\\Backup\\BackupLockedException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass DeleteBackupService\n{\n    public function __construct(\n        private ConnectionInterface $connection,\n        private BackupManager $manager,\n        private DaemonBackupRepository $daemonBackupRepository,\n    ) {\n    }\n\n    /**\n     * Deletes a backup from the system. If the backup is stored in S3 a request\n     * will be made to delete that backup from the disk as well.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(Backup $backup): void\n    {\n        // If the backup is marked as failed it can still be deleted, even if locked\n        // since the UI doesn't allow you to unlock a failed backup in the first place.\n        //\n        // I also don't really see any reason you'd have a locked, failed backup to keep\n        // around. The logic that updates the backup to the failed state will also remove\n        // the lock, so this condition should really never happen.\n        if ($backup->is_locked && ($backup->is_successful && !is_null($backup->completed_at))) {\n            throw new BackupLockedException();\n        }\n\n        if ($backup->disk === Backup::ADAPTER_AWS_S3) {\n            $this->deleteFromS3($backup);\n\n            return;\n        }\n\n        $this->connection->transaction(function () use ($backup) {\n            try {\n                $this->daemonBackupRepository->setServer($backup->server)->delete($backup);\n            } catch (DaemonConnectionException $exception) {\n                $previous = $exception->getPrevious();\n                // Don't fail the request if the Daemon responds with a 404, just assume the backup\n                // doesn't actually exist and remove its reference from the Panel as well.\n                if (!$previous instanceof ClientException || $previous->getResponse()->getStatusCode() !== Response::HTTP_NOT_FOUND) {\n                    throw $exception;\n                }\n            }\n\n            $backup->delete();\n        });\n    }\n\n    /**\n     * Deletes a backup from an S3 disk.\n     *\n     * @throws \\Throwable\n     */\n    protected function deleteFromS3(Backup $backup): void\n    {\n        $this->connection->transaction(function () use ($backup) {\n            $backup->delete();\n\n            /** @var \\Pterodactyl\\Extensions\\Filesystem\\S3Filesystem $adapter */\n            $adapter = $this->manager->adapter(Backup::ADAPTER_AWS_S3);\n\n            // @phpstan-ignore-next-line method.notFound\n            $adapter->getClient()->deleteObject([\n                'Bucket' => $adapter->getBucket(),\n                'Key' => sprintf('%s/%s.tar.gz', $backup->server->uuid, $backup->uuid),\n            ]);\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Backups/DownloadLinkService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Backups;\n\nuse Carbon\\CarbonImmutable;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Backup;\nuse Pterodactyl\\Services\\Nodes\\NodeJWTService;\nuse Pterodactyl\\Extensions\\Backups\\BackupManager;\n\nclass DownloadLinkService\n{\n    /**\n     * DownloadLinkService constructor.\n     */\n    public function __construct(private BackupManager $backupManager, private NodeJWTService $jwtService)\n    {\n    }\n\n    /**\n     * Returns the URL that allows for a backup to be downloaded by an individual\n     * user, or by the Wings control software.\n     */\n    public function handle(Backup $backup, User $user): string\n    {\n        if ($backup->disk === Backup::ADAPTER_AWS_S3) {\n            return $this->getS3BackupUrl($backup);\n        }\n\n        $token = $this->jwtService\n            ->setExpiresAt(CarbonImmutable::now()->addMinutes(15))\n            ->setUser($user)\n            ->setClaims([\n                'backup_uuid' => $backup->uuid,\n                'server_uuid' => $backup->server->uuid,\n            ])\n            ->handle($backup->server->node, $user->id . $backup->server->uuid);\n\n        return sprintf('%s/download/backup?token=%s', $backup->server->node->getConnectionAddress(), $token->toString());\n    }\n\n    /**\n     * Returns a signed URL that allows us to download a file directly out of a non-public\n     * S3 bucket by using a signed URL.\n     */\n    protected function getS3BackupUrl(Backup $backup): string\n    {\n        /** @var \\Pterodactyl\\Extensions\\Filesystem\\S3Filesystem $adapter */\n        $adapter = $this->backupManager->adapter(Backup::ADAPTER_AWS_S3);\n\n        $request = $adapter->getClient()->createPresignedRequest(\n            $adapter->getClient()->getCommand('GetObject', [\n                'Bucket' => $adapter->getBucket(),\n                'Key' => sprintf('%s/%s.tar.gz', $backup->server->uuid, $backup->uuid),\n                'ContentType' => 'application/x-gzip',\n            ]),\n            CarbonImmutable::now()->addMinutes(5)\n        );\n\n        return $request->getUri()->__toString();\n    }\n}\n"
  },
  {
    "path": "app/Services/Backups/InitiateBackupService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Backups;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Carbon\\CarbonImmutable;\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Backup;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Extensions\\Backups\\BackupManager;\nuse Pterodactyl\\Repositories\\Eloquent\\BackupRepository;\nuse Pterodactyl\\Repositories\\Wings\\DaemonBackupRepository;\nuse Pterodactyl\\Exceptions\\Service\\Backup\\TooManyBackupsException;\nuse Symfony\\Component\\HttpKernel\\Exception\\TooManyRequestsHttpException;\n\nclass InitiateBackupService\n{\n    private array $ignoredFiles = [];\n\n    private bool $isLocked = false;\n\n    /**\n     * InitiateBackupService constructor.\n     */\n    public function __construct(\n        private BackupRepository $repository,\n        private ConnectionInterface $connection,\n        private DaemonBackupRepository $daemonBackupRepository,\n        private DeleteBackupService $deleteBackupService,\n        private BackupManager $backupManager,\n    ) {\n    }\n\n    /**\n     * Set if the backup should be locked once it is created which will prevent\n     * its deletion by users or automated system processes.\n     */\n    public function setIsLocked(bool $isLocked): self\n    {\n        $this->isLocked = $isLocked;\n\n        return $this;\n    }\n\n    /**\n     * Sets the files to be ignored by this backup.\n     *\n     * @param string[]|null $ignored\n     */\n    public function setIgnoredFiles(?array $ignored): self\n    {\n        if (is_array($ignored)) {\n            foreach ($ignored as $value) {\n                Assert::string($value); // @phpstan-ignore staticMethod.alreadyNarrowedType\n            }\n        }\n\n        // Set the ignored files to be any values that are not empty in the array. Don't use\n        // the PHP empty function here incase anything that is \"empty\" by default (0, false, etc.)\n        // were passed as a file or folder name.\n        $this->ignoredFiles = is_null($ignored) ? [] : array_filter($ignored, function ($value) {\n            return strlen($value) > 0;\n        });\n\n        return $this;\n    }\n\n    /**\n     * Initiates the backup process for a server on Wings.\n     *\n     * @throws \\Throwable\n     * @throws TooManyBackupsException\n     * @throws TooManyRequestsHttpException\n     */\n    public function handle(Server $server, ?string $name = null, bool $override = false): Backup\n    {\n        $limit = config('backups.throttles.limit');\n        $period = config('backups.throttles.period');\n        if ($period > 0) {\n            $previous = $this->repository->getBackupsGeneratedDuringTimespan($server->id, $period);\n            if ($previous->count() >= $limit) {\n                $message = sprintf('Only %d backups may be generated within a %d second span of time.', $limit, $period);\n\n                throw new TooManyRequestsHttpException((int) CarbonImmutable::now()->diffInSeconds($previous->last()->created_at->addSeconds($period)), $message);\n            }\n        }\n\n        // Check if the server has reached or exceeded its backup limit.\n        // completed_at == null will cover any ongoing backups, while is_successful == true will cover any completed backups.\n        $successful = $this->repository->getNonFailedBackups($server);\n        if (!$server->backup_limit || $successful->count() >= $server->backup_limit) {\n            // Do not allow the user to continue if this server is already at its limit and can't override.\n            if (!$override || $server->backup_limit <= 0) {\n                throw new TooManyBackupsException($server->backup_limit);\n            }\n\n            // Get the oldest backup the server has that is not \"locked\" (indicating a backup that should\n            // never be automatically purged). If we find a backup we will delete it and then continue with\n            // this process. If no backup is found that can be used an exception is thrown.\n            $oldest = $successful->where('is_locked', false)->orderBy('created_at')->first();\n            if (!$oldest) {\n                throw new TooManyBackupsException($server->backup_limit);\n            }\n\n            $this->deleteBackupService->handle($oldest);\n        }\n\n        return $this->connection->transaction(function () use ($server, $name) {\n            /** @var Backup $backup */\n            $backup = $this->repository->create([\n                'server_id' => $server->id,\n                'uuid' => Uuid::uuid4()->toString(),\n                'name' => trim($name) ?: sprintf('备份于 %s', CarbonImmutable::now()->toDateTimeString()),\n                'ignored_files' => array_values($this->ignoredFiles),\n                'disk' => $this->backupManager->getDefaultAdapter(),\n                'is_locked' => $this->isLocked,\n            ], true, true);\n\n            $this->daemonBackupRepository->setServer($server)\n                ->setBackupAdapter($this->backupManager->getDefaultAdapter())\n                ->backup($backup);\n\n            return $backup;\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Databases/DatabaseManagementService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Databases;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Helpers\\Utilities;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Extensions\\DynamicDatabaseConnection;\nuse Pterodactyl\\Repositories\\Eloquent\\DatabaseRepository;\nuse Pterodactyl\\Exceptions\\Repository\\DuplicateDatabaseNameException;\nuse Pterodactyl\\Exceptions\\Service\\Database\\TooManyDatabasesException;\nuse Pterodactyl\\Exceptions\\Service\\Database\\DatabaseClientFeatureNotEnabledException;\n\nclass DatabaseManagementService\n{\n    /**\n     * The regex used to validate that the database name passed through to the function is\n     * in the expected format.\n     *\n     * @see \\Pterodactyl\\Services\\Databases\\DatabaseManagementService::generateUniqueDatabaseName()\n     */\n    private const MATCH_NAME_REGEX = '/^(s[\\d]+_)(.*)$/';\n\n    /**\n     * Determines if the service should validate the user's ability to create an additional\n     * database for this server. In almost all cases this should be true, but to keep things\n     * flexible you can also set it to false and create more databases than the server is\n     * allocated.\n     */\n    protected bool $validateDatabaseLimit = true;\n\n    public function __construct(\n        protected ConnectionInterface $connection,\n        protected DynamicDatabaseConnection $dynamic,\n        protected Encrypter $encrypter,\n        protected DatabaseRepository $repository,\n    ) {\n    }\n\n    /**\n     * Generates a unique database name for the given server. This name should be passed through when\n     * calling this handle function for this service, otherwise the database will be created with\n     * whatever name is provided.\n     */\n    public static function generateUniqueDatabaseName(string $name, int $serverId): string\n    {\n        // Max of 48 characters, including the s123_ that we append to the front.\n        return sprintf('s%d_%s', $serverId, substr($name, 0, 48 - strlen(\"s{$serverId}_\")));\n    }\n\n    /**\n     * Set whether this class should validate that the server has enough slots\n     * left before creating the new database.\n     */\n    public function setValidateDatabaseLimit(bool $validate): self\n    {\n        $this->validateDatabaseLimit = $validate;\n\n        return $this;\n    }\n\n    /**\n     * Create a new database that is linked to a specific host.\n     *\n     * @throws \\Throwable\n     * @throws TooManyDatabasesException\n     * @throws DatabaseClientFeatureNotEnabledException\n     */\n    public function create(Server $server, array $data): Database\n    {\n        if (!config('pterodactyl.client_features.databases.enabled')) {\n            throw new DatabaseClientFeatureNotEnabledException();\n        }\n\n        if ($this->validateDatabaseLimit) {\n            // If the server has a limit assigned and we've already reached that limit, throw back\n            // an exception and kill the process.\n            if (!is_null($server->database_limit) && $server->databases()->count() >= $server->database_limit) {\n                throw new TooManyDatabasesException();\n            }\n        }\n\n        // Protect against developer mistakes...\n        if (empty($data['database']) || !preg_match(self::MATCH_NAME_REGEX, $data['database'])) {\n            throw new \\InvalidArgumentException('The database name passed to DatabaseManagementService::handle MUST be prefixed with \"s{server_id}_\".');\n        }\n\n        $data = array_merge($data, [\n            'server_id' => $server->id,\n            'username' => sprintf('u%d_%s', $server->id, str_random(10)),\n            'password' => $this->encrypter->encrypt(\n                Utilities::randomStringWithSpecialCharacters(24)\n            ),\n        ]);\n\n        $database = null;\n\n        try {\n            return $this->connection->transaction(function () use ($data, &$database) {\n                $database = $this->createModel($data);\n\n                $this->dynamic->set('dynamic', $data['database_host_id']);\n\n                $this->repository->createDatabase($database->database);\n                $this->repository->createUser(\n                    $database->username,\n                    $database->remote,\n                    $this->encrypter->decrypt($database->password),\n                    $database->max_connections\n                );\n                $this->repository->assignUserToDatabase($database->database, $database->username, $database->remote);\n                $this->repository->flush();\n\n                return $database;\n            });\n        } catch (\\Exception $exception) {\n            try {\n                // This is actually incorrect, it can be null in the case that the $database model\n                // itself isn't able to be created in Pterodactyl's database.\n                //\n                // @phpstan-ignore-next-line instanceof.alwaysFalse\n                if ($database instanceof Database) {\n                    $this->repository->dropDatabase($database->database);\n                    $this->repository->dropUser($database->username, $database->remote);\n                    $this->repository->flush();\n                }\n            } catch (\\Throwable $deletionException) { // @phpstan-ignore catch.neverThrown\n                // Do nothing here. We've already encountered an issue before this point so no\n                // reason to prioritize this error over the initial one.\n            }\n\n            throw $exception;\n        }\n    }\n\n    /**\n     * Delete a database from the given host server.\n     *\n     * @throws \\Exception\n     */\n    public function delete(Database $database): ?bool\n    {\n        $this->dynamic->set('dynamic', $database->database_host_id);\n\n        $this->repository->dropDatabase($database->database);\n        $this->repository->dropUser($database->username, $database->remote);\n        $this->repository->flush();\n\n        return $database->delete();\n    }\n\n    /**\n     * Create the database if there is not an identical match in the DB. While you can technically\n     * have the same name across multiple hosts, for the sake of keeping this logic easy to understand\n     * and avoiding user confusion we will ignore the specific host and just look across all hosts.\n     *\n     * @throws DuplicateDatabaseNameException\n     * @throws \\Throwable\n     */\n    protected function createModel(array $data): Database\n    {\n        $exists = Database::query()->where('server_id', $data['server_id'])\n            ->where('database', $data['database'])\n            ->exists();\n\n        if ($exists) {\n            throw new DuplicateDatabaseNameException('A database with that name already exists for this server.');\n        }\n\n        $database = (new Database())->forceFill($data);\n        $database->saveOrFail();\n\n        return $database;\n    }\n}\n"
  },
  {
    "path": "app/Services/Databases/DatabasePasswordService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Databases;\n\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Helpers\\Utilities;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Extensions\\DynamicDatabaseConnection;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseRepositoryInterface;\n\nclass DatabasePasswordService\n{\n    /**\n     * DatabasePasswordService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private DynamicDatabaseConnection $dynamic,\n        private Encrypter $encrypter,\n        private DatabaseRepositoryInterface $repository,\n    ) {\n    }\n\n    /**\n     * Updates a password for a given database.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(Database|int $database): string\n    {\n        $password = Utilities::randomStringWithSpecialCharacters(24);\n\n        $this->connection->transaction(function () use ($database, $password) {\n            $database->sharedLock()->update([\n                'password' => $this->encrypter->encrypt($password),\n            ]);\n\n            $this->dynamic->set('dynamic', $database->database_host_id);\n            $this->repository->dropUser($database->username, $database->remote);\n            $this->repository->createUser($database->username, $database->remote, $password, $database->max_connections);\n            $this->repository->assignUserToDatabase($database->database, $database->username, $database->remote);\n            $this->repository->flush();\n        });\n\n        return $password;\n    }\n}\n"
  },
  {
    "path": "app/Services/Databases/DeployServerDatabaseService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Databases;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Pterodactyl\\Exceptions\\Service\\Database\\NoSuitableDatabaseHostException;\n\nclass DeployServerDatabaseService\n{\n    /**\n     * DeployServerDatabaseService constructor.\n     */\n    public function __construct(private DatabaseManagementService $managementService)\n    {\n    }\n\n    /**\n     * @throws \\Throwable\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Database\\TooManyDatabasesException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Database\\DatabaseClientFeatureNotEnabledException\n     */\n    public function handle(Server $server, array $data): Database\n    {\n        Assert::notEmpty($data['database'] ?? null);\n        Assert::notEmpty($data['remote'] ?? null);\n\n        $hosts = DatabaseHost::query()->get()->toBase();\n        if ($hosts->isEmpty()) {\n            throw new NoSuitableDatabaseHostException();\n        } else {\n            $nodeHosts = $hosts->where('node_id', $server->node_id)->toBase();\n\n            if ($nodeHosts->isEmpty() && !config('pterodactyl.client_features.databases.allow_random')) {\n                throw new NoSuitableDatabaseHostException();\n            }\n        }\n\n        return $this->managementService->create($server, [\n            'database_host_id' => $nodeHosts->isEmpty()\n                ? $hosts->random()->id\n                : $nodeHosts->random()->id,\n            'database' => DatabaseManagementService::generateUniqueDatabaseName($data['database'], $server->id),\n            'remote' => $data['remote'],\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Services/Databases/Hosts/HostCreationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Databases\\Hosts;\n\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Illuminate\\Database\\DatabaseManager;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Extensions\\DynamicDatabaseConnection;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseHostRepositoryInterface;\n\nclass HostCreationService\n{\n    /**\n     * HostCreationService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private DatabaseManager $databaseManager,\n        private DynamicDatabaseConnection $dynamic,\n        private Encrypter $encrypter,\n        private DatabaseHostRepositoryInterface $repository,\n    ) {\n    }\n\n    /**\n     * Create a new database host on the Panel.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(array $data): DatabaseHost\n    {\n        return $this->connection->transaction(function () use ($data) {\n            $host = $this->repository->create([\n                'password' => $this->encrypter->encrypt(array_get($data, 'password')),\n                'name' => array_get($data, 'name'),\n                'host' => array_get($data, 'host'),\n                'port' => array_get($data, 'port'),\n                'username' => array_get($data, 'username'),\n                'max_databases' => null,\n                'node_id' => array_get($data, 'node_id'),\n            ]);\n\n            // Confirm access using the provided credentials before saving data.\n            $this->dynamic->set('dynamic', $host);\n            $this->databaseManager->connection('dynamic')->select('SELECT 1 FROM dual');\n\n            return $host;\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Databases/Hosts/HostDeletionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Databases\\Hosts;\n\nuse Pterodactyl\\Exceptions\\Service\\HasActiveServersException;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseHostRepositoryInterface;\n\nclass HostDeletionService\n{\n    /**\n     * HostDeletionService constructor.\n     */\n    public function __construct(\n        private DatabaseRepositoryInterface $databaseRepository,\n        private DatabaseHostRepositoryInterface $repository,\n    ) {\n    }\n\n    /**\n     * Delete a specified host from the Panel if no databases are\n     * attached to it.\n     *\n     * @throws HasActiveServersException\n     */\n    public function handle(int $host): int\n    {\n        $count = $this->databaseRepository->findCountWhere([['database_host_id', '=', $host]]);\n        if ($count > 0) {\n            throw new HasActiveServersException(trans('exceptions.databases.delete_has_databases'));\n        }\n\n        return $this->repository->delete($host);\n    }\n}\n"
  },
  {
    "path": "app/Services/Databases/Hosts/HostUpdateService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Databases\\Hosts;\n\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Illuminate\\Database\\DatabaseManager;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Extensions\\DynamicDatabaseConnection;\nuse Pterodactyl\\Contracts\\Repository\\DatabaseHostRepositoryInterface;\n\nclass HostUpdateService\n{\n    /**\n     * HostUpdateService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private DatabaseManager $databaseManager,\n        private DynamicDatabaseConnection $dynamic,\n        private Encrypter $encrypter,\n        private DatabaseHostRepositoryInterface $repository,\n    ) {\n    }\n\n    /**\n     * Update a database host and persist to the database.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(int $hostId, array $data): DatabaseHost\n    {\n        if (!empty(array_get($data, 'password'))) {\n            $data['password'] = $this->encrypter->encrypt($data['password']);\n        } else {\n            unset($data['password']);\n        }\n\n        return $this->connection->transaction(function () use ($data, $hostId) {\n            $host = $this->repository->update($hostId, $data);\n            $this->dynamic->set('dynamic', $host);\n            $this->databaseManager->connection('dynamic')->select('SELECT 1 FROM dual');\n\n            return $host;\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Deployment/AllocationSelectionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Deployment;\n\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Services\\Allocations\\AssignmentService;\nuse Pterodactyl\\Contracts\\Repository\\AllocationRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableAllocationException;\n\nclass AllocationSelectionService\n{\n    protected bool $dedicated = false;\n\n    protected array $nodes = [];\n\n    protected array $ports = [];\n\n    /**\n     * AllocationSelectionService constructor.\n     */\n    public function __construct(private AllocationRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Toggle if the selected allocation should be the only allocation belonging\n     * to the given IP address. If true an allocation will not be selected if an IP\n     * already has another server set to use on if its allocations.\n     */\n    public function setDedicated(bool $dedicated): self\n    {\n        $this->dedicated = $dedicated;\n\n        return $this;\n    }\n\n    /**\n     * A list of node IDs that should be used when selecting an allocation. If empty, all\n     * nodes will be used to filter with.\n     */\n    public function setNodes(array $nodes): self\n    {\n        $this->nodes = $nodes;\n\n        return $this;\n    }\n\n    /**\n     * An array of individual ports or port ranges to use when selecting an allocation. If\n     * empty, all ports will be considered when finding an allocation. If set, only ports appearing\n     * in the array or range will be used.\n     *\n     * @throws DisplayException\n     */\n    public function setPorts(array $ports): self\n    {\n        $stored = [];\n        foreach ($ports as $port) {\n            if (is_digit($port)) {\n                $stored[] = $port;\n            }\n\n            // Ranges are stored in the ports array as an array which can be\n            // better processed in the repository.\n            if (preg_match(AssignmentService::PORT_RANGE_REGEX, $port, $matches)) {\n                if (abs($matches[2] - $matches[1]) > AssignmentService::PORT_RANGE_LIMIT) {\n                    throw new DisplayException(trans('exceptions.allocations.too_many_ports'));\n                }\n\n                $stored[] = [$matches[1], $matches[2]];\n            }\n        }\n\n        $this->ports = $stored;\n\n        return $this;\n    }\n\n    /**\n     * Return a single allocation that should be used as the default allocation for a server.\n     *\n     * @throws NoViableAllocationException\n     */\n    public function handle(): Allocation\n    {\n        $allocation = $this->repository->getRandomAllocation($this->nodes, $this->ports, $this->dedicated);\n\n        if (is_null($allocation)) {\n            throw new NoViableAllocationException(trans('exceptions.deployment.no_viable_allocations'));\n        }\n\n        return $allocation;\n    }\n}\n"
  },
  {
    "path": "app/Services/Deployment/FindViableNodesService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Deployment;\n\nuse Pterodactyl\\Models\\Node;\nuse Webmozart\\Assert\\Assert;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Contracts\\Pagination\\LengthAwarePaginator;\nuse Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableNodeException;\n\nclass FindViableNodesService\n{\n    protected array $locations = [];\n    protected ?int $disk = null;\n    protected ?int $memory = null;\n\n    /**\n     * Set the locations that should be searched through to locate available nodes.\n     */\n    public function setLocations(array $locations): self\n    {\n        Assert::allIntegerish($locations, 'An array of location IDs should be provided when calling setLocations.');\n\n        $this->locations = $locations;\n\n        return $this;\n    }\n\n    /**\n     * Set the amount of disk that will be used by the server being created. Nodes will be\n     * filtered out if they do not have enough available free disk space for this server\n     * to be placed on.\n     */\n    public function setDisk(int $disk): self\n    {\n        $this->disk = $disk;\n\n        return $this;\n    }\n\n    /**\n     * Set the amount of memory that this server will be using. As with disk space, nodes that\n     * do not have enough free memory will be filtered out.\n     */\n    public function setMemory(int $memory): self\n    {\n        $this->memory = $memory;\n\n        return $this;\n    }\n\n    /**\n     * Returns an array of nodes that meet the provided requirements and can then\n     * be passed to the AllocationSelectionService to return a single allocation.\n     *\n     * This functionality is used for automatic deployments of servers and will\n     * attempt to find all nodes in the defined locations that meet the disk and\n     * memory availability requirements. Any nodes not meeting those requirements\n     * are tossed out, as are any nodes marked as non-public, meaning automatic\n     * deployments should not be done against them.\n     *\n     * @param int|null $page If provided the results will be paginated by returning\n     *                       up to 50 nodes at a time starting at the provided page.\n     *                       If \"null\" is provided as the value no pagination will\n     *                       be used.\n     *\n     * @throws NoViableNodeException\n     */\n    public function handle(?int $perPage = null, ?int $page = null): LengthAwarePaginator|Collection\n    {\n        Assert::integer($this->disk, 'Disk space must be an int, got %s');\n        Assert::integer($this->memory, 'Memory usage must be an int, got %s');\n\n        $query = Node::query()->select('nodes.*')\n            ->selectRaw('IFNULL(SUM(servers.memory), 0) as sum_memory')\n            ->selectRaw('IFNULL(SUM(servers.disk), 0) as sum_disk')\n            ->leftJoin('servers', 'servers.node_id', '=', 'nodes.id')\n            ->where('nodes.public', 1);\n\n        if (!empty($this->locations)) {\n            $query = $query->whereIn('nodes.location_id', $this->locations);\n        }\n\n        $results = $query->groupBy('nodes.id')\n            ->havingRaw('(IFNULL(SUM(servers.memory), 0) + ?) <= (nodes.memory * (1 + (nodes.memory_overallocate / 100)))', [$this->memory])\n            ->havingRaw('(IFNULL(SUM(servers.disk), 0) + ?) <= (nodes.disk * (1 + (nodes.disk_overallocate / 100)))', [$this->disk]);\n\n        if (!is_null($page)) {\n            $results = $results->paginate($perPage ?? 50, ['*'], 'page', $page);\n        } else {\n            $results = $results->get()->toBase();\n        }\n\n        if ($results->isEmpty()) {\n            throw new NoViableNodeException(trans('exceptions.deployment.no_viable_nodes'));\n        }\n\n        return $results;\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/EggConfigurationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs;\n\nuse Illuminate\\Support\\Arr;\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Services\\Servers\\ServerConfigurationStructureService;\n\nclass EggConfigurationService\n{\n    /**\n     * EggConfigurationService constructor.\n     */\n    public function __construct(private ServerConfigurationStructureService $configurationStructureService)\n    {\n    }\n\n    /**\n     * Return an Egg file to be used by the Daemon.\n     */\n    public function handle(Server $server): array\n    {\n        $configs = $this->replacePlaceholders(\n            $server,\n            json_decode($server->egg->inherit_config_files)\n        );\n\n        return [\n            'startup' => $this->convertStartupToNewFormat(json_decode($server->egg->inherit_config_startup, true)),\n            'stop' => $this->convertStopToNewFormat($server->egg->inherit_config_stop),\n            'configs' => $configs,\n        ];\n    }\n\n    /**\n     * Convert the \"done\" variable into an array if it is not currently one.\n     */\n    protected function convertStartupToNewFormat(array $startup): array\n    {\n        $done = Arr::get($startup, 'done');\n\n        return [\n            'done' => is_string($done) ? [$done] : $done,\n            'user_interaction' => [],\n            'strip_ansi' => Arr::get($startup, 'strip_ansi') ?? false,\n        ];\n    }\n\n    /**\n     * Converts a legacy stop string into a new generation stop option for a server.\n     *\n     * For most eggs, this ends up just being a command sent to the server console, but\n     * if the stop command is something starting with a caret (^), it will be converted\n     * into the associated kill signal for the instance.\n     */\n    protected function convertStopToNewFormat(string $stop): array\n    {\n        if (!Str::startsWith($stop, '^')) {\n            return [\n                'type' => 'command',\n                'value' => $stop,\n            ];\n        }\n\n        $signal = substr($stop, 1);\n\n        return [\n            'type' => 'signal',\n            'value' => strtoupper($signal),\n        ];\n    }\n\n    protected function replacePlaceholders(Server $server, object $configs): array\n    {\n        // Get the legacy configuration structure for the server so that we\n        // can property map the egg placeholders to values.\n        $structure = $this->configurationStructureService->handle($server, [], true);\n\n        $response = [];\n        // Normalize the output of the configuration for the new Wings Daemon to more\n        // easily ingest, as well as make things more flexible down the road.\n        foreach ($configs as $file => $data) {\n            // Try to head off any errors relating to parsing a set of configuration files\n            // or other JSON data for the egg. This should probably be blocked at the time\n            // of egg creation/update, but it isn't so this check will at least prevent a\n            // 500 error which would crash the entire Wings boot process.\n            //\n            // @see https://github.com/pterodactyl/panel/issues/3055\n            if (!is_object($data) || !isset($data->find)) {\n                continue;\n            }\n\n            $append = array_merge((array) $data, ['file' => $file, 'replace' => []]);\n\n            foreach ($this->iterate($data->find, $structure) as $find => $replace) {\n                if (is_object($replace)) {\n                    foreach ($replace as $match => $replaceWith) {\n                        $append['replace'][] = [\n                            'match' => $find,\n                            'if_value' => $match,\n                            'replace_with' => $replaceWith,\n                        ];\n                    }\n\n                    continue;\n                }\n\n                $append['replace'][] = [\n                    'match' => $find,\n                    'replace_with' => $replace,\n                ];\n            }\n\n            unset($append['find']);\n\n            $response[] = $append;\n        }\n\n        return $response;\n    }\n\n    /**\n     * Replaces the legacy modifies from eggs with their new counterpart. The legacy Daemon would\n     * set SERVER_MEMORY, SERVER_IP, and SERVER_PORT with their respective values on the Daemon\n     * side. Ensure that anything referencing those properly replaces them with the matching config\n     * value.\n     */\n    protected function replaceLegacyModifiers(string $key, string $value): string\n    {\n        switch ($key) {\n            case 'config.docker.interface':\n                $replace = 'config.docker.network.interface';\n                break;\n            case 'server.build.env.SERVER_MEMORY':\n            case 'env.SERVER_MEMORY':\n                $replace = 'server.build.memory';\n                break;\n            case 'server.build.env.SERVER_IP':\n            case 'env.SERVER_IP':\n                $replace = 'server.build.default.ip';\n                break;\n            case 'server.build.env.SERVER_PORT':\n            case 'env.SERVER_PORT':\n                $replace = 'server.build.default.port';\n                break;\n            default:\n                // By default, we don't need to change anything, only if we ended up matching a specific legacy item.\n                $replace = $key;\n        }\n\n        return str_replace(\"{{{$key}}}\", \"{{{$replace}}}\", $value);\n    }\n\n    protected function matchAndReplaceKeys(mixed $value, array $structure): mixed\n    {\n        preg_match_all('/{{(?<key>[\\w.-]*)}}/', $value, $matches);\n\n        foreach ($matches['key'] as $key) {\n            // Matched something in {{server.X}} format, now replace that with the actual\n            // value from the server properties.\n            //\n            // The Daemon supports server.X, env.X, and config.X placeholders.\n            if (!Str::startsWith($key, ['server.', 'env.', 'config.'])) {\n                continue;\n            }\n\n            // Don't do a replacement on anything that is not a string, we don't want to unintentionally\n            // modify the resulting output.\n            if (!is_string($value)) {\n                continue;\n            }\n\n            $value = $this->replaceLegacyModifiers($key, $value);\n\n            // We don't want to do anything with config keys since the Daemon will need to handle\n            // that. For example, the Spigot egg uses \"config.docker.interface\" to identify the Docker\n            // interface to proxy through, but the Panel would be unaware of that.\n            if (Str::startsWith($key, 'config.')) {\n                continue;\n            }\n\n            // Replace anything starting with \"server.\" with the value out of the server configuration\n            // array that used to be created for the old daemon.\n            if (Str::startsWith($key, 'server.')) {\n                $plucked = Arr::get($structure, preg_replace('/^server\\./', '', $key), '');\n\n                $value = str_replace(\"{{{$key}}}\", $plucked, $value);\n                continue;\n            }\n\n            // Finally, replace anything starting with env. with the expected environment\n            // variable from the server configuration.\n            $plucked = Arr::get(\n                $structure,\n                preg_replace('/^env\\./', 'build.env.', $key),\n                ''\n            );\n\n            $value = str_replace(\"{{{$key}}}\", $plucked, $value);\n        }\n\n        return $value;\n    }\n\n    /**\n     * Iterates over a set of \"find\" values for a given file in the parser configuration. If\n     * the value of the line match is something iterable, continue iterating, otherwise perform\n     * a match & replace.\n     */\n    private function iterate(mixed $data, array $structure): mixed\n    {\n        if (!is_iterable($data) && !is_object($data)) {\n            return $data;\n        }\n\n        // Remember, in PHP objects are always passed by reference, so if we do not clone this object\n        // instance we'll end up making modifications to the object outside the scope of this function\n        // which leads to some fun behavior in the parser.\n        if (is_array($data)) {\n            // Copy the array.\n            // NOTE: if the array contains any objects, they will be passed by reference.\n            $clone = $data;\n        } else {\n            $clone = clone $data;\n        }\n        foreach ($clone as $key => &$value) {\n            if (is_iterable($value) || is_object($value)) {\n                $value = $this->iterate($value, $structure);\n\n                continue;\n            }\n\n            $value = $this->matchAndReplaceKeys($value, $structure);\n        }\n\n        return $clone;\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/EggCreationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Contracts\\Repository\\EggRepositoryInterface;\nuse Illuminate\\Contracts\\Config\\Repository as ConfigRepository;\nuse Pterodactyl\\Exceptions\\Service\\Egg\\NoParentConfigurationFoundException;\n\n// When a mommy and a daddy pterodactyl really like each other...\nclass EggCreationService\n{\n    /**\n     * EggCreationService constructor.\n     */\n    public function __construct(private ConfigRepository $config, private EggRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Create a new service option and assign it to the given service.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws NoParentConfigurationFoundException\n     */\n    public function handle(array $data): Egg\n    {\n        $data['config_from'] = array_get($data, 'config_from');\n        if (!is_null($data['config_from'])) {\n            $results = $this->repository->findCountWhere([\n                ['nest_id', '=', array_get($data, 'nest_id')],\n                ['id', '=', array_get($data, 'config_from')],\n            ]);\n\n            if ($results !== 1) {\n                throw new NoParentConfigurationFoundException(trans('exceptions.nest.egg.must_be_child'));\n            }\n        }\n\n        return $this->repository->create(array_merge($data, [\n            'uuid' => Uuid::uuid4()->toString(),\n            'author' => $this->config->get('pterodactyl.service.author'),\n        ]), true, true);\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/EggDeletionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs;\n\nuse Pterodactyl\\Contracts\\Repository\\EggRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\Egg\\HasChildrenException;\nuse Pterodactyl\\Exceptions\\Service\\HasActiveServersException;\nuse Pterodactyl\\Contracts\\Repository\\ServerRepositoryInterface;\n\nclass EggDeletionService\n{\n    /**\n     * EggDeletionService constructor.\n     */\n    public function __construct(\n        protected ServerRepositoryInterface $serverRepository,\n        protected EggRepositoryInterface $repository,\n    ) {\n    }\n\n    /**\n     * Delete an Egg from the database if it has no active servers attached to it.\n     *\n     * @throws HasActiveServersException\n     * @throws HasChildrenException\n     */\n    public function handle(int $egg): int\n    {\n        $servers = $this->serverRepository->findCountWhere([['egg_id', '=', $egg]]);\n        if ($servers > 0) {\n            throw new HasActiveServersException(trans('exceptions.nest.egg.delete_has_servers'));\n        }\n\n        $children = $this->repository->findCountWhere([['config_from', '=', $egg]]);\n        if ($children > 0) {\n            throw new HasChildrenException(trans('exceptions.nest.egg.has_children'));\n        }\n\n        return $this->repository->delete($egg);\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/EggParserService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs;\n\nuse Illuminate\\Support\\Arr;\nuse Pterodactyl\\Models\\Egg;\nuse Illuminate\\Http\\UploadedFile;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Exceptions\\Service\\InvalidFileUploadException;\n\nclass EggParserService\n{\n    /**\n     * Takes an uploaded file and parses out the egg configuration from within.\n     *\n     * @throws \\JsonException\n     * @throws InvalidFileUploadException\n     */\n    public function handle(UploadedFile $file): array\n    {\n        if ($file->getError() !== UPLOAD_ERR_OK || !$file->isFile()) {\n            throw new InvalidFileUploadException('The selected file is not valid and cannot be imported.');\n        }\n\n        /** @var array $parsed */\n        $parsed = json_decode($file->openFile()->fread($file->getSize()), true, 512, JSON_THROW_ON_ERROR);\n        if (!in_array(Arr::get($parsed, 'meta.version') ?? '', ['PTDL_v1', 'PTDL_v2'])) {\n            throw new InvalidFileUploadException('The JSON file provided is not in a format that can be recognized.');\n        }\n\n        return $this->convertToV2($parsed);\n    }\n\n    /**\n     * Fills the provided model with the parsed JSON data.\n     */\n    public function fillFromParsed(Egg $model, array $parsed): Egg\n    {\n        return $model->forceFill([\n            'name' => Arr::get($parsed, 'name'),\n            'description' => Arr::get($parsed, 'description'),\n            'features' => Arr::get($parsed, 'features'),\n            'docker_images' => Arr::get($parsed, 'docker_images'),\n            'file_denylist' => Collection::make(Arr::get($parsed, 'file_denylist'))\n                ->filter(fn ($value) => !empty($value)),\n            'update_url' => Arr::get($parsed, 'meta.update_url'),\n            'config_files' => Arr::get($parsed, 'config.files'),\n            'config_startup' => Arr::get($parsed, 'config.startup'),\n            'config_logs' => Arr::get($parsed, 'config.logs'),\n            'config_stop' => Arr::get($parsed, 'config.stop'),\n            'startup' => Arr::get($parsed, 'startup'),\n            'script_install' => Arr::get($parsed, 'scripts.installation.script'),\n            'script_entry' => Arr::get($parsed, 'scripts.installation.entrypoint'),\n            'script_container' => Arr::get($parsed, 'scripts.installation.container'),\n        ]);\n    }\n\n    /**\n     * Converts a PTDL_V1 egg into the expected PTDL_V2 egg format. This just handles\n     * the \"docker_images\" field potentially not being present, and not being in the\n     * expected \"key => value\" format.\n     */\n    protected function convertToV2(array $parsed): array\n    {\n        if (Arr::get($parsed, 'meta.version') === Egg::EXPORT_VERSION) {\n            return $parsed;\n        }\n\n        // Maintain backwards compatability for eggs that are still using the old single image\n        // string format. New eggs can provide an array of Docker images that can be used.\n        if (!isset($parsed['images'])) {\n            $images = [Arr::get($parsed, 'image') ?? 'nil'];\n        } else {\n            $images = $parsed['images'];\n        }\n\n        unset($parsed['images'], $parsed['image']);\n\n        $parsed['docker_images'] = [];\n        foreach ($images as $image) {\n            $parsed['docker_images'][$image] = $image;\n        }\n\n        $parsed['variables'] = array_map(function ($value) {\n            return array_merge($value, ['field_type' => 'text']);\n        }, $parsed['variables']);\n\n        return $parsed;\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/EggUpdateService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs;\n\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Contracts\\Repository\\EggRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\Egg\\NoParentConfigurationFoundException;\n\nclass EggUpdateService\n{\n    /**\n     * EggUpdateService constructor.\n     */\n    public function __construct(protected EggRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Update a service option.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws NoParentConfigurationFoundException\n     */\n    public function handle(Egg $egg, array $data): void\n    {\n        if (!is_null(array_get($data, 'config_from'))) {\n            $results = $this->repository->findCountWhere([\n                ['nest_id', '=', $egg->nest_id],\n                ['id', '=', array_get($data, 'config_from')],\n            ]);\n\n            if ($results !== 1) {\n                throw new NoParentConfigurationFoundException(trans('exceptions.nest.egg.must_be_child'));\n            }\n        }\n\n        // TODO(dane): Once the admin UI is done being reworked and this is exposed\n        //  in said UI, remove this so that you can actually update the denylist.\n        unset($data['file_denylist']);\n\n        $this->repository->withoutFreshModel()->update($egg->id, $data);\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/Scripts/InstallScriptService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs\\Scripts;\n\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Contracts\\Repository\\EggRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\Egg\\InvalidCopyFromException;\n\nclass InstallScriptService\n{\n    /**\n     * InstallScriptService constructor.\n     */\n    public function __construct(protected EggRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Modify the install script for a given Egg.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws InvalidCopyFromException\n     */\n    public function handle(Egg $egg, array $data): void\n    {\n        if (!is_null(array_get($data, 'copy_script_from'))) {\n            if (!$this->repository->isCopyableScript(array_get($data, 'copy_script_from'), $egg->nest_id)) {\n                throw new InvalidCopyFromException(trans('exceptions.nest.egg.invalid_copy_id'));\n            }\n        }\n\n        $this->repository->withoutFreshModel()->update($egg->id, [\n            'script_install' => array_get($data, 'script_install'),\n            'script_is_privileged' => array_get($data, 'script_is_privileged', 1),\n            'script_entry' => array_get($data, 'script_entry'),\n            'script_container' => array_get($data, 'script_container'),\n            'copy_script_from' => array_get($data, 'copy_script_from'),\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/Sharing/EggExporterService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs\\Sharing;\n\nuse Carbon\\Carbon;\nuse Pterodactyl\\Models\\Egg;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Models\\EggVariable;\nuse Pterodactyl\\Contracts\\Repository\\EggRepositoryInterface;\n\nclass EggExporterService\n{\n    /**\n     * EggExporterService constructor.\n     */\n    public function __construct(protected EggRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Return a JSON representation of an egg and its variables.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function handle(int $egg): string\n    {\n        $egg = $this->repository->getWithExportAttributes($egg);\n\n        $struct = [\n            '_comment' => 'DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO',\n            'meta' => [\n                'version' => Egg::EXPORT_VERSION,\n                'update_url' => $egg->update_url,\n            ],\n            'exported_at' => Carbon::now()->toAtomString(),\n            'name' => $egg->name,\n            'author' => $egg->author,\n            'description' => $egg->description,\n            'features' => $egg->features,\n            'docker_images' => $egg->docker_images,\n            'file_denylist' => Collection::make($egg->inherit_file_denylist)->filter(function ($value) {\n                return !empty($value);\n            }),\n            'startup' => $egg->startup,\n            'config' => [\n                'files' => $egg->inherit_config_files,\n                'startup' => $egg->inherit_config_startup,\n                'logs' => $egg->inherit_config_logs,\n                'stop' => $egg->inherit_config_stop,\n            ],\n            'scripts' => [\n                'installation' => [\n                    'script' => $egg->copy_script_install,\n                    'container' => $egg->copy_script_container,\n                    'entrypoint' => $egg->copy_script_entry,\n                ],\n            ],\n            'variables' => $egg->variables->transform(function (EggVariable $item) {\n                return Collection::make($item->toArray())\n                    ->except(['id', 'egg_id', 'created_at', 'updated_at'])\n                    ->merge(['field_type' => 'text'])\n                    ->toArray();\n            }),\n        ];\n\n        return json_encode($struct, JSON_PRETTY_PRINT);\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/Sharing/EggImporterService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs\\Sharing;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Arr;\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\Nest;\nuse Illuminate\\Http\\UploadedFile;\nuse Pterodactyl\\Models\\EggVariable;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Services\\Eggs\\EggParserService;\n\nclass EggImporterService\n{\n    public function __construct(protected ConnectionInterface $connection, protected EggParserService $parser)\n    {\n    }\n\n    /**\n     * Take an uploaded JSON file and parse it into a new egg.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\InvalidFileUploadException|\\Throwable\n     */\n    public function handle(UploadedFile $file, int $nest): Egg\n    {\n        $parsed = $this->parser->handle($file);\n\n        /** @var Nest $nest */\n        $nest = Nest::query()->with('eggs', 'eggs.variables')->findOrFail($nest);\n\n        return $this->connection->transaction(function () use ($nest, $parsed) {\n            $egg = (new Egg())->forceFill([\n                'uuid' => Uuid::uuid4()->toString(),\n                'nest_id' => $nest->id,\n                'author' => Arr::get($parsed, 'author'),\n                'copy_script_from' => null,\n            ]);\n\n            $egg = $this->parser->fillFromParsed($egg, $parsed);\n            $egg->save();\n\n            foreach ($parsed['variables'] ?? [] as $variable) {\n                EggVariable::query()->forceCreate(array_merge($variable, ['egg_id' => $egg->id]));\n            }\n\n            return $egg;\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/Sharing/EggUpdateImporterService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs\\Sharing;\n\nuse Pterodactyl\\Models\\Egg;\nuse Illuminate\\Http\\UploadedFile;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Models\\EggVariable;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Services\\Eggs\\EggParserService;\n\nclass EggUpdateImporterService\n{\n    /**\n     * EggUpdateImporterService constructor.\n     */\n    public function __construct(protected ConnectionInterface $connection, protected EggParserService $parser)\n    {\n    }\n\n    /**\n     * Update an existing Egg using an uploaded JSON file.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Service\\InvalidFileUploadException|\\Throwable\n     */\n    public function handle(Egg $egg, UploadedFile $file): Egg\n    {\n        $parsed = $this->parser->handle($file);\n\n        return $this->connection->transaction(function () use ($egg, $parsed) {\n            $egg = $this->parser->fillFromParsed($egg, $parsed);\n            $egg->save();\n\n            // Update existing variables or create new ones.\n            foreach ($parsed['variables'] ?? [] as $variable) {\n                EggVariable::unguarded(function () use ($egg, $variable) {\n                    $egg->variables()->updateOrCreate([\n                        'env_variable' => $variable['env_variable'],\n                    ], Collection::make($variable)->except('egg_id', 'env_variable')->toArray());\n                });\n            }\n\n            $imported = array_map(fn ($value) => $value['env_variable'], $parsed['variables'] ?? []);\n\n            $egg->variables()->whereNotIn('env_variable', $imported)->delete();\n\n            return $egg->refresh();\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/Variables/VariableCreationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs\\Variables;\n\nuse Pterodactyl\\Models\\EggVariable;\nuse Pterodactyl\\Traits\\Services\\ValidatesValidationRules;\nuse Illuminate\\Contracts\\Validation\\Factory as ValidationFactory;\nuse Pterodactyl\\Contracts\\Repository\\EggVariableRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\Egg\\Variable\\ReservedVariableNameException;\n\nclass VariableCreationService\n{\n    use ValidatesValidationRules;\n\n    /**\n     * VariableCreationService constructor.\n     */\n    public function __construct(private EggVariableRepositoryInterface $repository, private ValidationFactory $validator)\n    {\n    }\n\n    /**\n     * Return the validation factory instance to be used by rule validation\n     * checking in the trait.\n     */\n    protected function getValidator(): ValidationFactory\n    {\n        return $this->validator;\n    }\n\n    /**\n     * Create a new variable for a given Egg.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Egg\\Variable\\BadValidationRuleException\n     * @throws ReservedVariableNameException\n     */\n    public function handle(int $egg, array $data): EggVariable\n    {\n        if (in_array(strtoupper(array_get($data, 'env_variable')), explode(',', EggVariable::RESERVED_ENV_NAMES))) {\n            throw new ReservedVariableNameException(sprintf('Cannot use the protected name %s for this environment variable.', array_get($data, 'env_variable')));\n        }\n\n        if (!empty($data['rules'] ?? '')) {\n            $this->validateRules($data['rules']);\n        }\n\n        $options = array_get($data, 'options') ?? [];\n\n        return $this->repository->create([\n            'egg_id' => $egg,\n            'name' => $data['name'] ?? '',\n            'description' => $data['description'] ?? '',\n            'env_variable' => $data['env_variable'] ?? '',\n            'default_value' => $data['default_value'] ?? '',\n            'user_viewable' => in_array('user_viewable', $options),\n            'user_editable' => in_array('user_editable', $options),\n            'rules' => $data['rules'] ?? '',\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Services/Eggs/Variables/VariableUpdateService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Eggs\\Variables;\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\EggVariable;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Traits\\Services\\ValidatesValidationRules;\nuse Illuminate\\Contracts\\Validation\\Factory as ValidationFactory;\nuse Pterodactyl\\Contracts\\Repository\\EggVariableRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\Egg\\Variable\\ReservedVariableNameException;\n\nclass VariableUpdateService\n{\n    use ValidatesValidationRules;\n\n    /**\n     * VariableUpdateService constructor.\n     */\n    public function __construct(private EggVariableRepositoryInterface $repository, private ValidationFactory $validator)\n    {\n    }\n\n    /**\n     * Return the validation factory instance to be used by rule validation\n     * checking in the trait.\n     */\n    protected function getValidator(): ValidationFactory\n    {\n        return $this->validator;\n    }\n\n    /**\n     * Update a specific egg variable.\n     *\n     * @throws DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws ReservedVariableNameException\n     */\n    public function handle(EggVariable $variable, array $data): mixed\n    {\n        if (!is_null(array_get($data, 'env_variable'))) {\n            if (in_array(strtoupper(array_get($data, 'env_variable')), explode(',', EggVariable::RESERVED_ENV_NAMES))) {\n                throw new ReservedVariableNameException(trans('exceptions.service.variables.reserved_name', ['name' => array_get($data, 'env_variable')]));\n            }\n\n            $search = $this->repository->setColumns('id')->findCountWhere([\n                ['env_variable', '=', $data['env_variable']],\n                ['egg_id', '=', $variable->egg_id],\n                ['id', '!=', $variable->id],\n            ]);\n\n            if ($search > 0) {\n                throw new DisplayException(trans('exceptions.service.variables.env_not_unique', ['name' => array_get($data, 'env_variable')]));\n            }\n        }\n\n        if (!empty($data['rules'] ?? '')) {\n            $this->validateRules(\n                (is_string($data['rules']) && Str::contains($data['rules'], ';;'))\n                    ? explode(';;', $data['rules'])\n                    : $data['rules']\n            );\n        }\n\n        $options = array_get($data, 'options') ?? [];\n\n        return $this->repository->withoutFreshModel()->update($variable->id, [\n            'name' => $data['name'] ?? '',\n            'description' => $data['description'] ?? '',\n            'env_variable' => $data['env_variable'] ?? '',\n            'default_value' => $data['default_value'] ?? '',\n            'user_viewable' => in_array('user_viewable', $options),\n            'user_editable' => in_array('user_editable', $options),\n            'rules' => $data['rules'] ?? '',\n        ]);\n    }\n}\n"
  },
  {
    "path": "app/Services/Helpers/AssetHashService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Helpers;\n\nuse Illuminate\\Support\\Arr;\nuse Illuminate\\Filesystem\\FilesystemManager;\nuse Illuminate\\Contracts\\Filesystem\\Filesystem;\nuse Pterodactyl\\Exceptions\\ManifestDoesNotExistException;\n\nclass AssetHashService\n{\n    /**\n     * Location of the manifest file generated by gulp.\n     */\n    public const MANIFEST_PATH = './assets/manifest.json';\n\n    private Filesystem $filesystem;\n\n    protected static mixed $manifest = null;\n\n    /**\n     * AssetHashService constructor.\n     */\n    public function __construct(FilesystemManager $filesystem)\n    {\n        $this->filesystem = $filesystem->createLocalDriver(['root' => public_path()]);\n    }\n\n    /**\n     * Modify a URL to append the asset hash.\n     */\n    public function url(string $resource): string\n    {\n        $file = last(explode('/', $resource));\n        $data = Arr::get($this->manifest(), $file) ?? $file;\n\n        return str_replace($file, Arr::get($data, 'src') ?? $file, $resource);\n    }\n\n    /**\n     * Return the data integrity hash for a resource.\n     */\n    public function integrity(string $resource): string\n    {\n        $file = last(explode('/', $resource));\n        $data = array_get($this->manifest(), $file, $file);\n\n        return Arr::get($data, 'integrity') ?? '';\n    }\n\n    /**\n     * Return a built CSS import using the provided URL.\n     */\n    public function css(string $resource): string\n    {\n        $attributes = [\n            'href' => $this->url($resource),\n            'rel' => 'stylesheet preload',\n            'as' => 'style',\n            'crossorigin' => 'anonymous',\n            'referrerpolicy' => 'no-referrer',\n        ];\n\n        if (config('pterodactyl.assets.use_hash')) {\n            $attributes['integrity'] = $this->integrity($resource);\n        }\n\n        $output = '<link';\n        foreach ($attributes as $key => $value) {\n            $output .= \" $key=\\\"$value\\\"\";\n        }\n\n        return $output . '>';\n    }\n\n    /**\n     * Return a built JS import using the provided URL.\n     */\n    public function js(string $resource): string\n    {\n        $attributes = [\n            'src' => $this->url($resource),\n            'crossorigin' => 'anonymous',\n        ];\n\n        if (config('pterodactyl.assets.use_hash')) {\n            $attributes['integrity'] = $this->integrity($resource);\n        }\n\n        $output = '<script';\n        foreach ($attributes as $key => $value) {\n            $output .= \" $key=\\\"$value\\\"\";\n        }\n\n        return $output . '></script>';\n    }\n\n    /**\n     * Get the asset manifest and store it in the cache for quicker lookups.\n     */\n    protected function manifest(): array\n    {\n        if (static::$manifest === null) {\n            self::$manifest = json_decode(\n                $this->filesystem->get(self::MANIFEST_PATH),\n                true\n            );\n        }\n\n        $manifest = static::$manifest;\n        if ($manifest === null) {\n            throw new ManifestDoesNotExistException();\n        }\n\n        return $manifest;\n    }\n}\n"
  },
  {
    "path": "app/Services/Helpers/SoftwareVersionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Helpers;\n\nuse GuzzleHttp\\Client;\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Support\\Arr;\nuse Illuminate\\Contracts\\Cache\\Repository as CacheRepository;\nuse Pterodactyl\\Exceptions\\Service\\Helper\\CdnVersionFetchingException;\n\nclass SoftwareVersionService\n{\n    public const VERSION_CACHE_KEY = 'pterodactyl:versioning_data';\n\n    private static array $result;\n\n    /**\n     * SoftwareVersionService constructor.\n     */\n    public function __construct(\n        protected CacheRepository $cache,\n        protected Client $client,\n    ) {\n        self::$result = $this->cacheVersionData();\n    }\n\n    /**\n     * Get the latest version of the panel from the CDN servers.\n     */\n    public function getPanel(): string\n    {\n        return Arr::get(self::$result, 'panel') ?? 'error';\n    }\n\n    /**\n     * Get the latest version of the daemon from the CDN servers.\n     */\n    public function getDaemon(): string\n    {\n        return Arr::get(self::$result, 'wings') ?? 'error';\n    }\n\n    /**\n     * Get the URL to the discord server.\n     */\n    public function getDiscord(): string\n    {\n        return Arr::get(self::$result, 'discord') ?? 'https://pterodactyl.io/discord';\n    }\n\n    /**\n     * Get the URL for donations.\n     */\n    public function getDonations(): string\n    {\n        return Arr::get(self::$result, 'donations') ?? 'https://afdian.net/a/vlssu';\n    }\n\n    /**\n     * Determine if the current version of the panel is the latest.\n     */\n    public function isLatestPanel(): bool\n    {\n        if (config('app.version') === 'canary') {\n            return true;\n        }\n\n        return version_compare(config('app.version'), $this->getPanel()) >= 0;\n    }\n\n    /**\n     * Determine if a passed daemon version string is the latest.\n     */\n    public function isLatestDaemon(string $version): bool\n    {\n        if ($version === 'develop') {\n            return true;\n        }\n\n        return version_compare($version, $this->getDaemon()) >= 0;\n    }\n\n    /**\n     * Keeps the versioning cache up-to-date with the latest results from the CDN.\n     */\n    protected function cacheVersionData(): array\n    {\n        return $this->cache->remember(self::VERSION_CACHE_KEY, CarbonImmutable::now()->addMinutes(config('pterodactyl.cdn.cache_time', 60)), function () {\n            try {\n                $response = $this->client->request('GET', config('pterodactyl.cdn.url'));\n\n                if ($response->getStatusCode() === 200) {\n                    return json_decode($response->getBody(), true);\n                }\n\n                throw new CdnVersionFetchingException();\n            } catch (\\Exception) {\n                return [];\n            }\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Locations/LocationCreationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Locations;\n\nuse Pterodactyl\\Models\\Location;\nuse Pterodactyl\\Contracts\\Repository\\LocationRepositoryInterface;\n\nclass LocationCreationService\n{\n    /**\n     * LocationCreationService constructor.\n     */\n    public function __construct(protected LocationRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Create a new location.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function handle(array $data): Location\n    {\n        return $this->repository->create($data);\n    }\n}\n"
  },
  {
    "path": "app/Services/Locations/LocationDeletionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Locations;\n\nuse Pterodactyl\\Models\\Location;\nuse Pterodactyl\\Contracts\\Repository\\NodeRepositoryInterface;\nuse Pterodactyl\\Contracts\\Repository\\LocationRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\Location\\HasActiveNodesException;\n\nclass LocationDeletionService\n{\n    /**\n     * LocationDeletionService constructor.\n     */\n    public function __construct(\n        protected LocationRepositoryInterface $repository,\n        protected NodeRepositoryInterface $nodeRepository,\n    ) {\n    }\n\n    /**\n     * Delete an existing location.\n     *\n     * @throws HasActiveNodesException\n     */\n    public function handle(Location|int $location): ?int\n    {\n        $location = $location instanceof Location ? $location->id : $location;\n\n        $count = $this->nodeRepository->findCountWhere([['location_id', '=', $location]]);\n        if ($count > 0) {\n            throw new HasActiveNodesException(trans('exceptions.locations.has_nodes'));\n        }\n\n        return $this->repository->delete($location);\n    }\n}\n"
  },
  {
    "path": "app/Services/Locations/LocationUpdateService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Locations;\n\nuse Pterodactyl\\Models\\Location;\nuse Pterodactyl\\Contracts\\Repository\\LocationRepositoryInterface;\n\nclass LocationUpdateService\n{\n    /**\n     * LocationUpdateService constructor.\n     */\n    public function __construct(protected LocationRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Update an existing location.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function handle(Location|int $location, array $data): Location\n    {\n        $location = ($location instanceof Location) ? $location->id : $location;\n\n        return $this->repository->update($location, $data);\n    }\n}\n"
  },
  {
    "path": "app/Services/Nests/NestCreationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Nests;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Pterodactyl\\Models\\Nest;\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\nuse Illuminate\\Contracts\\Config\\Repository as ConfigRepository;\n\nclass NestCreationService\n{\n    /**\n     * NestCreationService constructor.\n     */\n    public function __construct(private ConfigRepository $config, private NestRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Create a new nest on the system.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function handle(array $data, ?string $author = null): Nest\n    {\n        return $this->repository->create([\n            'uuid' => Uuid::uuid4()->toString(),\n            'author' => $author ?? $this->config->get('pterodactyl.service.author'),\n            'name' => array_get($data, 'name'),\n            'description' => array_get($data, 'description'),\n        ], true, true);\n    }\n}\n"
  },
  {
    "path": "app/Services/Nests/NestDeletionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Nests;\n\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\HasActiveServersException;\nuse Pterodactyl\\Contracts\\Repository\\ServerRepositoryInterface;\n\nclass NestDeletionService\n{\n    /**\n     * NestDeletionService constructor.\n     */\n    public function __construct(\n        protected ServerRepositoryInterface $serverRepository,\n        protected NestRepositoryInterface $repository,\n    ) {\n    }\n\n    /**\n     * Delete a nest from the system only if there are no servers attached to it.\n     *\n     * @throws HasActiveServersException\n     */\n    public function handle(int $nest): int\n    {\n        $count = $this->serverRepository->findCountWhere([['nest_id', '=', $nest]]);\n        if ($count > 0) {\n            throw new HasActiveServersException(trans('exceptions.nest.delete_has_servers'));\n        }\n\n        return $this->repository->delete($nest);\n    }\n}\n"
  },
  {
    "path": "app/Services/Nests/NestUpdateService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Nests;\n\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\n\nclass NestUpdateService\n{\n    /**\n     * NestUpdateService constructor.\n     */\n    public function __construct(protected NestRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Update a nest and prevent changing the author once it is set.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function handle(int $nest, array $data): void\n    {\n        if (!is_null(array_get($data, 'author'))) {\n            unset($data['author']);\n        }\n\n        $this->repository->withoutFreshModel()->update($nest, $data);\n    }\n}\n"
  },
  {
    "path": "app/Services/Nodes/NodeCreationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Nodes;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Contracts\\Repository\\NodeRepositoryInterface;\n\nclass NodeCreationService\n{\n    /**\n     * NodeCreationService constructor.\n     */\n    public function __construct(protected NodeRepositoryInterface $repository)\n    {\n    }\n\n    /**\n     * Create a new node on the panel.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function handle(array $data): Node\n    {\n        $data['uuid'] = Uuid::uuid4()->toString();\n        $data['daemon_token'] = app(Encrypter::class)->encrypt(Str::random(Node::DAEMON_TOKEN_LENGTH));\n        $data['daemon_token_id'] = Str::random(Node::DAEMON_TOKEN_ID_LENGTH);\n\n        return $this->repository->create($data, true, true);\n    }\n}\n"
  },
  {
    "path": "app/Services/Nodes/NodeDeletionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Nodes;\n\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Contracts\\Translation\\Translator;\nuse Pterodactyl\\Contracts\\Repository\\NodeRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Service\\HasActiveServersException;\nuse Pterodactyl\\Contracts\\Repository\\ServerRepositoryInterface;\n\nclass NodeDeletionService\n{\n    /**\n     * NodeDeletionService constructor.\n     */\n    public function __construct(\n        protected NodeRepositoryInterface $repository,\n        protected ServerRepositoryInterface $serverRepository,\n        protected Translator $translator,\n    ) {\n    }\n\n    /**\n     * Delete a node from the panel if no servers are attached to it.\n     *\n     * @throws HasActiveServersException\n     */\n    public function handle(int|Node $node): int\n    {\n        if ($node instanceof Node) {\n            $node = $node->id;\n        }\n\n        $servers = $this->serverRepository->setColumns('id')->findCountWhere([['node_id', '=', $node]]);\n        if ($servers > 0) {\n            throw new HasActiveServersException($this->translator->get('exceptions.node.servers_attached'));\n        }\n\n        return $this->repository->delete($node);\n    }\n}\n"
  },
  {
    "path": "app/Services/Nodes/NodeJWTService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Nodes;\n\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\User;\nuse Lcobucci\\JWT\\Configuration;\nuse Lcobucci\\JWT\\UnencryptedToken;\nuse Lcobucci\\JWT\\Signer\\Hmac\\Sha256;\nuse Lcobucci\\JWT\\Signer\\Key\\InMemory;\nuse Pterodactyl\\Extensions\\Lcobucci\\JWT\\Encoding\\TimestampDates;\n\nclass NodeJWTService\n{\n    private array $claims = [];\n\n    private ?User $user = null;\n\n    private \\DateTimeImmutable $expiresAt;\n\n    private ?string $subject = null;\n\n    /**\n     * Set the claims to include in this JWT.\n     */\n    public function setClaims(array $claims): self\n    {\n        $this->claims = $claims;\n\n        return $this;\n    }\n\n    /**\n     * Attaches a user to the JWT being created and will automatically inject the\n     * \"user_uuid\" key into the final claims array with the user's UUID.\n     */\n    public function setUser(User $user): self\n    {\n        $this->user = $user;\n\n        return $this;\n    }\n\n    public function setExpiresAt(\\DateTimeImmutable $date): self\n    {\n        $this->expiresAt = $date;\n\n        return $this;\n    }\n\n    public function setSubject(string $subject): self\n    {\n        $this->subject = $subject;\n\n        return $this;\n    }\n\n    /**\n     * Generate a new JWT for a given node.\n     */\n    public function handle(Node $node, ?string $identifiedBy, string $algo = 'md5'): UnencryptedToken\n    {\n        $identifier = hash($algo, $identifiedBy);\n        $config = Configuration::forSymmetricSigner(new Sha256(), InMemory::plainText($node->getDecryptedKey()));\n\n        $builder = $config->builder(new TimestampDates())\n            ->issuedBy(config('app.url'))\n            ->permittedFor($node->getConnectionAddress())\n            ->identifiedBy($identifier)\n            ->withHeader('jti', $identifier)\n            ->issuedAt(CarbonImmutable::now())\n            ->canOnlyBeUsedAfter(CarbonImmutable::now()->subMinutes(5));\n\n        if (isset($this->expiresAt)) {\n            $builder = $builder->expiresAt($this->expiresAt);\n        }\n\n        if (!empty($this->subject)) {\n            $builder = $builder->relatedTo($this->subject)->withHeader('sub', $this->subject);\n        }\n\n        foreach ($this->claims as $key => $value) {\n            $builder = $builder->withClaim($key, $value);\n        }\n\n        if (!is_null($this->user)) {\n            $builder = $builder\n                ->withClaim('user_uuid', $this->user->uuid)\n                // The \"user_id\" claim is deprecated and should not be referenced — it remains\n                // here solely to ensure older versions of Wings are unaffected when the Panel\n                // is updated.\n                //\n                // This claim will be removed in Panel@1.11 or later.\n                ->withClaim('user_id', $this->user->id);\n        }\n\n        return $builder\n            ->withClaim('unique_id', Str::random())\n            ->getToken($config->signer(), $config->signingKey());\n    }\n}\n"
  },
  {
    "path": "app/Services/Nodes/NodeUpdateService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Nodes;\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Support\\Facades\\Log;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Repositories\\Eloquent\\NodeRepository;\nuse Pterodactyl\\Repositories\\Wings\\DaemonConfigurationRepository;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\nuse Pterodactyl\\Exceptions\\Service\\Node\\ConfigurationNotPersistedException;\n\nclass NodeUpdateService\n{\n    /**\n     * NodeUpdateService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private DaemonConfigurationRepository $configurationRepository,\n        private Encrypter $encrypter,\n        private NodeRepository $repository,\n    ) {\n    }\n\n    /**\n     * Update the configuration values for a given node on the machine.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(Node $node, array $data, bool $resetToken = false): Node\n    {\n        if ($resetToken) {\n            $data['daemon_token'] = $this->encrypter->encrypt(Str::random(Node::DAEMON_TOKEN_LENGTH));\n            $data['daemon_token_id'] = Str::random(Node::DAEMON_TOKEN_ID_LENGTH);\n        }\n\n        [$updated, $exception] = $this->connection->transaction(function () use ($data, $node) {\n            /** @var Node $updated */\n            $updated = $this->repository->withFreshModel()->update($node->id, $data, true, true);\n\n            try {\n                // If we're changing the FQDN for the node, use the newly provided FQDN for the connection\n                // address. This should alleviate issues where the node gets pointed to a \"valid\" FQDN that\n                // isn't actually running the daemon software, and therefore you can't actually change it\n                // back.\n                //\n                // This makes more sense anyways, because only the Panel uses the FQDN for connecting, the\n                // node doesn't actually care about this.\n                //\n                // @see https://github.com/pterodactyl/panel/issues/1931\n                $node->fqdn = $updated->fqdn;\n\n                $this->configurationRepository->setNode($node)->update($updated);\n            } catch (DaemonConnectionException $exception) {\n                Log::warning($exception, ['node_id' => $node->id]);\n\n                // Never actually throw these exceptions up the stack. If we were able to change the settings\n                // but something went wrong with Wings we just want to store the update and let the user manually\n                // make changes as needed.\n                //\n                // This avoids issues with proxies such as Cloudflare which will see Wings as offline and then\n                // inject their own response pages, causing this logic to get fucked up.\n                //\n                // @see https://github.com/pterodactyl/panel/issues/2712\n                return [$updated, true];\n            }\n\n            return [$updated, false];\n        });\n\n        if ($exception) {\n            throw new ConfigurationNotPersistedException(trans('exceptions.node.daemon_off_config_updated'));\n        }\n\n        return $updated;\n    }\n}\n"
  },
  {
    "path": "app/Services/Schedules/ProcessScheduleService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Schedules;\n\nuse Exception;\nuse Pterodactyl\\Models\\Schedule;\nuse Illuminate\\Contracts\\Bus\\Dispatcher;\nuse Pterodactyl\\Jobs\\Schedule\\RunTaskJob;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass ProcessScheduleService\n{\n    /**\n     * ProcessScheduleService constructor.\n     */\n    public function __construct(private ConnectionInterface $connection, private Dispatcher $dispatcher, private DaemonServerRepository $serverRepository)\n    {\n    }\n\n    /**\n     * Process a schedule and push the first task onto the queue worker.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(Schedule $schedule, bool $now = false): void\n    {\n        $task = $schedule->tasks()->orderBy('sequence_id')->first();\n        if (is_null($task)) {\n            throw new DisplayException('Cannot process schedule for task execution: no tasks are registered.');\n        }\n\n        $this->connection->transaction(function () use ($schedule, $task) {\n            $schedule->forceFill([\n                'is_processing' => true,\n                'next_run_at' => $schedule->getNextRunDate(),\n            ])->saveOrFail();\n\n            $task->update(['is_queued' => true]);\n        });\n\n        $job = new RunTaskJob($task, $now);\n        if ($schedule->only_when_online) {\n            // Check that the server is currently in a starting or running state before executing\n            // this schedule if this option has been set.\n            try {\n                $details = $this->serverRepository->setServer($schedule->server)->getDetails();\n                $state = $details['state'] ?? 'offline';\n                // If the server is stopping or offline just do nothing with this task.\n                if (in_array($state, ['offline', 'stopping'])) {\n                    $job->failed();\n\n                    return;\n                }\n            } catch (\\Exception $exception) {\n                if (!$exception instanceof DaemonConnectionException) {\n                    // If we encountered some exception during this process that wasn't just an\n                    // issue connecting to Wings run the failed sequence for a job. Otherwise we\n                    // can just quietly mark the task as completed without actually running anything.\n                    $job->failed($exception);\n                }\n                $job->failed();\n\n                return;\n            }\n        }\n\n        if (!$now) {\n            $this->dispatcher->dispatch($job->delay($task->time_offset));\n        } else {\n            // When using dispatchNow the RunTaskJob::failed() function is not called automatically\n            // so we need to manually trigger it and then continue with the exception throw.\n            //\n            // @see https://github.com/pterodactyl/panel/issues/2550\n            try {\n                $this->dispatcher->dispatchNow($job);\n            } catch (\\Exception $exception) {\n                $job->failed($exception);\n\n                throw $exception;\n            }\n        }\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/BuildModificationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Illuminate\\Support\\Arr;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Allocation;\nuse Illuminate\\Support\\Facades\\Log;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass BuildModificationService\n{\n    /**\n     * BuildModificationService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private DaemonServerRepository $daemonServerRepository,\n        private ServerConfigurationStructureService $structureService,\n    ) {\n    }\n\n    /**\n     * Change the build details for a specified server.\n     *\n     * @throws \\Throwable\n     * @throws DisplayException\n     */\n    public function handle(Server $server, array $data): Server\n    {\n        /** @var Server $server */\n        $server = $this->connection->transaction(function () use ($server, $data) {\n            $this->processAllocations($server, $data);\n\n            if (isset($data['allocation_id']) && $data['allocation_id'] != $server->allocation_id) {\n                try {\n                    Allocation::query()->where('id', $data['allocation_id'])->where('server_id', $server->id)->firstOrFail();\n                } catch (ModelNotFoundException) {\n                    throw new DisplayException('The requested default allocation is not currently assigned to this server.');\n                }\n            }\n\n            // If any of these values are passed through in the data array go ahead and set\n            // them correctly on the server model.\n            $merge = Arr::only($data, ['oom_disabled', 'memory', 'swap', 'io', 'cpu', 'threads', 'disk', 'allocation_id']);\n\n            $server->forceFill(array_merge($merge, [\n                'database_limit' => Arr::get($data, 'database_limit', 0) ?? null,\n                'allocation_limit' => Arr::get($data, 'allocation_limit', 0) ?? null,\n                'backup_limit' => Arr::get($data, 'backup_limit', 0) ?? 0,\n            ]))->saveOrFail();\n\n            return $server->refresh();\n        });\n\n        $updateData = $this->structureService->handle($server);\n\n        // Because Wings always fetches an updated configuration from the Panel when booting\n        // a server this type of exception can be safely \"ignored\" and just written to the logs.\n        // Ideally this request succeeds, so we can apply resource modifications on the fly, but\n        // if it fails we can just continue on as normal.\n        if (!empty($updateData['build'])) {\n            try {\n                $this->daemonServerRepository->setServer($server)->sync();\n            } catch (DaemonConnectionException $exception) {\n                Log::warning($exception, ['server_id' => $server->id]);\n            }\n        }\n\n        return $server;\n    }\n\n    /**\n     * Process the allocations being assigned in the data and ensure they are available for a server.\n     *\n     * @throws DisplayException\n     */\n    private function processAllocations(Server $server, array &$data): void\n    {\n        if (empty($data['add_allocations']) && empty($data['remove_allocations'])) {\n            return;\n        }\n\n        // Handle the addition of allocations to this server. Only assign allocations that are not currently\n        // assigned to a different server, and only allocations on the same node as the server.\n        if (!empty($data['add_allocations'])) {\n            $query = Allocation::query()\n                ->where('node_id', $server->node_id)\n                ->whereIn('id', $data['add_allocations'])\n                ->whereNull('server_id');\n\n            // Keep track of all the allocations we're just now adding so that we can use the first\n            // one to reset the default allocation to.\n            $freshlyAllocated = $query->pluck('id')->first(); // @phpstan-ignore larastan.noUnnecessaryCollectionCall\n\n            $query->update(['server_id' => $server->id, 'notes' => null]);\n        }\n\n        if (!empty($data['remove_allocations'])) {\n            foreach ($data['remove_allocations'] as $allocation) {\n                // If we are attempting to remove the default allocation for the server, see if we can reassign\n                // to the first provided value in add_allocations. If there is no new first allocation then we\n                // will throw an exception back.\n                if ($allocation === ($data['allocation_id'] ?? $server->allocation_id)) {\n                    if (empty($freshlyAllocated)) {\n                        throw new DisplayException('You are attempting to delete the default allocation for this server but there is no fallback allocation to use.');\n                    }\n\n                    // Update the default allocation to be the first allocation that we are creating.\n                    $data['allocation_id'] = $freshlyAllocated;\n                }\n            }\n\n            // Remove any of the allocations we got that are currently assigned to this server on\n            // this node. Also set the notes to null, otherwise when re-allocated to a new server those\n            // notes will be carried over.\n            Allocation::query()->where('node_id', $server->node_id)\n                ->where('server_id', $server->id)\n                // Only remove the allocations that we didn't also attempt to add to the server...\n                ->whereIn('id', array_diff($data['remove_allocations'], $data['add_allocations'] ?? []))\n                ->update([\n                    'notes' => null,\n                    'server_id' => null,\n                ]);\n        }\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/DetailsModificationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Illuminate\\Support\\Arr;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Jobs\\RevokeSftpAccessJob;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Traits\\Services\\ReturnsUpdatedModels;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Repositories\\Wings\\DaemonRevocationRepository;\n\nclass DetailsModificationService\n{\n    use ReturnsUpdatedModels;\n\n    /**\n     * DetailsModificationService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private DaemonServerRepository $serverRepository,\n        private DaemonRevocationRepository $revocationRepository,\n    ) {\n    }\n\n    /**\n     * Update the details for a single server instance.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(Server $server, array $data): Server\n    {\n        return $this->connection->transaction(function () use ($data, $server) {\n            $original = $server->user;\n\n            $server->forceFill([\n                'external_id' => Arr::get($data, 'external_id'),\n                'owner_id' => Arr::get($data, 'owner_id'),\n                'name' => Arr::get($data, 'name'),\n                'description' => Arr::get($data, 'description') ?? '',\n            ])->saveOrFail();\n\n            // If the owner_id value is changed we need to revoke any tokens that exist for the server\n            // on the Wings instance so that the old owner no longer has any permission to access the\n            // websockets.\n            if (! $server->refresh()->user->is($original)) {\n                RevokeSftpAccessJob::dispatch($original->uuid, $server);\n            }\n\n            return $server;\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/EnvironmentService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\EggVariable;\n\nclass EnvironmentService\n{\n    private array $additional = [];\n\n    /**\n     * Dynamically configure additional environment variables to be assigned\n     * with a specific server.\n     */\n    public function setEnvironmentKey(string $key, callable $closure): void\n    {\n        $this->additional[$key] = $closure;\n    }\n\n    /**\n     * Return the dynamically added additional keys.\n     */\n    public function getEnvironmentKeys(): array\n    {\n        return $this->additional;\n    }\n\n    /**\n     * Take all of the environment variables configured for this server and return\n     * them in an easy to process format.\n     */\n    public function handle(Server $server): array\n    {\n        $variables = $server->variables->toBase()->mapWithKeys(function (EggVariable $variable) {\n            return [$variable->env_variable => $variable->server_value ?? $variable->default_value];\n        });\n\n        // Process environment variables defined in this file. This is done first\n        // in order to allow run-time and config defined variables to take\n        // priority over built-in values.\n        foreach ($this->getEnvironmentMappings() as $key => $object) {\n            $variables->put($key, object_get($server, $object));\n        }\n\n        // Process variables set in the configuration file.\n        foreach (config('pterodactyl.environment_variables', []) as $key => $object) {\n            $variables->put(\n                $key,\n                is_callable($object) ? call_user_func($object, $server) : object_get($server, $object)\n            );\n        }\n\n        // Process dynamically included environment variables.\n        foreach ($this->additional as $key => $closure) {\n            $variables->put($key, call_user_func($closure, $server));\n        }\n\n        return $variables->toArray();\n    }\n\n    /**\n     * Return a mapping of Panel default environment variables.\n     */\n    private function getEnvironmentMappings(): array\n    {\n        return [\n            'STARTUP' => 'startup',\n            'P_SERVER_LOCATION' => 'location.short',\n            'P_SERVER_UUID' => 'uuid',\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/GetUserPermissionsService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\n\nclass GetUserPermissionsService\n{\n    /**\n     * Returns the server specific permissions that a user has. This checks\n     * if they are an admin or a subuser for the server. If no permissions are\n     * found, an empty array is returned.\n     */\n    public function handle(Server $server, User $user): array\n    {\n        if ($user->root_admin || $user->id === $server->owner_id) {\n            $permissions = ['*'];\n\n            if ($user->root_admin) {\n                $permissions[] = 'admin.websocket.errors';\n                $permissions[] = 'admin.websocket.install';\n                $permissions[] = 'admin.websocket.transfer';\n            }\n\n            return $permissions;\n        }\n\n        /** @var \\Pterodactyl\\Models\\Subuser|null $subuserPermissions */\n        $subuserPermissions = $server->subusers()->where('user_id', $user->id)->first();\n\n        return $subuserPermissions ? $subuserPermissions->permissions : [];\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/ReinstallServerService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\n\nclass ReinstallServerService\n{\n    /**\n     * ReinstallService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private DaemonServerRepository $daemonServerRepository,\n    ) {\n    }\n\n    /**\n     * Reinstall a server on the remote daemon.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(Server $server): Server\n    {\n        return $this->connection->transaction(function () use ($server) {\n            $server->fill(['status' => Server::STATUS_INSTALLING])->save();\n\n            $this->daemonServerRepository->setServer($server)->reinstall();\n\n            return $server->refresh();\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/ServerConfigurationStructureService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Pterodactyl\\Models\\Mount;\nuse Pterodactyl\\Models\\Server;\n\nclass ServerConfigurationStructureService\n{\n    /**\n     * ServerConfigurationStructureService constructor.\n     */\n    public function __construct(private EnvironmentService $environment)\n    {\n    }\n\n    /**\n     * Return a configuration array for a specific server when passed a server model.\n     *\n     * DO NOT MODIFY THIS FUNCTION. This powers legacy code handling for the new Wings\n     * daemon, if you modify the structure eggs will break unexpectedly.\n     */\n    public function handle(Server $server, array $override = [], bool $legacy = false): array\n    {\n        $clone = $server;\n        // If any overrides have been set on this call make sure to update them on the\n        // cloned instance so that the configuration generated uses them.\n        if (!empty($override)) {\n            $clone = $server->fresh();\n            foreach ($override as $key => $value) {\n                $clone->setAttribute($key, $value);\n            }\n        }\n\n        return $legacy\n            ? $this->returnLegacyFormat($clone)\n            : $this->returnCurrentFormat($clone);\n    }\n\n    /**\n     * Returns the new data format used for the Wings daemon.\n     */\n    protected function returnCurrentFormat(Server $server): array\n    {\n        return [\n            'uuid' => $server->uuid,\n            'meta' => [\n                'name' => $server->name,\n                'description' => $server->description,\n            ],\n            'suspended' => $server->isSuspended(),\n            'environment' => $this->environment->handle($server),\n            'invocation' => $server->startup,\n            'skip_egg_scripts' => $server->skip_scripts,\n            'build' => [\n                'memory_limit' => $server->memory,\n                'swap' => $server->swap,\n                'io_weight' => $server->io,\n                'cpu_limit' => $server->cpu,\n                'threads' => $server->threads,\n                'disk_space' => $server->disk,\n                'oom_disabled' => $server->oom_disabled,\n            ],\n            'container' => [\n                'image' => $server->image,\n                // This field is deprecated — use the value in the \"build\" block.\n                //\n                // TODO: remove this key in V2.\n                'oom_disabled' => $server->oom_disabled,\n                'requires_rebuild' => false,\n            ],\n            'allocations' => [\n                'force_outgoing_ip' => $server->egg->force_outgoing_ip,\n                'default' => [\n                    'ip' => $server->allocation->ip,\n                    'port' => $server->allocation->port,\n                ],\n                'mappings' => $server->getAllocationMappings(),\n            ],\n            'mounts' => $server->mounts->map(function (Mount $mount) {\n                return [\n                    'source' => $mount->source,\n                    'target' => $mount->target,\n                    'read_only' => $mount->read_only,\n                ];\n            }),\n            'egg' => [\n                'id' => $server->egg->uuid,\n                'file_denylist' => $server->egg->inherit_file_denylist,\n            ],\n        ];\n    }\n\n    /**\n     * Returns the legacy server data format to continue support for old egg configurations\n     * that have not yet been updated.\n     *\n     * @deprecated\n     */\n    protected function returnLegacyFormat(Server $server): array\n    {\n        return [\n            'uuid' => $server->uuid,\n            'build' => [\n                'default' => [\n                    'ip' => $server->allocation->ip,\n                    'port' => $server->allocation->port,\n                ],\n                'ports' => $server->allocations->groupBy('ip')->map(function ($item) {\n                    return $item->pluck('port');\n                })->toArray(),\n                'env' => $this->environment->handle($server),\n                'oom_disabled' => $server->oom_disabled,\n                'memory' => (int) $server->memory,\n                'swap' => (int) $server->swap,\n                'io' => (int) $server->io,\n                'cpu' => (int) $server->cpu,\n                'threads' => $server->threads,\n                'disk' => (int) $server->disk,\n                'image' => $server->image,\n            ],\n            'service' => [\n                'egg' => $server->egg->uuid,\n                'skip_scripts' => $server->skip_scripts,\n            ],\n            'rebuild' => false,\n            'suspended' => $server->isSuspended() ? 1 : 0,\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/ServerCreationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Arr;\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\User;\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Models\\Allocation;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Models\\Objects\\DeploymentObject;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerRepository;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Services\\Deployment\\FindViableNodesService;\nuse Pterodactyl\\Repositories\\Eloquent\\ServerVariableRepository;\nuse Pterodactyl\\Services\\Deployment\\AllocationSelectionService;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass ServerCreationService\n{\n    /**\n     * ServerCreationService constructor.\n     */\n    public function __construct(\n        private AllocationSelectionService $allocationSelectionService,\n        private ConnectionInterface $connection,\n        private DaemonServerRepository $daemonServerRepository,\n        private FindViableNodesService $findViableNodesService,\n        private ServerRepository $repository,\n        private ServerDeletionService $serverDeletionService,\n        private ServerVariableRepository $serverVariableRepository,\n        private VariableValidatorService $validatorService,\n    ) {\n    }\n\n    /**\n     * Create a server on the Panel and trigger a request to the Daemon to begin the server\n     * creation process. This function will attempt to set as many additional values\n     * as possible given the input data. For example, if an allocation_id is passed with\n     * no node_id the node_is will be picked from the allocation.\n     *\n     * @throws \\Throwable\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Illuminate\\Validation\\ValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableNodeException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableAllocationException\n     */\n    public function handle(array $data, ?DeploymentObject $deployment = null): Server\n    {\n        // If a deployment object has been passed we need to get the allocation\n        // that the server should use, and assign the node from that allocation.\n        if ($deployment instanceof DeploymentObject) {\n            $allocation = $this->configureDeployment($data, $deployment);\n            $data['allocation_id'] = $allocation->id;\n            $data['node_id'] = $allocation->node_id;\n        }\n\n        // Auto-configure the node based on the selected allocation\n        // if no node was defined.\n        if (empty($data['node_id'])) {\n            Assert::false(empty($data['allocation_id']), 'Expected a non-empty allocation_id in server creation data.');\n\n            $data['node_id'] = Allocation::query()->findOrFail($data['allocation_id'])->node_id;\n        }\n\n        if (empty($data['nest_id'])) {\n            Assert::false(empty($data['egg_id']), 'Expected a non-empty egg_id in server creation data.');\n\n            $data['nest_id'] = Egg::query()->findOrFail($data['egg_id'])->nest_id;\n        }\n\n        $eggVariableData = $this->validatorService\n            ->setUserLevel(User::USER_LEVEL_ADMIN)\n            ->handle(Arr::get($data, 'egg_id'), Arr::get($data, 'environment', []));\n\n        // Due to the design of the Daemon, we need to persist this server to the disk\n        // before we can actually create it on the Daemon.\n        //\n        // If that connection fails out we will attempt to perform a cleanup by just\n        // deleting the server itself from the system.\n        /** @var Server $server */\n        $server = $this->connection->transaction(function () use ($data, $eggVariableData) {\n            // Create the server and assign any additional allocations to it.\n            $server = $this->createModel($data);\n\n            $this->storeAssignedAllocations($server, $data);\n            $this->storeEggVariables($server, $eggVariableData);\n\n            return $server;\n        }, 5);\n\n        try {\n            $this->daemonServerRepository->setServer($server)->create(\n                Arr::get($data, 'start_on_completion', false) ?? false\n            );\n        } catch (DaemonConnectionException $exception) {\n            $this->serverDeletionService->withForce()->handle($server);\n\n            throw $exception;\n        }\n\n        return $server;\n    }\n\n    /**\n     * Gets an allocation to use for automatic deployment.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableAllocationException\n     * @throws \\Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableNodeException\n     */\n    private function configureDeployment(array $data, DeploymentObject $deployment): Allocation\n    {\n        /** @var Collection $nodes */\n        $nodes = $this->findViableNodesService->setLocations($deployment->getLocations())\n            ->setDisk(Arr::get($data, 'disk'))\n            ->setMemory(Arr::get($data, 'memory'))\n            ->handle();\n\n        return $this->allocationSelectionService->setDedicated($deployment->isDedicated())\n            ->setNodes($nodes->pluck('id')->toArray())\n            ->setPorts($deployment->getPorts())\n            ->handle();\n    }\n\n    /**\n     * Store the server in the database and return the model.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    private function createModel(array $data): Server\n    {\n        $uuid = $this->generateUniqueUuidCombo();\n\n        /** @var Server $model */\n        $model = $this->repository->create([\n            'external_id' => Arr::get($data, 'external_id'),\n            'uuid' => $uuid,\n            'uuidShort' => substr($uuid, 0, 8),\n            'node_id' => Arr::get($data, 'node_id'),\n            'name' => Arr::get($data, 'name'),\n            'description' => Arr::get($data, 'description') ?? '',\n            'status' => Server::STATUS_INSTALLING,\n            'skip_scripts' => Arr::get($data, 'skip_scripts') ?? isset($data['skip_scripts']),\n            'owner_id' => Arr::get($data, 'owner_id'),\n            'memory' => Arr::get($data, 'memory'),\n            'swap' => Arr::get($data, 'swap'),\n            'disk' => Arr::get($data, 'disk'),\n            'io' => Arr::get($data, 'io'),\n            'cpu' => Arr::get($data, 'cpu'),\n            'threads' => Arr::get($data, 'threads'),\n            'oom_disabled' => Arr::get($data, 'oom_disabled') ?? true,\n            'allocation_id' => Arr::get($data, 'allocation_id'),\n            'nest_id' => Arr::get($data, 'nest_id'),\n            'egg_id' => Arr::get($data, 'egg_id'),\n            'startup' => Arr::get($data, 'startup'),\n            'image' => Arr::get($data, 'image'),\n            'database_limit' => Arr::get($data, 'database_limit') ?? 0,\n            'allocation_limit' => Arr::get($data, 'allocation_limit') ?? 0,\n            'backup_limit' => Arr::get($data, 'backup_limit') ?? 0,\n        ]);\n\n        return $model;\n    }\n\n    /**\n     * Configure the allocations assigned to this server.\n     */\n    private function storeAssignedAllocations(Server $server, array $data): void\n    {\n        $records = [$data['allocation_id']];\n        if (isset($data['allocation_additional']) && is_array($data['allocation_additional'])) {\n            $records = array_merge($records, $data['allocation_additional']);\n        }\n\n        Allocation::query()->whereIn('id', $records)->update([\n            'server_id' => $server->id,\n        ]);\n    }\n\n    /**\n     * Process environment variables passed for this server and store them in the database.\n     */\n    private function storeEggVariables(Server $server, Collection $variables): void\n    {\n        $records = $variables->map(function ($result) use ($server) {\n            return [\n                'server_id' => $server->id,\n                'variable_id' => $result->id,\n                'variable_value' => $result->value ?? '',\n            ];\n        })->toArray();\n\n        if (!empty($records)) {\n            $this->serverVariableRepository->insert($records);\n        }\n    }\n\n    /**\n     * Create a unique UUID and UUID-Short combo for a server.\n     */\n    private function generateUniqueUuidCombo(): string\n    {\n        $uuid = Uuid::uuid4()->toString();\n\n        if (!$this->repository->isUniqueUuidCombo($uuid, substr($uuid, 0, 8))) {\n            return $this->generateUniqueUuidCombo();\n        }\n\n        return $uuid;\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/ServerDeletionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Support\\Facades\\Log;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Services\\Databases\\DatabaseManagementService;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass ServerDeletionService\n{\n    protected bool $force = false;\n\n    /**\n     * ServerDeletionService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private DaemonServerRepository $daemonServerRepository,\n        private DatabaseManagementService $databaseManagementService,\n    ) {\n    }\n\n    /**\n     * Set if the server should be forcibly deleted from the panel (ignoring daemon errors) or not.\n     */\n    public function withForce(bool $bool = true): self\n    {\n        $this->force = $bool;\n\n        return $this;\n    }\n\n    /**\n     * Delete a server from the panel, clear any allocation notes, and remove any associated databases from hosts.\n     *\n     * @throws \\Throwable\n     * @throws \\Pterodactyl\\Exceptions\\DisplayException\n     */\n    public function handle(Server $server): void\n    {\n        try {\n            $this->daemonServerRepository->setServer($server)->delete();\n        } catch (DaemonConnectionException $exception) {\n            // If there is an error not caused a 404 error and this isn't a forced delete,\n            // go ahead and bail out. We specifically ignore a 404 since that can be assumed\n            // to be a safe error, meaning the server doesn't exist at all on Wings so there\n            // is no reason we need to bail out from that.\n            if (!$this->force && $exception->getStatusCode() !== Response::HTTP_NOT_FOUND) {\n                throw $exception;\n            }\n\n            Log::warning($exception);\n        }\n\n        $this->connection->transaction(function () use ($server) {\n            foreach ($server->databases as $database) {\n                try {\n                    $this->databaseManagementService->delete($database);\n                } catch (\\Exception $exception) {\n                    if (!$this->force) {\n                        throw $exception;\n                    }\n\n                    // Oh well, just try to delete the database entry we have from the database\n                    // so that the server itself can be deleted. This will leave it dangling on\n                    // the host instance, but we couldn't delete it anyways so not sure how we would\n                    // handle this better anyways.\n                    //\n                    // @see https://github.com/pterodactyl/panel/issues/2085\n                    $database->delete();\n\n                    Log::warning($exception);\n                }\n            }\n\n            // clear any allocation notes for the server\n            $server->allocations()->update(['notes' => null]);\n\n\n            $server->delete();\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/StartupCommandService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Pterodactyl\\Models\\Server;\n\nclass StartupCommandService\n{\n    /**\n     * Generates a startup command for a given server instance.\n     */\n    public function handle(Server $server, bool $hideAllValues = false): string\n    {\n        $find = ['{{SERVER_MEMORY}}', '{{SERVER_IP}}', '{{SERVER_PORT}}'];\n        $replace = [$server->memory, $server->allocation->ip, $server->allocation->port];\n\n        foreach ($server->variables as $variable) {\n            $find[] = '{{' . $variable->env_variable . '}}';\n            $replace[] = ($variable->user_viewable && !$hideAllValues) ? ($variable->server_value ?? $variable->default_value) : '[hidden]';\n        }\n\n        return str_replace($find, $replace, $server->startup);\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/StartupModificationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Illuminate\\Support\\Arr;\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\ServerVariable;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Traits\\Services\\HasUserLevels;\n\nclass StartupModificationService\n{\n    use HasUserLevels;\n\n    /**\n     * StartupModificationService constructor.\n     */\n    public function __construct(private ConnectionInterface $connection, private VariableValidatorService $validatorService)\n    {\n    }\n\n    /**\n     * Process startup modification for a server.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(Server $server, array $data): Server\n    {\n        return $this->connection->transaction(function () use ($server, $data) {\n            if (!empty($data['environment'])) {\n                $egg = $this->isUserLevel(User::USER_LEVEL_ADMIN) ? ($data['egg_id'] ?? $server->egg_id) : $server->egg_id;\n\n                $results = $this->validatorService\n                    ->setUserLevel($this->getUserLevel())\n                    ->handle($egg, $data['environment']);\n\n                foreach ($results as $result) {\n                    ServerVariable::query()->updateOrCreate(\n                        [\n                            'server_id' => $server->id,\n                            'variable_id' => $result->id,\n                        ],\n                        ['variable_value' => $result->value ?? '']\n                    );\n                }\n            }\n\n            if ($this->isUserLevel(User::USER_LEVEL_ADMIN)) {\n                $this->updateAdministrativeSettings($data, $server);\n            }\n\n            // Calling ->refresh() rather than ->fresh() here causes it to return the\n            // variables as triplicates for some reason? Not entirely sure, should dig\n            // in more to figure it out, but luckily we have a test case covering this\n            // specific call so we can be assured we're not breaking it _here_ at least.\n            //\n            // TODO(dane): this seems like a red-flag for the code powering the relationship\n            //  that should be looked into more.\n            return $server->fresh();\n        });\n    }\n\n    /**\n     * Update certain administrative settings for a server in the DB.\n     */\n    protected function updateAdministrativeSettings(array $data, Server &$server): void\n    {\n        $eggId = Arr::get($data, 'egg_id');\n\n        if (is_digit($eggId) && $server->egg_id !== (int) $eggId) {\n            /** @var Egg $egg */\n            $egg = Egg::query()->findOrFail($data['egg_id']);\n\n            $server = $server->forceFill([\n                'egg_id' => $egg->id,\n                'nest_id' => $egg->nest_id,\n            ]);\n        }\n\n        $server->fill([\n            'startup' => $data['startup'] ?? $server->startup,\n            'skip_scripts' => $data['skip_scripts'] ?? isset($data['skip_scripts']),\n            'image' => $data['docker_image'] ?? $server->image,\n        ])->save();\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/SuspensionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Symfony\\Component\\HttpKernel\\Exception\\ConflictHttpException;\n\nclass SuspensionService\n{\n    public const ACTION_SUSPEND = 'suspend';\n    public const ACTION_UNSUSPEND = 'unsuspend';\n\n    /**\n     * SuspensionService constructor.\n     */\n    public function __construct(\n        private DaemonServerRepository $daemonServerRepository,\n    ) {\n    }\n\n    /**\n     * Suspends a server on the system.\n     *\n     * @throws \\Throwable\n     */\n    public function toggle(Server $server, string $action = self::ACTION_SUSPEND): void\n    {\n        Assert::oneOf($action, [self::ACTION_SUSPEND, self::ACTION_UNSUSPEND]);\n\n        $isSuspending = $action === self::ACTION_SUSPEND;\n        // Nothing needs to happen if we're suspending the server, and it is already\n        // suspended in the database. Additionally, nothing needs to happen if the server\n        // is not suspended, and we try to un-suspend the instance.\n        if ($isSuspending === $server->isSuspended()) {\n            return;\n        }\n\n        // Check if the server is currently being transferred.\n        if (!is_null($server->transfer)) {\n            throw new ConflictHttpException('Cannot toggle suspension status on a server that is currently being transferred.');\n        }\n\n        // Update the server's suspension status.\n        $server->update([\n            'status' => $isSuspending ? Server::STATUS_SUSPENDED : null,\n        ]);\n\n        try {\n            // Tell wings to re-sync the server state.\n            $this->daemonServerRepository->setServer($server)->sync();\n        } catch (\\Exception $exception) {\n            // Rollback the server's suspension status if wings fails to sync the server.\n            $server->update([\n                'status' => $isSuspending ? null : Server::STATUS_SUSPENDED,\n            ]);\n            throw $exception;\n        }\n    }\n}\n"
  },
  {
    "path": "app/Services/Servers/VariableValidatorService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Servers;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Models\\EggVariable;\nuse Illuminate\\Validation\\ValidationException;\nuse Pterodactyl\\Traits\\Services\\HasUserLevels;\nuse Illuminate\\Contracts\\Validation\\Factory as ValidationFactory;\n\nclass VariableValidatorService\n{\n    use HasUserLevels;\n\n    /**\n     * VariableValidatorService constructor.\n     */\n    public function __construct(private ValidationFactory $validator)\n    {\n    }\n\n    /**\n     * Validate all of the passed data against the given service option variables.\n     *\n     * @throws ValidationException\n     */\n    public function handle(int $egg, array $fields = []): Collection\n    {\n        $query = EggVariable::query()->where('egg_id', $egg);\n        if (!$this->isUserLevel(User::USER_LEVEL_ADMIN)) {\n            // Don't attempt to validate variables if they aren't user editable,\n            // and we're not running this at an admin level.\n            $query = $query->where('user_editable', true)->where('user_viewable', true);\n        }\n\n        /** @var \\Pterodactyl\\Models\\EggVariable[] $variables */\n        $variables = $query->get();\n\n        $data = $rules = $customAttributes = [];\n        foreach ($variables as $variable) {\n            $data['environment'][$variable->env_variable] = array_get($fields, $variable->env_variable);\n            $rules['environment.' . $variable->env_variable] = $variable->rules;\n            $customAttributes['environment.' . $variable->env_variable] = trans('validation.internal.variable_value', ['env' => $variable->name]);\n        }\n\n        $validator = $this->validator->make($data, $rules, [], $customAttributes);\n        if ($validator->fails()) {\n            throw new ValidationException($validator);\n        }\n\n        return Collection::make($variables)->map(function ($item) use ($fields) {\n            return (object) [\n                'id' => $item->id,\n                'key' => $item->env_variable,\n                'value' => $fields[$item->env_variable] ?? null,\n            ];\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Subusers/SubuserCreationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Subusers;\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Subuser;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Pterodactyl\\Services\\Users\\UserCreationService;\nuse Pterodactyl\\Repositories\\Eloquent\\SubuserRepository;\nuse Pterodactyl\\Contracts\\Repository\\UserRepositoryInterface;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\nuse Pterodactyl\\Exceptions\\Service\\Subuser\\UserIsServerOwnerException;\nuse Pterodactyl\\Exceptions\\Service\\Subuser\\ServerSubuserExistsException;\n\nclass SubuserCreationService\n{\n    /**\n     * SubuserCreationService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private SubuserRepository $subuserRepository,\n        private UserCreationService $userCreationService,\n        private UserRepositoryInterface $userRepository,\n    ) {\n    }\n\n    /**\n     * Creates a new user on the system and assigns them access to the provided server.\n     * If the email address already belongs to a user on the system a new user will not\n     * be created.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws ServerSubuserExistsException\n     * @throws UserIsServerOwnerException\n     * @throws \\Throwable\n     */\n    public function handle(Server $server, string $email, array $permissions): Subuser\n    {\n        return $this->connection->transaction(function () use ($server, $email, $permissions) {\n            try {\n                $user = $this->userRepository->findFirstWhere([['email', '=', $email]]);\n\n                if ($server->owner_id === $user->id) {\n                    throw new UserIsServerOwnerException(trans('exceptions.subusers.user_is_owner'));\n                }\n\n                $subuserCount = $this->subuserRepository->findCountWhere([['user_id', '=', $user->id], ['server_id', '=', $server->id]]);\n                if ($subuserCount !== 0) {\n                    throw new ServerSubuserExistsException(trans('exceptions.subusers.subuser_exists'));\n                }\n            } catch (RecordNotFoundException) {\n                // Just cap the username generated at 64 characters at most and then append a random string\n                // to the end to make it \"unique\"...\n                $username = substr(preg_replace('/([^\\w\\.-]+)/', '', strtok($email, '@')), 0, 64) . Str::random(3);\n\n                $user = $this->userCreationService->handle([\n                    'email' => $email,\n                    'username' => $username,\n                    'name_first' => '服务器',\n                    'name_last' => '子用户',\n                    'root_admin' => false,\n                ]);\n            }\n\n            return $this->subuserRepository->create([\n                'user_id' => $user->id,\n                'server_id' => $server->id,\n                'permissions' => array_unique($permissions),\n            ]);\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Telemetry/TelemetryCollectionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Telemetry;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Arr;\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\Nest;\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Mount;\nuse Pterodactyl\\Models\\Backup;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Location;\nuse Illuminate\\Support\\Facades\\DB;\nuse Pterodactyl\\Models\\Allocation;\nuse Illuminate\\Support\\Facades\\Http;\nuse Pterodactyl\\Repositories\\Eloquent\\SettingsRepository;\nuse Pterodactyl\\Repositories\\Wings\\DaemonConfigurationRepository;\n\nclass TelemetryCollectionService\n{\n    /**\n     * TelemetryCollectionService constructor.\n     */\n    public function __construct(\n        private DaemonConfigurationRepository $daemonConfigurationRepository,\n        private SettingsRepository $settingsRepository,\n    ) {\n    }\n\n    /**\n     * Collects telemetry data and sends it to the Pterodactyl Telemetry Service.\n     */\n    public function __invoke(): void\n    {\n        try {\n            $data = $this->collect();\n        } catch (\\Exception) {\n            return;\n        }\n\n        Http::post('https://telemetry.pterodactyl.io', $data);\n    }\n\n    /**\n     * Collects telemetry data and returns it as an array.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function collect(): array\n    {\n        $uuid = $this->settingsRepository->get('app:telemetry:uuid');\n        if (is_null($uuid)) {\n            $uuid = Uuid::uuid4()->toString();\n            $this->settingsRepository->set('app:telemetry:uuid', $uuid);\n        }\n\n        $nodes = Node::all()->map(function ($node) {\n            try {\n                $info = $this->daemonConfigurationRepository->setNode($node)->getSystemInformation(2);\n            } catch (\\Exception) {\n                return null;\n            }\n\n            return [\n                'id' => $node->uuid,\n                'version' => Arr::get($info, 'version', ''),\n\n                'docker' => [\n                    'version' => Arr::get($info, 'docker.version', ''),\n\n                    'cgroups' => [\n                        'driver' => Arr::get($info, 'docker.cgroups.driver', ''),\n                        'version' => Arr::get($info, 'docker.cgroups.version', ''),\n                    ],\n\n                    'containers' => [\n                        'total' => Arr::get($info, 'docker.containers.total', -1),\n                        'running' => Arr::get($info, 'docker.containers.running', -1),\n                        'paused' => Arr::get($info, 'docker.containers.paused', -1),\n                        'stopped' => Arr::get($info, 'docker.containers.stopped', -1),\n                    ],\n\n                    'storage' => [\n                        'driver' => Arr::get($info, 'docker.storage.driver', ''),\n                        'filesystem' => Arr::get($info, 'docker.storage.filesystem', ''),\n                    ],\n\n                    'runc' => [\n                        'version' => Arr::get($info, 'docker.runc.version', ''),\n                    ],\n                ],\n\n                'system' => [\n                    'architecture' => Arr::get($info, 'system.architecture', ''),\n                    'cpuThreads' => Arr::get($info, 'system.cpu_threads', ''),\n                    'memoryBytes' => Arr::get($info, 'system.memory_bytes', ''),\n                    'kernelVersion' => Arr::get($info, 'system.kernel_version', ''),\n                    'os' => Arr::get($info, 'system.os', ''),\n                    'osType' => Arr::get($info, 'system.os_type', ''),\n                ],\n            ];\n        })->filter(fn ($node) => !is_null($node))->toArray();\n\n        return [\n            'id' => $uuid,\n\n            'panel' => [\n                'version' => config('app.version'),\n                'phpVersion' => phpversion(),\n\n                'drivers' => [\n                    'backup' => [\n                        'type' => config('backups.default'),\n                    ],\n\n                    'cache' => [\n                        'type' => config('cache.default'),\n                    ],\n\n                    'database' => [\n                        'type' => config('database.default'),\n                        'version' => DB::getPdo()->getAttribute(\\PDO::ATTR_SERVER_VERSION),\n                    ],\n                ],\n            ],\n\n            'resources' => [\n                'allocations' => [\n                    'count' => Allocation::count(),\n                    'used' => Allocation::whereNotNull('server_id')->count(),\n                ],\n\n                'backups' => [\n                    'count' => Backup::count(),\n                    'bytes' => Backup::sum('bytes'),\n                ],\n\n                'eggs' => [\n                    'count' => Egg::count(),\n                    // Egg UUIDs are generated randomly on import, so there is not a consistent way to\n                    // determine if servers are using default eggs or not.\n                    //                    'server_usage' => Egg::all()\n                    //                        ->flatMap(fn (Egg $egg) => [$egg->uuid => $egg->servers->count()])\n                    //                        ->filter(fn (int $count) => $count > 0)\n                    //                        ->toArray(),\n                ],\n\n                'locations' => [\n                    'count' => Location::count(),\n                ],\n\n                'mounts' => [\n                    'count' => Mount::count(),\n                ],\n\n                'nests' => [\n                    'count' => Nest::count(),\n                    // Nest UUIDs are generated randomly on import, so there is not a consistent way to\n                    // determine if servers are using default eggs or not.\n                    //                    'server_usage' => Nest::all()\n                    //                        ->flatMap(fn (Nest $nest) => [$nest->uuid => $nest->eggs->sum(fn (Egg $egg) => $egg->servers->count())])\n                    //                        ->filter(fn (int $count) => $count > 0)\n                    //                        ->toArray(),\n                ],\n\n                'nodes' => [\n                    'count' => Node::count(),\n                ],\n\n                'servers' => [\n                    'count' => Server::count(),\n                    'suspended' => Server::where('status', Server::STATUS_SUSPENDED)->count(),\n                ],\n\n                'users' => [\n                    'count' => User::count(),\n                    'admins' => User::where('root_admin', true)->count(),\n                ],\n            ],\n\n            'nodes' => $nodes,\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Services/Users/ToggleTwoFactorService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Users;\n\nuse Carbon\\Carbon;\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\User;\nuse PragmaRX\\Google2FA\\Google2FA;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Contracts\\Repository\\UserRepositoryInterface;\nuse Pterodactyl\\Repositories\\Eloquent\\RecoveryTokenRepository;\nuse Pterodactyl\\Exceptions\\Service\\User\\TwoFactorAuthenticationTokenInvalid;\n\nclass ToggleTwoFactorService\n{\n    /**\n     * ToggleTwoFactorService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private Encrypter $encrypter,\n        private Google2FA $google2FA,\n        private RecoveryTokenRepository $recoveryTokenRepository,\n        private UserRepositoryInterface $repository,\n    ) {\n    }\n\n    /**\n     * Toggle 2FA on an account only if the token provided is valid.\n     *\n     * @throws \\Throwable\n     * @throws \\PragmaRX\\Google2FA\\Exceptions\\IncompatibleWithGoogleAuthenticatorException\n     * @throws \\PragmaRX\\Google2FA\\Exceptions\\InvalidCharactersException\n     * @throws \\PragmaRX\\Google2FA\\Exceptions\\SecretKeyTooShortException\n     * @throws TwoFactorAuthenticationTokenInvalid\n     */\n    public function handle(User $user, string $token, ?bool $toggleState = null): array\n    {\n        $secret = $this->encrypter->decrypt($user->totp_secret);\n\n        $isValidToken = $this->google2FA->verifyKey($secret, $token, config()->get('pterodactyl.auth.2fa.window'));\n\n        if (!$isValidToken) {\n            throw new TwoFactorAuthenticationTokenInvalid();\n        }\n\n        return $this->connection->transaction(function () use ($user, $toggleState) {\n            // Now that we're enabling 2FA on the account, generate 10 recovery tokens for the account\n            // and store them hashed in the database. We'll return them to the caller so that the user\n            // can see and save them.\n            //\n            // If a user is unable to login with a 2FA token they can provide one of these backup codes\n            // which will then be marked as deleted from the database and will also bypass 2FA protections\n            // on their account.\n            $tokens = [];\n            if ((!$toggleState && !$user->use_totp) || $toggleState) {\n                $inserts = [];\n                for ($i = 0; $i < 10; ++$i) {\n                    $token = Str::random(10);\n\n                    $inserts[] = [\n                        'user_id' => $user->id,\n                        'token' => password_hash($token, PASSWORD_DEFAULT),\n                        // insert() won't actually set the time on the models, so make sure we do this\n                        // manually here.\n                        'created_at' => Carbon::now(),\n                    ];\n\n                    $tokens[] = $token;\n                }\n\n                // Before inserting any new records make sure all of the old ones are deleted to avoid\n                // any issues or storing an unnecessary number of tokens in the database.\n                $this->recoveryTokenRepository->deleteWhere(['user_id' => $user->id]);\n\n                // Bulk insert the hashed tokens.\n                $this->recoveryTokenRepository->insert($inserts);\n            }\n\n            $this->repository->withoutFreshModel()->update($user->id, [\n                'totp_authenticated_at' => null,\n                'use_totp' => (is_null($toggleState) ? !$user->use_totp : $toggleState),\n            ]);\n\n            return $tokens;\n        });\n    }\n}\n"
  },
  {
    "path": "app/Services/Users/TwoFactorSetupService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Users;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Contracts\\Repository\\UserRepositoryInterface;\nuse Illuminate\\Contracts\\Config\\Repository as ConfigRepository;\n\nclass TwoFactorSetupService\n{\n    public const VALID_BASE32_CHARACTERS = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ234567';\n\n    /**\n     * TwoFactorSetupService constructor.\n     */\n    public function __construct(\n        private ConfigRepository $config,\n        private Encrypter $encrypter,\n        private UserRepositoryInterface $repository,\n    ) {\n    }\n\n    /**\n     * Generate a 2FA token and store it in the database before returning the\n     * QR code URL. This URL will need to be attached to a QR generating service in\n     * order to function.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     * @throws \\Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException\n     */\n    public function handle(User $user): array\n    {\n        $secret = '';\n        try {\n            for ($i = 0; $i < $this->config->get('pterodactyl.auth.2fa.bytes', 16); ++$i) {\n                $secret .= substr(self::VALID_BASE32_CHARACTERS, random_int(0, 31), 1);\n            }\n        } catch (\\Exception $exception) {\n            throw new \\RuntimeException($exception->getMessage(), 0, $exception);\n        }\n\n        $this->repository->withoutFreshModel()->update($user->id, [\n            'totp_secret' => $this->encrypter->encrypt($secret),\n        ]);\n\n        $company = urlencode(preg_replace('/\\s/', '', $this->config->get('app.name')));\n\n        return [\n            'image_url_data' => sprintf(\n                'otpauth://totp/%1$s:%2$s?secret=%3$s&issuer=%1$s',\n                rawurlencode($company),\n                rawurlencode($user->email),\n                rawurlencode($secret),\n            ),\n            'secret' => $secret,\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Services/Users/UserCreationService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Users;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Contracts\\Hashing\\Hasher;\nuse Illuminate\\Database\\ConnectionInterface;\nuse Illuminate\\Contracts\\Auth\\PasswordBroker;\nuse Pterodactyl\\Notifications\\AccountCreated;\nuse Pterodactyl\\Contracts\\Repository\\UserRepositoryInterface;\n\nclass UserCreationService\n{\n    /**\n     * UserCreationService constructor.\n     */\n    public function __construct(\n        private ConnectionInterface $connection,\n        private Hasher $hasher,\n        private PasswordBroker $passwordBroker,\n        private UserRepositoryInterface $repository,\n    ) {\n    }\n\n    /**\n     * Create a new user on the system.\n     *\n     * @throws \\Exception\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function handle(array $data): User\n    {\n        if (array_key_exists('password', $data) && !empty($data['password'])) {\n            $data['password'] = $this->hasher->make($data['password']);\n        }\n\n        $this->connection->beginTransaction();\n        if (!isset($data['password']) || empty($data['password'])) {\n            $generateResetToken = true;\n            $data['password'] = $this->hasher->make(str_random(30));\n        }\n\n        /** @var User $user */\n        $user = $this->repository->create(array_merge($data, [\n            'uuid' => Uuid::uuid4()->toString(),\n        ]), true, true);\n\n        if (isset($generateResetToken)) {\n            $token = $this->passwordBroker->createToken($user);\n        }\n\n        $this->connection->commit();\n        $user->notify(new AccountCreated($user, $token ?? null));\n\n        return $user;\n    }\n}\n"
  },
  {
    "path": "app/Services/Users/UserDeletionService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Users;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Exceptions\\DisplayException;\n\nclass UserDeletionService\n{\n    /**\n     * Delete a user from the panel only if they have no servers attached to their account.\n     *\n     * @throws DisplayException\n     */\n    public function handle(int|User $user): ?bool\n    {\n        $user = $user instanceof User ? $user : User::query()->findOrFail($user);\n\n        $servers = Server::query()->where('owner_id', $user->id)->count();\n        if ($servers > 0) {\n            throw new DisplayException(trans('admin/user.exceptions.user_has_servers'));\n        }\n\n        return $user->delete();\n    }\n}\n"
  },
  {
    "path": "app/Services/Users/UserUpdateService.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Services\\Users;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Contracts\\Hashing\\Hasher;\nuse Pterodactyl\\Events\\User\\PasswordChanged;\nuse Pterodactyl\\Traits\\Services\\HasUserLevels;\n\nclass UserUpdateService\n{\n    use HasUserLevels;\n\n    /**\n     * UserUpdateService constructor.\n     */\n    public function __construct(private Hasher $hasher)\n    {\n    }\n\n    /**\n     * Update the user model instance and return the updated model.\n     *\n     * @throws \\Throwable\n     */\n    public function handle(User $user, array $data): User\n    {\n        if (!empty(array_get($data, 'password'))) {\n            $data['password'] = $this->hasher->make($data['password']);\n        } else {\n            unset($data['password']);\n        }\n\n        $user->forceFill($data)->saveOrFail();\n\n        if (isset($data['password'])) {\n            PasswordChanged::dispatch($user);\n        }\n\n        return $user->refresh();\n    }\n}\n"
  },
  {
    "path": "app/Traits/Commands/EnvironmentWriterTrait.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Traits\\Commands;\n\nuse Pterodactyl\\Exceptions\\PterodactylException;\n\ntrait EnvironmentWriterTrait\n{\n    /**\n     * Escapes an environment value by looking for any characters that could\n     * reasonably cause environment parsing issues. Those values are then wrapped\n     * in quotes before being returned.\n     */\n    public function escapeEnvironmentValue(?string $value): string\n    {\n        if (is_null($value)) {\n            return '';\n        }\n\n        if (!preg_match('/^\\\"(.*)\\\"$/', $value) && preg_match('/([^\\w.\\-+\\/])+/', $value)) {\n            return sprintf('\"%s\"', addslashes($value));\n        }\n\n        return $value;\n    }\n\n    /**\n     * Update the .env file for the application using the passed in values.\n     *\n     * @throws PterodactylException\n     */\n    public function writeToEnvironment(array $values = []): void\n    {\n        $path = base_path('.env');\n        if (!file_exists($path)) {\n            throw new PterodactylException('Cannot locate .env file, was this software installed correctly?');\n        }\n\n        $saveContents = file_get_contents($path);\n        collect($values)->each(function ($value, $key) use (&$saveContents) {\n            $key = strtoupper($key);\n            $saveValue = sprintf('%s=%s', $key, $this->escapeEnvironmentValue($value));\n\n            if (preg_match_all('/^' . $key . '=(.*)$/m', $saveContents) < 1) {\n                $saveContents = $saveContents . PHP_EOL . $saveValue;\n            } else {\n                $saveContents = preg_replace('/^' . $key . '=(.*)$/m', $saveValue, $saveContents);\n            }\n        });\n\n        file_put_contents($path, $saveContents);\n    }\n}\n"
  },
  {
    "path": "app/Traits/Controllers/JavascriptInjection.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Traits\\Controllers;\n\nuse Illuminate\\Http\\Request;\n\ntrait JavascriptInjection\n{\n    private Request $request;\n\n    /**\n     * Set the request object to use when injecting JS.\n     */\n    public function setRequest(Request $request): self\n    {\n        $this->request = $request;\n\n        return $this;\n    }\n\n    /**\n     * Injects the exact array passed in, nothing more.\n     */\n    public function plainInject(array $args = []): string\n    {\n        return \\JavaScript::put($args);\n    }\n}\n"
  },
  {
    "path": "app/Traits/Helpers/AvailableLanguages.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Traits\\Helpers;\n\nuse Matriphe\\ISO639\\ISO639;\nuse Illuminate\\Filesystem\\Filesystem;\n\ntrait AvailableLanguages\n{\n    private ?ISO639 $iso639 = null;\n\n    private ?Filesystem $filesystem = null;\n\n    /**\n     * Return all the available languages on the Panel based on those\n     * that are present in the language folder.\n     */\n    public function getAvailableLanguages(bool $localize = false): array\n    {\n        return collect($this->getFilesystemInstance()->directories(resource_path('lang')))->mapWithKeys(function ($path) use ($localize) {\n            $code = basename($path);\n            $value = $localize ? $this->getIsoInstance()->nativeByCode1($code) : $this->getIsoInstance()->languageByCode1($code);\n\n            return [$code => title_case($value)];\n        })->toArray();\n    }\n\n    /**\n     * Return an instance of the filesystem for getting a folder listing.\n     */\n    private function getFilesystemInstance(): Filesystem\n    {\n        return $this->filesystem = $this->filesystem ?: app()->make(Filesystem::class);\n    }\n\n    /**\n     * Return an instance of the ISO639 class for generating names.\n     */\n    private function getIsoInstance(): ISO639\n    {\n        return $this->iso639 = $this->iso639 ?: app()->make(ISO639::class);\n    }\n}\n"
  },
  {
    "path": "app/Traits/Services/HasUserLevels.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Traits\\Services;\n\nuse Pterodactyl\\Models\\User;\n\ntrait HasUserLevels\n{\n    private int $userLevel = User::USER_LEVEL_USER;\n\n    /**\n     * Set the access level for running this function.\n     */\n    public function setUserLevel(int $level): self\n    {\n        $this->userLevel = $level;\n\n        return $this;\n    }\n\n    /**\n     * Determine which level this function is running at.\n     */\n    public function getUserLevel(): int\n    {\n        return $this->userLevel;\n    }\n\n    /**\n     * Determine if the current user level is set to a specific level.\n     */\n    public function isUserLevel(int $level): bool\n    {\n        return $this->getUserLevel() === $level;\n    }\n}\n"
  },
  {
    "path": "app/Traits/Services/ReturnsUpdatedModels.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Traits\\Services;\n\ntrait ReturnsUpdatedModels\n{\n    private bool $updatedModel = false;\n\n    public function getUpdatedModel(): bool\n    {\n        return $this->updatedModel;\n    }\n\n    /**\n     * If called a fresh model will be returned from the database. This is used\n     * for API calls, but is unnecessary for UI based updates where the page is\n     * being reloaded and a fresh model will be pulled anyways.\n     */\n    public function returnUpdatedModel(bool $toggle = true): self\n    {\n        $this->updatedModel = $toggle;\n\n        return $this;\n    }\n}\n"
  },
  {
    "path": "app/Traits/Services/ValidatesValidationRules.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Traits\\Services;\n\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Contracts\\Validation\\Factory as ValidationFactory;\nuse Pterodactyl\\Exceptions\\Service\\Egg\\Variable\\BadValidationRuleException;\n\ntrait ValidatesValidationRules\n{\n    abstract protected function getValidator(): ValidationFactory;\n\n    /**\n     * Validate that the rules being provided are valid for Laravel and can\n     * be resolved.\n     *\n     * @throws BadValidationRuleException\n     */\n    public function validateRules(array|string $rules): void\n    {\n        try {\n            $this->getValidator()->make(['__TEST' => 'test'], ['__TEST' => $rules])->fails();\n        } catch (\\BadMethodCallException $exception) {\n            $matches = [];\n            if (preg_match('/Method \\[(.+)\\] does not exist\\./', $exception->getMessage(), $matches)) {\n                throw new BadValidationRuleException(trans('exceptions.nest.variables.bad_validation_rule', ['rule' => Str::snake(str_replace('validate', '', array_get($matches, 1, 'unknownRule')))]), $exception);\n            }\n\n            throw $exception;\n        }\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/AllocationTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\Server;\nuse League\\Fractal\\Resource\\Item;\nuse Pterodactyl\\Models\\Allocation;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass AllocationTransformer extends BaseTransformer\n{\n    /**\n     * Relationships that can be loaded onto allocation transformations.\n     */\n    protected array $availableIncludes = ['node', 'server'];\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Allocation::RESOURCE_NAME;\n    }\n\n    /**\n     * Return a generic transformed allocation array.\n     */\n    public function transform(Allocation $allocation): array\n    {\n        return [\n            'id' => $allocation->id,\n            'ip' => $allocation->ip,\n            'alias' => $allocation->ip_alias,\n            'port' => $allocation->port,\n            'notes' => $allocation->notes,\n            'assigned' => !is_null($allocation->server_id),\n        ];\n    }\n\n    /**\n     * Load the node relationship onto a given transformation.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeNode(Allocation $allocation): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_NODES)) {\n            return $this->null();\n        }\n\n        return $this->item(\n            $allocation->node,\n            $this->makeTransformer(NodeTransformer::class),\n            Node::RESOURCE_NAME\n        );\n    }\n\n    /**\n     * Load the server relationship onto a given transformation.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeServer(Allocation $allocation): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_SERVERS) || !$allocation->server) {\n            return $this->null();\n        }\n\n        return $this->item(\n            $allocation->server,\n            $this->makeTransformer(ServerTransformer::class),\n            Server::RESOURCE_NAME\n        );\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/BaseTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Carbon\\CarbonImmutable;\nuse Carbon\\CarbonInterface;\nuse Illuminate\\Http\\Request;\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\ApiKey;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Database\\Eloquent\\Model;\nuse League\\Fractal\\TransformerAbstract;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\n/**\n * @method array transform(Model $model)\n */\nabstract class BaseTransformer extends TransformerAbstract\n{\n    public const RESPONSE_TIMEZONE = 'UTC';\n\n    protected Request $request;\n\n    /**\n     * BaseTransformer constructor.\n     */\n    public function __construct()\n    {\n        // Transformers allow for dependency injection on the handle method.\n        if (method_exists($this, 'handle')) {\n            Container::getInstance()->call([$this, 'handle']);\n        }\n    }\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    abstract public function getResourceName(): string;\n\n    /**\n     * Sets the request on the instance.\n     */\n    public function setRequest(Request $request): self\n    {\n        $this->request = $request;\n\n        return $this;\n    }\n\n    /**\n     * Returns a new transformer instance with the request set on the instance.\n     */\n    public static function fromRequest(Request $request): static\n    {\n        return app(static::class)->setRequest($request);\n    }\n\n    /**\n     * Determine if the API key loaded onto the transformer has permission\n     * to access a different resource. This is used when including other\n     * models on a transformation request.\n     *\n     * @deprecated — prefer $user->can/cannot methods\n     */\n    protected function authorize(string $resource): bool\n    {\n        $allowed = [ApiKey::TYPE_ACCOUNT, ApiKey::TYPE_APPLICATION];\n\n        $token = $this->request->user()?->currentAccessToken();\n        if (!$token instanceof ApiKey || !in_array($token->key_type, $allowed)) {\n            return false;\n        }\n\n        // If this is not a deprecated application token type we can only check that\n        // the user is a root admin at the moment. In a future release we'll be rolling\n        // out more specific permissions for keys.\n        if ($token->key_type === ApiKey::TYPE_ACCOUNT) {\n            return $this->request->user()->root_admin;\n        }\n\n        return AdminAcl::check($token, $resource);\n    }\n\n    /**\n     * Create a new instance of the transformer and pass along the currently\n     * set API key.\n     *\n     * @template T of \\Pterodactyl\\Transformers\\Api\\Application\\BaseTransformer\n     *\n     * @param class-string<T> $abstract\n     *\n     * @return T\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     *\n     * @noinspection PhpDocSignatureInspection\n     */\n    protected function makeTransformer(string $abstract)\n    {\n        Assert::subclassOf($abstract, self::class); // @phpstan-ignore staticMethod.alreadyNarrowedType\n\n        return $abstract::fromRequest($this->request);\n    }\n\n    /**\n     * Return an ISO-8601 formatted timestamp to use in the API response.\n     */\n    protected function formatTimestamp(string $timestamp): string\n    {\n        return CarbonImmutable::createFromFormat(CarbonInterface::DEFAULT_TO_STRING_FORMAT, $timestamp)\n            ->setTimezone(self::RESPONSE_TIMEZONE)\n            ->toAtomString();\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/DatabaseHostTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\DatabaseHost;\nuse League\\Fractal\\Resource\\Collection;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass DatabaseHostTransformer extends BaseTransformer\n{\n    protected array $availableIncludes = [\n        'databases',\n    ];\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return DatabaseHost::RESOURCE_NAME;\n    }\n\n    /**\n     * Transform database host into a representation for the application API.\n     */\n    public function transform(DatabaseHost $model): array\n    {\n        return [\n            'id' => $model->id,\n            'name' => $model->name,\n            'host' => $model->host,\n            'port' => $model->port,\n            'username' => $model->username,\n            'node' => $model->node_id,\n            'created_at' => $model->created_at->toAtomString(),\n            'updated_at' => $model->updated_at->toAtomString(),\n        ];\n    }\n\n    /**\n     * Include the databases associated with this host.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeDatabases(DatabaseHost $model): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_SERVER_DATABASES)) {\n            return $this->null();\n        }\n\n        $model->loadMissing('databases');\n\n        return $this->collection($model->getRelation('databases'), $this->makeTransformer(ServerDatabaseTransformer::class), Database::RESOURCE_NAME);\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/EggTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Illuminate\\Support\\Arr;\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\Nest;\nuse Pterodactyl\\Models\\Server;\nuse League\\Fractal\\Resource\\Item;\nuse Pterodactyl\\Models\\EggVariable;\nuse League\\Fractal\\Resource\\Collection;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass EggTransformer extends BaseTransformer\n{\n    /**\n     * Relationships that can be loaded onto this transformation.\n     */\n    protected array $availableIncludes = [\n        'nest',\n        'servers',\n        'config',\n        'script',\n        'variables',\n    ];\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Egg::RESOURCE_NAME;\n    }\n\n    /**\n     * Transform an Egg model into a representation that can be consumed by\n     * the application api.\n     *\n     * @throws \\JsonException\n     */\n    public function transform(Egg $model): array\n    {\n        $files = json_decode($model->config_files, true, 512, JSON_THROW_ON_ERROR);\n        if (empty($files)) {\n            $files = new \\stdClass();\n        }\n\n        return [\n            'id' => $model->id,\n            'uuid' => $model->uuid,\n            'name' => $model->name,\n            'nest' => $model->nest_id,\n            'author' => $model->author,\n            'description' => $model->description,\n            // \"docker_image\" is deprecated, but left here to avoid breaking too many things at once\n            // in external software. We'll remove it down the road once things have gotten the chance\n            // to upgrade to using \"docker_images\".\n            'docker_image' => count($model->docker_images) > 0 ? Arr::first($model->docker_images) : '',\n            'docker_images' => $model->docker_images,\n            'config' => [\n                'files' => $files,\n                'startup' => json_decode($model->config_startup, true),\n                'stop' => $model->config_stop,\n                'logs' => json_decode($model->config_logs, true),\n                'file_denylist' => $model->file_denylist,\n                'extends' => $model->config_from,\n            ],\n            'startup' => $model->startup,\n            'script' => [\n                'privileged' => $model->script_is_privileged,\n                'install' => $model->script_install,\n                'entry' => $model->script_entry,\n                'container' => $model->script_container,\n                'extends' => $model->copy_script_from,\n            ],\n            $model->getCreatedAtColumn() => $this->formatTimestamp($model->created_at),\n            $model->getUpdatedAtColumn() => $this->formatTimestamp($model->updated_at),\n        ];\n    }\n\n    /**\n     * Include the Nest relationship for the given Egg in the transformation.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeNest(Egg $model): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_NESTS)) {\n            return $this->null();\n        }\n\n        $model->loadMissing('nest');\n\n        return $this->item($model->getRelation('nest'), $this->makeTransformer(NestTransformer::class), Nest::RESOURCE_NAME);\n    }\n\n    /**\n     * Include the Servers relationship for the given Egg in the transformation.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeServers(Egg $model): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_SERVERS)) {\n            return $this->null();\n        }\n\n        $model->loadMissing('servers');\n\n        return $this->collection($model->getRelation('servers'), $this->makeTransformer(ServerTransformer::class), Server::RESOURCE_NAME);\n    }\n\n    /**\n     * Include more detailed information about the configuration if this Egg is\n     * extending another.\n     */\n    public function includeConfig(Egg $model): Item|NullResource\n    {\n        if (is_null($model->config_from)) {\n            return $this->null();\n        }\n\n        $model->loadMissing('configFrom');\n\n        return $this->item($model, function (Egg $model) {\n            return [\n                'files' => json_decode($model->inherit_config_files),\n                'startup' => json_decode($model->inherit_config_startup),\n                'stop' => $model->inherit_config_stop,\n                'logs' => json_decode($model->inherit_config_logs),\n            ];\n        });\n    }\n\n    /**\n     * Include more detailed information about the script configuration if the\n     * Egg is extending another.\n     */\n    public function includeScript(Egg $model): Item|NullResource\n    {\n        if (is_null($model->copy_script_from)) {\n            return $this->null();\n        }\n\n        $model->loadMissing('scriptFrom');\n\n        return $this->item($model, function (Egg $model) {\n            return [\n                'privileged' => $model->script_is_privileged,\n                'install' => $model->copy_script_install,\n                'entry' => $model->copy_script_entry,\n                'container' => $model->copy_script_container,\n            ];\n        });\n    }\n\n    /**\n     * Include the variables that are defined for this Egg.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeVariables(Egg $model): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_EGGS)) {\n            return $this->null();\n        }\n\n        $model->loadMissing('variables');\n\n        return $this->collection(\n            $model->getRelation('variables'),\n            $this->makeTransformer(EggVariableTransformer::class),\n            EggVariable::RESOURCE_NAME\n        );\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/EggVariableTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\EggVariable;\n\nclass EggVariableTransformer extends BaseTransformer\n{\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Egg::RESOURCE_NAME;\n    }\n\n    public function transform(EggVariable $model)\n    {\n        return $model->toArray();\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/LocationTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Pterodactyl\\Models\\Location;\nuse League\\Fractal\\Resource\\Collection;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass LocationTransformer extends BaseTransformer\n{\n    /**\n     * List of resources that can be included.\n     */\n    protected array $availableIncludes = ['nodes', 'servers'];\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Location::RESOURCE_NAME;\n    }\n\n    /**\n     * Return a generic transformed location array.\n     */\n    public function transform(Location $location): array\n    {\n        return [\n            'id' => $location->id,\n            'short' => $location->short,\n            'long' => $location->long,\n            $location->getUpdatedAtColumn() => $this->formatTimestamp($location->updated_at),\n            $location->getCreatedAtColumn() => $this->formatTimestamp($location->created_at),\n        ];\n    }\n\n    /**\n     * Return the nodes associated with this location.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeServers(Location $location): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_SERVERS)) {\n            return $this->null();\n        }\n\n        $location->loadMissing('servers');\n\n        return $this->collection($location->getRelation('servers'), $this->makeTransformer(ServerTransformer::class), 'server');\n    }\n\n    /**\n     * Return the nodes associated with this location.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeNodes(Location $location): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_NODES)) {\n            return $this->null();\n        }\n\n        $location->loadMissing('nodes');\n\n        return $this->collection($location->getRelation('nodes'), $this->makeTransformer(NodeTransformer::class), 'node');\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/NestTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\Nest;\nuse Pterodactyl\\Models\\Server;\nuse League\\Fractal\\Resource\\Collection;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass NestTransformer extends BaseTransformer\n{\n    /**\n     * Relationships that can be loaded onto this transformation.\n     */\n    protected array $availableIncludes = [\n        'eggs', 'servers',\n    ];\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Nest::RESOURCE_NAME;\n    }\n\n    /**\n     * Transform a Nest model into a representation that can be consumed by the\n     * application API.\n     */\n    public function transform(Nest $model): array\n    {\n        $response = $model->toArray();\n\n        $response[$model->getUpdatedAtColumn()] = $this->formatTimestamp($model->updated_at);\n        $response[$model->getCreatedAtColumn()] = $this->formatTimestamp($model->created_at);\n\n        return $response;\n    }\n\n    /**\n     * Include the Eggs relationship on the given Nest model transformation.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeEggs(Nest $model): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_EGGS)) {\n            return $this->null();\n        }\n\n        $model->loadMissing('eggs');\n\n        return $this->collection($model->getRelation('eggs'), $this->makeTransformer(EggTransformer::class), Egg::RESOURCE_NAME);\n    }\n\n    /**\n     * Include the servers relationship on the given Nest model.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeServers(Nest $model): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_SERVERS)) {\n            return $this->null();\n        }\n\n        $model->loadMissing('servers');\n\n        return $this->collection($model->getRelation('servers'), $this->makeTransformer(ServerTransformer::class), Server::RESOURCE_NAME);\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/NodeTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Pterodactyl\\Models\\Node;\nuse League\\Fractal\\Resource\\Item;\nuse League\\Fractal\\Resource\\Collection;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass NodeTransformer extends BaseTransformer\n{\n    /**\n     * List of resources that can be included.\n     */\n    protected array $availableIncludes = ['allocations', 'location', 'servers'];\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Node::RESOURCE_NAME;\n    }\n\n    /**\n     * Return a node transformed into a format that can be consumed by the\n     * external administrative API.\n     */\n    public function transform(Node $node): array\n    {\n        $response = collect($node->toArray())->mapWithKeys(function ($value, $key) {\n            // I messed up early in 2016 when I named this column as poorly\n            // as I did. This is the tragic result of my mistakes.\n            $key = ($key === 'daemonSFTP') ? 'daemonSftp' : $key;\n\n            return [snake_case($key) => $value];\n        })->toArray();\n\n        $response[$node->getUpdatedAtColumn()] = $this->formatTimestamp($node->updated_at);\n        $response[$node->getCreatedAtColumn()] = $this->formatTimestamp($node->created_at);\n\n        $resources = $node->servers()->select(['memory', 'disk'])->get();\n\n        $response['allocated_resources'] = [\n            'memory' => $resources->sum('memory'),\n            'disk' => $resources->sum('disk'),\n        ];\n\n        return $response;\n    }\n\n    /**\n     * Return the nodes associated with this location.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeAllocations(Node $node): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_ALLOCATIONS)) {\n            return $this->null();\n        }\n\n        $node->loadMissing('allocations');\n\n        return $this->collection(\n            $node->getRelation('allocations'),\n            $this->makeTransformer(AllocationTransformer::class),\n            'allocation'\n        );\n    }\n\n    /**\n     * Return the nodes associated with this location.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeLocation(Node $node): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_LOCATIONS)) {\n            return $this->null();\n        }\n\n        $node->loadMissing('location');\n\n        return $this->item(\n            $node->getRelation('location'),\n            $this->makeTransformer(LocationTransformer::class),\n            'location'\n        );\n    }\n\n    /**\n     * Return the nodes associated with this location.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeServers(Node $node): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_SERVERS)) {\n            return $this->null();\n        }\n\n        $node->loadMissing('servers');\n\n        return $this->collection(\n            $node->getRelation('servers'),\n            $this->makeTransformer(ServerTransformer::class),\n            'server'\n        );\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/ServerDatabaseTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Pterodactyl\\Models\\Database;\nuse League\\Fractal\\Resource\\Item;\nuse Pterodactyl\\Models\\DatabaseHost;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\n\nclass ServerDatabaseTransformer extends BaseTransformer\n{\n    protected array $availableIncludes = ['password', 'host'];\n\n    private Encrypter $encrypter;\n\n    /**\n     * Perform dependency injection.\n     */\n    public function handle(Encrypter $encrypter)\n    {\n        $this->encrypter = $encrypter;\n    }\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Database::RESOURCE_NAME;\n    }\n\n    /**\n     * Transform a database model in a representation for the application API.\n     */\n    public function transform(Database $model): array\n    {\n        return [\n            'id' => $model->id,\n            'server' => $model->server_id,\n            'host' => $model->database_host_id,\n            'database' => $model->database,\n            'username' => $model->username,\n            'remote' => $model->remote,\n            'max_connections' => $model->max_connections,\n            'created_at' => $model->created_at->toAtomString(),\n            'updated_at' => $model->updated_at->toAtomString(),\n        ];\n    }\n\n    /**\n     * Include the database password in the request.\n     */\n    public function includePassword(Database $model): Item\n    {\n        return $this->item($model, function (Database $model) {\n            return [\n                'password' => $this->encrypter->decrypt($model->password),\n            ];\n        }, 'database_password');\n    }\n\n    /**\n     * Return the database host relationship for this server database.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeHost(Database $model): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_DATABASE_HOSTS)) {\n            return $this->null();\n        }\n\n        $model->loadMissing('host');\n\n        return $this->item(\n            $model->getRelation('host'),\n            $this->makeTransformer(DatabaseHostTransformer::class),\n            DatabaseHost::RESOURCE_NAME\n        );\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/ServerTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Pterodactyl\\Models\\Server;\nuse League\\Fractal\\Resource\\Item;\nuse League\\Fractal\\Resource\\Collection;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Services\\Servers\\EnvironmentService;\n\nclass ServerTransformer extends BaseTransformer\n{\n    private EnvironmentService $environmentService;\n\n    /**\n     * List of resources that can be included.\n     */\n    protected array $availableIncludes = [\n        'allocations',\n        'user',\n        'subusers',\n        'nest',\n        'egg',\n        'variables',\n        'location',\n        'node',\n        'databases',\n        'transfer',\n    ];\n\n    /**\n     * Perform dependency injection.\n     */\n    public function handle(EnvironmentService $environmentService)\n    {\n        $this->environmentService = $environmentService;\n    }\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Server::RESOURCE_NAME;\n    }\n\n    /**\n     * Return a generic transformed server array.\n     */\n    public function transform(Server $server): array\n    {\n        return [\n            'id' => $server->getKey(),\n            'external_id' => $server->external_id,\n            'uuid' => $server->uuid,\n            'identifier' => $server->uuidShort,\n            'name' => $server->name,\n            'description' => $server->description,\n            'status' => $server->status,\n            // This field is deprecated, please use \"status\".\n            'suspended' => $server->isSuspended(),\n            'limits' => [\n                'memory' => $server->memory,\n                'swap' => $server->swap,\n                'disk' => $server->disk,\n                'io' => $server->io,\n                'cpu' => $server->cpu,\n                'threads' => $server->threads,\n                'oom_disabled' => $server->oom_disabled,\n            ],\n            'feature_limits' => [\n                'databases' => $server->database_limit,\n                'allocations' => $server->allocation_limit,\n                'backups' => $server->backup_limit,\n            ],\n            'user' => $server->owner_id,\n            'node' => $server->node_id,\n            'allocation' => $server->allocation_id,\n            'nest' => $server->nest_id,\n            'egg' => $server->egg_id,\n            'container' => [\n                'startup_command' => $server->startup,\n                'image' => $server->image,\n                // This field is deprecated, please use \"status\".\n                'installed' => $server->isInstalled() ? 1 : 0,\n                'environment' => $this->environmentService->handle($server),\n            ],\n            $server->getUpdatedAtColumn() => $this->formatTimestamp($server->updated_at),\n            $server->getCreatedAtColumn() => $this->formatTimestamp($server->created_at),\n        ];\n    }\n\n    /**\n     * Return a generic array of allocations for this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeAllocations(Server $server): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_ALLOCATIONS)) {\n            return $this->null();\n        }\n\n        $server->loadMissing('allocations');\n\n        return $this->collection($server->getRelation('allocations'), $this->makeTransformer(AllocationTransformer::class), 'allocation');\n    }\n\n    /**\n     * Return a generic array of data about subusers for this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeSubusers(Server $server): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_USERS)) {\n            return $this->null();\n        }\n\n        $server->loadMissing('subusers');\n\n        return $this->collection($server->getRelation('subusers'), $this->makeTransformer(SubuserTransformer::class), 'subuser');\n    }\n\n    /**\n     * Return a generic array of data about subusers for this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeUser(Server $server): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_USERS)) {\n            return $this->null();\n        }\n\n        $server->loadMissing('user');\n\n        return $this->item($server->getRelation('user'), $this->makeTransformer(UserTransformer::class), 'user');\n    }\n\n    /**\n     * Return a generic array with nest information for this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeNest(Server $server): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_NESTS)) {\n            return $this->null();\n        }\n\n        $server->loadMissing('nest');\n\n        return $this->item($server->getRelation('nest'), $this->makeTransformer(NestTransformer::class), 'nest');\n    }\n\n    /**\n     * Return a generic array with egg information for this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeEgg(Server $server): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_EGGS)) {\n            return $this->null();\n        }\n\n        $server->loadMissing('egg');\n\n        return $this->item($server->getRelation('egg'), $this->makeTransformer(EggTransformer::class), 'egg');\n    }\n\n    /**\n     * Return a generic array of data about subusers for this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeVariables(Server $server): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_SERVERS)) {\n            return $this->null();\n        }\n\n        $server->loadMissing('variables');\n\n        return $this->collection($server->getRelation('variables'), $this->makeTransformer(ServerVariableTransformer::class), 'server_variable');\n    }\n\n    /**\n     * Return a generic array with location information for this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeLocation(Server $server): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_LOCATIONS)) {\n            return $this->null();\n        }\n\n        $server->loadMissing('location');\n\n        return $this->item($server->getRelation('location'), $this->makeTransformer(LocationTransformer::class), 'location');\n    }\n\n    /**\n     * Return a generic array with node information for this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeNode(Server $server): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_NODES)) {\n            return $this->null();\n        }\n\n        $server->loadMissing('node');\n\n        return $this->item($server->getRelation('node'), $this->makeTransformer(NodeTransformer::class), 'node');\n    }\n\n    /**\n     * Return a generic array with database information for this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeDatabases(Server $server): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_SERVER_DATABASES)) {\n            return $this->null();\n        }\n\n        $server->loadMissing('databases');\n\n        return $this->collection($server->getRelation('databases'), $this->makeTransformer(ServerDatabaseTransformer::class), 'databases');\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/ServerVariableTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse League\\Fractal\\Resource\\Item;\nuse Pterodactyl\\Models\\EggVariable;\nuse Pterodactyl\\Models\\ServerVariable;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass ServerVariableTransformer extends BaseTransformer\n{\n    /**\n     * List of resources that can be included.\n     */\n    protected array $availableIncludes = ['parent'];\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return ServerVariable::RESOURCE_NAME;\n    }\n\n    /**\n     * Return a generic transformed server variable array.\n     */\n    public function transform(EggVariable $variable): array\n    {\n        return $variable->toArray();\n    }\n\n    /**\n     * Return the parent service variable data.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeParent(EggVariable $variable): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_EGGS)) {\n            return $this->null();\n        }\n\n        $variable->loadMissing('variable');\n\n        return $this->item($variable->getRelation('variable'), $this->makeTransformer(EggVariableTransformer::class), 'variable');\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/SubuserTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Pterodactyl\\Models\\Subuser;\nuse League\\Fractal\\Resource\\Item;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass SubuserTransformer extends BaseTransformer\n{\n    /**\n     * List of resources that can be included.\n     */\n    protected array $availableIncludes = ['user', 'server'];\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Subuser::RESOURCE_NAME;\n    }\n\n    /**\n     * Return a transformed Subuser model that can be consumed by external services.\n     */\n    public function transform(Subuser $subuser): array\n    {\n        return [\n            'id' => $subuser->id,\n            'user_id' => $subuser->user_id,\n            'server_id' => $subuser->server_id,\n            'permissions' => $subuser->permissions,\n            'created_at' => $this->formatTimestamp($subuser->created_at),\n            'updated_at' => $this->formatTimestamp($subuser->updated_at),\n        ];\n    }\n\n    /**\n     * Return a generic item of user for this subuser.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeUser(Subuser $subuser): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_USERS)) {\n            return $this->null();\n        }\n\n        $subuser->loadMissing('user');\n\n        return $this->item($subuser->getRelation('user'), $this->makeTransformer(UserTransformer::class), 'user');\n    }\n\n    /**\n     * Return a generic item of server for this subuser.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeServer(Subuser $subuser): Item|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_SERVERS)) {\n            return $this->null();\n        }\n\n        $subuser->loadMissing('server');\n\n        return $this->item($subuser->getRelation('server'), $this->makeTransformer(ServerTransformer::class), 'server');\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Application/UserTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Application;\n\nuse Pterodactyl\\Models\\User;\nuse League\\Fractal\\Resource\\Collection;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass UserTransformer extends BaseTransformer\n{\n    /**\n     * List of resources that can be included.\n     */\n    protected array $availableIncludes = ['servers'];\n\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return User::RESOURCE_NAME;\n    }\n\n    /**\n     * Return a transformed User model that can be consumed by external services.\n     */\n    public function transform(User $user): array\n    {\n        return [\n            'id' => $user->id,\n            'external_id' => $user->external_id,\n            'uuid' => $user->uuid,\n            'username' => $user->username,\n            'email' => $user->email,\n            'first_name' => $user->name_first,\n            'last_name' => $user->name_last,\n            'language' => $user->language,\n            'root_admin' => (bool) $user->root_admin,\n            '2fa' => (bool) $user->use_totp,\n            'created_at' => $this->formatTimestamp($user->created_at),\n            'updated_at' => $this->formatTimestamp($user->updated_at),\n        ];\n    }\n\n    /**\n     * Return the servers associated with this user.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeServers(User $user): Collection|NullResource\n    {\n        if (!$this->authorize(AdminAcl::RESOURCE_SERVERS)) {\n            return $this->null();\n        }\n\n        $user->loadMissing('servers');\n\n        return $this->collection($user->getRelation('servers'), $this->makeTransformer(ServerTransformer::class), 'server');\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/AccountTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\User;\n\nclass AccountTransformer extends BaseClientTransformer\n{\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return 'user';\n    }\n\n    /**\n     * Return basic information about the currently logged-in user.\n     */\n    public function transform(User $model): array\n    {\n        return [\n            'id' => $model->id,\n            'admin' => $model->root_admin,\n            'username' => $model->username,\n            'email' => $model->email,\n            'first_name' => $model->name_first,\n            'last_name' => $model->name_last,\n            'language' => $model->language,\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/ActivityLogTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\ActivityLog;\nuse Illuminate\\Database\\Eloquent\\Model;\n\nclass ActivityLogTransformer extends BaseClientTransformer\n{\n    protected array $availableIncludes = ['actor'];\n\n    public function getResourceName(): string\n    {\n        return ActivityLog::RESOURCE_NAME;\n    }\n\n    public function transform(ActivityLog $model): array\n    {\n        return [\n            // This is not for security, it is only to provide a unique identifier to\n            // the front-end for each entry to improve rendering performance since there\n            // is nothing else sufficiently unique to key off at this point.\n            'id' => sha1($model->id),\n            'batch' => $model->batch,\n            'event' => $model->event,\n            'is_api' => !is_null($model->api_key_id),\n            'ip' => $this->canViewIP($model->actor) ? $model->ip : null,\n            'description' => $model->description,\n            'properties' => $this->properties($model),\n            'has_additional_metadata' => $this->hasAdditionalMetadata($model),\n            'timestamp' => $model->timestamp->toAtomString(),\n        ];\n    }\n\n    public function includeActor(ActivityLog $model)\n    {\n        if (!$model->actor instanceof User) {\n            return $this->null();\n        }\n\n        return $this->item($model->actor, $this->makeTransformer(UserTransformer::class), User::RESOURCE_NAME);\n    }\n\n    /**\n     * Transforms any array values in the properties into a countable field for easier\n     * use within the translation outputs.\n     */\n    protected function properties(ActivityLog $model): object\n    {\n        if (!$model->properties || $model->properties->isEmpty()) {\n            return (object) [];\n        }\n\n        $properties = $model->properties\n            ->mapWithKeys(function ($value, $key) use ($model) {\n                if ($key === 'ip' && !optional($model->actor)->is($this->request->user())) {\n                    return [$key => '[hidden]'];\n                }\n\n                if (!is_array($value)) {\n                    // Perform some directory normalization at this point.\n                    if ($key === 'directory') {\n                        $value = str_replace('//', '/', '/' . trim($value, '/') . '/');\n                    }\n\n                    return [$key => $value];\n                }\n\n                return [$key => $value, \"{$key}_count\" => count($value)];\n            });\n\n        $keys = $properties->keys()->filter(fn ($key) => Str::endsWith($key, '_count'))->values();\n        if ($keys->containsOneItem()) {\n            $properties = $properties->merge(['count' => $properties->get($keys[0])])->except($keys[0]);\n        }\n\n        return (object) $properties->toArray();\n    }\n\n    /**\n     * Determines if there are any log properties that we've not already exposed\n     * in the response language string and that are not just the IP address or\n     * the browser useragent.\n     *\n     * This is used by the front-end to selectively display an \"additional metadata\"\n     * button that is pointless if there is nothing the user can't already see from\n     * the event description.\n     */\n    protected function hasAdditionalMetadata(ActivityLog $model): bool\n    {\n        if (is_null($model->properties) || $model->properties->isEmpty()) {\n            return false;\n        }\n\n        $str = trans('activity.' . str_replace(':', '.', $model->event));\n        preg_match_all('/:(?<key>[\\w.-]+\\w)(?:[^\\w:]?|$)/', $str, $matches);\n\n        $exclude = array_merge($matches['key'], ['ip', 'useragent', 'using_sftp']);\n        foreach ($model->properties->keys() as $key) {\n            if (!in_array($key, $exclude, true)) {\n                return true;\n            }\n        }\n\n        return false;\n    }\n\n    /**\n     * Determines if the user can view the IP address in the output either because they are the\n     * actor that performed the action, or because they are an administrator on the Panel.\n     */\n    protected function canViewIP(?Model $actor = null): bool\n    {\n        return optional($actor)->is($this->request->user()) || $this->request->user()->root_admin;\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/AllocationTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\Allocation;\n\nclass AllocationTransformer extends BaseClientTransformer\n{\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return 'allocation';\n    }\n\n    public function transform(Allocation $model): array\n    {\n        return [\n            'id' => $model->id,\n            'ip' => $model->ip,\n            'ip_alias' => $model->ip_alias,\n            'port' => $model->port,\n            'notes' => $model->notes,\n            'is_default' => $model->server->allocation_id === $model->id,\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/ApiKeyTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\ApiKey;\n\nclass ApiKeyTransformer extends BaseClientTransformer\n{\n    public function getResourceName(): string\n    {\n        return ApiKey::RESOURCE_NAME;\n    }\n\n    /**\n     * Transform this model into a representation that can be consumed by a client.\n     */\n    public function transform(ApiKey $model): array\n    {\n        return [\n            'identifier' => $model->identifier,\n            'description' => $model->memo,\n            'allowed_ips' => $model->allowed_ips,\n            'last_used_at' => $model->last_used_at ? $model->last_used_at->toAtomString() : null,\n            'created_at' => $model->created_at->toAtomString(),\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/BackupTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\Backup;\n\nclass BackupTransformer extends BaseClientTransformer\n{\n    public function getResourceName(): string\n    {\n        return Backup::RESOURCE_NAME;\n    }\n\n    public function transform(Backup $backup): array\n    {\n        return [\n            'uuid' => $backup->uuid,\n            'is_successful' => $backup->is_successful,\n            'is_locked' => $backup->is_locked,\n            'name' => $backup->name,\n            'ignored_files' => $backup->ignored_files,\n            'checksum' => $backup->checksum,\n            'bytes' => $backup->bytes,\n            'created_at' => $backup->created_at->toAtomString(),\n            'completed_at' => $backup->completed_at ? $backup->completed_at->toAtomString() : null,\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/BaseClientTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\User;\nuse Webmozart\\Assert\\Assert;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Transformers\\Api\\Application\\BaseTransformer as BaseApplicationTransformer;\n\nabstract class BaseClientTransformer extends BaseApplicationTransformer\n{\n    /**\n     * Return the user model of the user requesting this transformation.\n     */\n    public function getUser(): User\n    {\n        return $this->request->user();\n    }\n\n    /**\n     * Determine if the API key loaded onto the transformer has permission\n     * to access a different resource. This is used when including other\n     * models on a transformation request.\n     *\n     * @noinspection PhpParameterNameChangedDuringInheritanceInspection\n     */\n    protected function authorize(string $ability, ?Server $server = null): bool\n    {\n        Assert::isInstanceOf($server, Server::class);\n\n        return $this->request->user()->can($ability, [$server]);\n    }\n\n    protected function makeTransformer(string $abstract)\n    {\n        Assert::subclassOf($abstract, self::class);\n\n        return parent::makeTransformer($abstract);\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/DatabaseTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\Database;\nuse League\\Fractal\\Resource\\Item;\nuse Pterodactyl\\Models\\Permission;\nuse League\\Fractal\\Resource\\NullResource;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Contracts\\Extensions\\HashidsInterface;\n\nclass DatabaseTransformer extends BaseClientTransformer\n{\n    protected array $availableIncludes = ['password'];\n\n    private Encrypter $encrypter;\n\n    private HashidsInterface $hashids;\n\n    /**\n     * Handle dependency injection.\n     */\n    public function handle(Encrypter $encrypter, HashidsInterface $hashids)\n    {\n        $this->encrypter = $encrypter;\n        $this->hashids = $hashids;\n    }\n\n    public function getResourceName(): string\n    {\n        return Database::RESOURCE_NAME;\n    }\n\n    public function transform(Database $model): array\n    {\n        $model->loadMissing('host');\n\n        return [\n            'id' => $this->hashids->encode($model->id),\n            'host' => [\n                'address' => $model->getRelation('host')->host,\n                'port' => $model->getRelation('host')->port,\n            ],\n            'name' => $model->database,\n            'username' => $model->username,\n            'connections_from' => $model->remote,\n            'max_connections' => $model->max_connections,\n        ];\n    }\n\n    /**\n     * Include the database password in the request.\n     */\n    public function includePassword(Database $database): Item|NullResource\n    {\n        if (!$this->request->user()->can(Permission::ACTION_DATABASE_VIEW_PASSWORD, $database->server)) {\n            return $this->null();\n        }\n\n        return $this->item($database, function (Database $model) {\n            return [\n                'password' => $this->encrypter->decrypt($model->password),\n            ];\n        }, 'database_password');\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/EggTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\Egg;\n\nclass EggTransformer extends BaseClientTransformer\n{\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Egg::RESOURCE_NAME;\n    }\n\n    public function transform(Egg $egg): array\n    {\n        return [\n            'uuid' => $egg->uuid,\n            'name' => $egg->name,\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/EggVariableTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\EggVariable;\n\nclass EggVariableTransformer extends BaseClientTransformer\n{\n    public function getResourceName(): string\n    {\n        return EggVariable::RESOURCE_NAME;\n    }\n\n    public function transform(EggVariable $variable): array\n    {\n        // This guards against someone incorrectly retrieving variables (haha, me) and then passing\n        // them into the transformer and along to the user. Just throw an exception and break the entire\n        // pathway since you should never be exposing these types of variables to a client.\n        if (!$variable->user_viewable) {\n            throw new \\BadMethodCallException('Cannot transform a hidden egg variable in a client transformer.');\n        }\n\n        return [\n            'name' => $variable->name,\n            'description' => $variable->description,\n            'env_variable' => $variable->env_variable,\n            'default_value' => $variable->default_value,\n            'server_value' => $variable->server_value,\n            'is_editable' => $variable->user_editable,\n            'rules' => $variable->rules,\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/FileObjectTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Carbon\\Carbon;\nuse Illuminate\\Support\\Arr;\n\nclass FileObjectTransformer extends BaseClientTransformer\n{\n    /**\n     * Transform a file object response from the daemon into a standardized response.\n     */\n    public function transform(array $item): array\n    {\n        return [\n            'name' => Arr::get($item, 'name'),\n            'mode' => Arr::get($item, 'mode'),\n            'mode_bits' => Arr::get($item, 'mode_bits'),\n            'size' => Arr::get($item, 'size'),\n            'is_file' => Arr::get($item, 'file', true),\n            'is_symlink' => Arr::get($item, 'symlink', false),\n            'mimetype' => Arr::get($item, 'mime', 'application/octet-stream'),\n            'created_at' => Carbon::parse(Arr::get($item, 'created', ''))->toAtomString(),\n            'modified_at' => Carbon::parse(Arr::get($item, 'modified', ''))->toAtomString(),\n        ];\n    }\n\n    public function getResourceName(): string\n    {\n        return 'file_object';\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/ScheduleTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\Task;\nuse Pterodactyl\\Models\\Schedule;\nuse League\\Fractal\\Resource\\Collection;\n\nclass ScheduleTransformer extends BaseClientTransformer\n{\n    protected array $availableIncludes = ['tasks'];\n\n    protected array $defaultIncludes = ['tasks'];\n\n    public function getResourceName(): string\n    {\n        return Schedule::RESOURCE_NAME;\n    }\n\n    /**\n     * Returns a transformed schedule model such that a client can view the information.\n     */\n    public function transform(Schedule $model): array\n    {\n        return [\n            'id' => $model->id,\n            'name' => $model->name,\n            'cron' => [\n                'day_of_week' => $model->cron_day_of_week,\n                'day_of_month' => $model->cron_day_of_month,\n                'month' => $model->cron_month,\n                'hour' => $model->cron_hour,\n                'minute' => $model->cron_minute,\n            ],\n            'is_active' => $model->is_active,\n            'is_processing' => $model->is_processing,\n            'only_when_online' => $model->only_when_online,\n            'last_run_at' => $model->last_run_at?->toAtomString(),\n            'next_run_at' => $model->next_run_at?->toAtomString(),\n            'created_at' => $model->created_at->toAtomString(),\n            'updated_at' => $model->updated_at->toAtomString(),\n        ];\n    }\n\n    /**\n     * Allows attaching the tasks specific to the schedule in the response.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeTasks(Schedule $model): Collection\n    {\n        return $this->collection(\n            $model->tasks,\n            $this->makeTransformer(TaskTransformer::class),\n            Task::RESOURCE_NAME\n        );\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/ServerTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Subuser;\nuse League\\Fractal\\Resource\\Item;\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Container\\Container;\nuse Pterodactyl\\Models\\EggVariable;\nuse League\\Fractal\\Resource\\Collection;\nuse League\\Fractal\\Resource\\NullResource;\nuse Pterodactyl\\Services\\Servers\\StartupCommandService;\n\nclass ServerTransformer extends BaseClientTransformer\n{\n    protected array $defaultIncludes = ['allocations', 'variables'];\n\n    protected array $availableIncludes = ['egg', 'subusers'];\n\n    public function getResourceName(): string\n    {\n        return Server::RESOURCE_NAME;\n    }\n\n    /**\n     * Transform a server model into a representation that can be returned\n     * to a client.\n     */\n    public function transform(Server $server): array\n    {\n        /** @var StartupCommandService $service */\n        $service = Container::getInstance()->make(StartupCommandService::class);\n\n        $user = $this->request->user();\n\n        return [\n            'server_owner' => $user->id === $server->owner_id,\n            'identifier' => config('pterodactyl.features.new_server_identifiers')\n                ? $server->identifier\n                : $server->uuidShort,\n            '__deprecated_uuid_short' => $server->uuidShort,\n            // In Pterodactyl 2.0 we'll be replacing `identifier` above with the actual\n            // \"identifier\" used internally. This is a completely different value compared\n            // to the current however, and would be quite a breaking change to URLs.\n            'server_identifier' => $server->identifier,\n            'internal_id' => $server->id,\n            'uuid' => $server->uuid,\n            'name' => $server->name,\n            'node' => $server->node->name,\n            'is_node_under_maintenance' => $server->node->isUnderMaintenance(),\n            'sftp_details' => [\n                'ip' => $server->node->fqdn,\n                'port' => $server->node->daemonSFTP,\n            ],\n            'description' => $server->description,\n            'limits' => [\n                'memory' => $server->memory,\n                'swap' => $server->swap,\n                'disk' => $server->disk,\n                'io' => $server->io,\n                'cpu' => $server->cpu,\n                'threads' => $server->threads,\n                'oom_disabled' => $server->oom_disabled,\n            ],\n            'invocation' => $service->handle($server, !$user->can(Permission::ACTION_STARTUP_READ, $server)),\n            'docker_image' => $server->image,\n            'egg_features' => $server->egg->inherit_features,\n            'feature_limits' => [\n                'databases' => $server->database_limit,\n                'allocations' => $server->allocation_limit,\n                'backups' => $server->backup_limit,\n            ],\n            'status' => $server->status,\n            // This field is deprecated, please use \"status\".\n            'is_suspended' => $server->isSuspended(),\n            // This field is deprecated, please use \"status\".\n            'is_installing' => !$server->isInstalled(),\n            'is_transferring' => !is_null($server->transfer),\n        ];\n    }\n\n    /**\n     * Returns the allocations associated with this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeAllocations(Server $server): Collection\n    {\n        $transformer = $this->makeTransformer(AllocationTransformer::class);\n\n        $user = $this->request->user();\n        // While we include this permission, we do need to actually handle it slightly different here\n        // for the purpose of keeping things functionally working. If the user doesn't have read permissions\n        // for the allocations we'll only return the primary server allocation, and any notes associated\n        // with it will be hidden.\n        //\n        // This allows us to avoid too much permission regression, without also hiding information that\n        // is generally needed for the frontend to make sense when browsing or searching results.\n        if (!$user->can(Permission::ACTION_ALLOCATION_READ, $server)) {\n            $primary = clone $server->allocation;\n            $primary->notes = null;\n\n            return $this->collection([$primary], $transformer, Allocation::RESOURCE_NAME);\n        }\n\n        return $this->collection($server->allocations, $transformer, Allocation::RESOURCE_NAME);\n    }\n\n    /**\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeVariables(Server $server): Collection|NullResource\n    {\n        if (!$this->request->user()->can(Permission::ACTION_STARTUP_READ, $server)) {\n            return $this->null();\n        }\n\n        return $this->collection(\n            $server->variables->where('user_viewable', true),\n            $this->makeTransformer(EggVariableTransformer::class),\n            EggVariable::RESOURCE_NAME\n        );\n    }\n\n    /**\n     * Returns the egg associated with this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeEgg(Server $server): Item\n    {\n        return $this->item($server->egg, $this->makeTransformer(EggTransformer::class), Egg::RESOURCE_NAME);\n    }\n\n    /**\n     * Returns the subusers associated with this server.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function includeSubusers(Server $server): Collection|NullResource\n    {\n        if (!$this->request->user()->can(Permission::ACTION_USER_READ, $server)) {\n            return $this->null();\n        }\n\n        return $this->collection($server->subusers, $this->makeTransformer(SubuserTransformer::class), Subuser::RESOURCE_NAME);\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/StatsTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Illuminate\\Support\\Arr;\n\nclass StatsTransformer extends BaseClientTransformer\n{\n    public function getResourceName(): string\n    {\n        return 'stats';\n    }\n\n    /**\n     * Transform stats from the daemon into a result set that can be used in\n     * the client API.\n     */\n    public function transform(array $data): array\n    {\n        return [\n            'current_state' => Arr::get($data, 'state', 'stopped'),\n            'is_suspended' => Arr::get($data, 'is_suspended', false),\n            'resources' => [\n                'memory_bytes' => Arr::get($data, 'utilization.memory_bytes', 0),\n                'cpu_absolute' => Arr::get($data, 'utilization.cpu_absolute', 0),\n                'disk_bytes' => Arr::get($data, 'utilization.disk_bytes', 0),\n                'network_rx_bytes' => Arr::get($data, 'utilization.network.rx_bytes', 0),\n                'network_tx_bytes' => Arr::get($data, 'utilization.network.tx_bytes', 0),\n                'uptime' => Arr::get($data, 'utilization.uptime', 0),\n            ],\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/SubuserTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\Subuser;\n\nclass SubuserTransformer extends BaseClientTransformer\n{\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return Subuser::RESOURCE_NAME;\n    }\n\n    /**\n     * Transforms a subuser into a model that can be shown to a front-end user.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Transformer\\InvalidTransformerLevelException\n     */\n    public function transform(Subuser $model): array\n    {\n        return array_merge(\n            $this->makeTransformer(UserTransformer::class)->transform($model->user),\n            ['permissions' => $model->permissions]\n        );\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/TaskTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\Task;\n\nclass TaskTransformer extends BaseClientTransformer\n{\n    public function getResourceName(): string\n    {\n        return Task::RESOURCE_NAME;\n    }\n\n    /**\n     * Transforms a schedule's task into a client viewable format.\n     */\n    public function transform(Task $model): array\n    {\n        return [\n            'id' => $model->id,\n            'sequence_id' => $model->sequence_id,\n            'action' => $model->action,\n            'payload' => $model->payload,\n            'time_offset' => $model->time_offset,\n            'is_queued' => $model->is_queued,\n            'continue_on_failure' => $model->continue_on_failure,\n            'created_at' => $model->created_at->toAtomString(),\n            'updated_at' => $model->updated_at->toAtomString(),\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/UserSSHKeyTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Pterodactyl\\Models\\UserSSHKey;\n\nclass UserSSHKeyTransformer extends BaseClientTransformer\n{\n    public function getResourceName(): string\n    {\n        return UserSSHKey::RESOURCE_NAME;\n    }\n\n    /**\n     * Return's a user's SSH key in an API response format.\n     */\n    public function transform(UserSSHKey $model): array\n    {\n        return [\n            'name' => $model->name,\n            'fingerprint' => $model->fingerprint,\n            'public_key' => $model->public_key,\n            'created_at' => $model->created_at->toAtomString(),\n        ];\n    }\n}\n"
  },
  {
    "path": "app/Transformers/Api/Client/UserTransformer.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Transformers\\Api\\Client;\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\User;\n\nclass UserTransformer extends BaseClientTransformer\n{\n    /**\n     * Return the resource name for the JSONAPI output.\n     */\n    public function getResourceName(): string\n    {\n        return User::RESOURCE_NAME;\n    }\n\n    /**\n     * Transforms a User model into a representation that can be shown to regular\n     * users of the API.\n     */\n    public function transform(User $model): array\n    {\n        return [\n            'uuid' => $model->uuid,\n            'identifier' => $model->identifier,\n            'username' => $model->username,\n            'email' => $model->email,\n            'image' => 'https://cravatar.cn/avatar/' . md5(Str::lower($model->email)),\n            '2fa_enabled' => $model->use_totp,\n            'created_at' => $model->created_at->toAtomString(),\n        ];\n    }\n}\n"
  },
  {
    "path": "app/helpers.php",
    "content": "<?php\n\nif (!function_exists('is_digit')) {\n    /**\n     * Deal with normal (and irritating) PHP behavior to determine if\n     * a value is a non-float positive integer.\n     */\n    function is_digit(mixed $value): bool\n    {\n        return !is_bool($value) && ctype_digit(strval($value));\n    }\n}\n\nif (!function_exists('object_get_strict')) {\n    /**\n     * Get an object using dot notation. An object key with a value of null is still considered valid\n     * and will not trigger the response of a default value (unlike object_get).\n     */\n    function object_get_strict(object $object, ?string $key, $default = null): mixed\n    {\n        if (is_null($key) || trim($key) == '') {\n            return $object;\n        }\n\n        foreach (explode('.', $key) as $segment) {\n            if (!is_object($object) || !property_exists($object, $segment)) {\n                return value($default);\n            }\n\n            $object = $object->{$segment};\n        }\n\n        return $object;\n    }\n}\n"
  },
  {
    "path": "artisan",
    "content": "#!/usr/bin/env php\n<?php\n\ndefine('LARAVEL_START', microtime(true));\n\n/*\n|--------------------------------------------------------------------------\n| Register The Auto Loader\n|--------------------------------------------------------------------------\n|\n| Composer provides a convenient, automatically generated class loader\n| for our application. We just need to utilize it! We'll require it\n| into the script here so that we do not have to worry about the\n| loading of our classes manually. It's great to relax.\n|\n*/\n\nrequire __DIR__ . '/vendor/autoload.php';\n\n$app = require_once __DIR__ . '/bootstrap/app.php';\n\n/*\n|--------------------------------------------------------------------------\n| Run The Artisan Application\n|--------------------------------------------------------------------------\n|\n| When we run the console application, the current CLI command will be\n| executed in this console and the response sent back to a terminal\n| or another output device for the developers. Here goes nothing!\n|\n*/\n\n$kernel = $app->make(Illuminate\\Contracts\\Console\\Kernel::class);\n\n$status = $kernel->handle(\n    $input = new Symfony\\Component\\Console\\Input\\ArgvInput(),\n    new Symfony\\Component\\Console\\Output\\ConsoleOutput()\n);\n\n/*\n|--------------------------------------------------------------------------\n| Shutdown The Application\n|--------------------------------------------------------------------------\n|\n| Once Artisan has finished running, we will fire off the shutdown events\n| so that any final work may be done by the application before we shut\n| down the process. This is the last thing to happen to the request.\n|\n*/\n\n$kernel->terminate($input, $status);\n\nexit($status);\n"
  },
  {
    "path": "babel.config.js",
    "content": "module.exports = function (api) {\n    let targets = {};\n    const plugins = [\n        'babel-plugin-macros',\n        'styled-components',\n        'react-hot-loader/babel',\n        '@babel/transform-runtime',\n        '@babel/transform-react-jsx',\n        '@babel/proposal-class-properties',\n        '@babel/proposal-object-rest-spread',\n        '@babel/proposal-optional-chaining',\n        '@babel/proposal-nullish-coalescing-operator',\n        '@babel/syntax-dynamic-import',\n    ];\n\n    if (api.env('test')) {\n        targets = { node: 'current' };\n        plugins.push('@babel/transform-modules-commonjs');\n    }\n\n    return {\n        plugins,\n        presets: [\n            '@babel/typescript',\n            ['@babel/env', {\n                modules: false,\n                useBuiltIns: 'entry',\n                corejs: 3,\n                targets,\n            }],\n            '@babel/react',\n        ]\n    };\n};\n"
  },
  {
    "path": "bootstrap/app.php",
    "content": "<?php\n\n/*\n|--------------------------------------------------------------------------\n| Create The Application\n|--------------------------------------------------------------------------\n|\n| The first thing we will do is create a new Laravel application instance\n| which serves as the \"glue\" for all the components of Laravel, and is\n| the IoC container for the system binding all of the various parts.\n|\n*/\n\n$app = new Illuminate\\Foundation\\Application(\n    $_ENV['APP_BASE_PATH'] ?? dirname(__DIR__)\n);\n\nif (isset($_ENV['APP_STORAGE_PATH'])) {\n    $app->useStoragePath($_ENV['APP_STORAGE_PATH']);\n}\n\n/*\n|--------------------------------------------------------------------------\n| Bind Important Interfaces\n|--------------------------------------------------------------------------\n|\n| Next, we need to bind some important interfaces into the container so\n| we will be able to resolve them when needed. The kernels serve the\n| incoming requests to this application from both the web and CLI.\n|\n*/\n\n$app->singleton(\n    Illuminate\\Contracts\\Http\\Kernel::class,\n    Pterodactyl\\Http\\Kernel::class\n);\n\n$app->singleton(\n    Illuminate\\Contracts\\Console\\Kernel::class,\n    Pterodactyl\\Console\\Kernel::class\n);\n\n$app->singleton(\n    Illuminate\\Contracts\\Debug\\ExceptionHandler::class,\n    Pterodactyl\\Exceptions\\Handler::class\n);\n\n/*\n|--------------------------------------------------------------------------\n| Return The Application\n|--------------------------------------------------------------------------\n|\n| This script returns the application instance. The instance is given to\n| the calling script so we can separate the building of the instances\n| from the actual running of the application and sending responses.\n|\n*/\n\nreturn $app;\n"
  },
  {
    "path": "bootstrap/cache/.gitignore",
    "content": "*\n!.gitignore\n"
  },
  {
    "path": "bootstrap/tests.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Str;\nuse NunoMaduro\\Collision\\Provider;\nuse Illuminate\\Contracts\\Console\\Kernel;\nuse Symfony\\Component\\Console\\Output\\ConsoleOutput;\n\nrequire __DIR__ . '/../vendor/autoload.php';\n\n$app = require __DIR__ . '/app.php';\n\n/** @var Pterodactyl\\Console\\Kernel $kernel */\n$kernel = $app->make(Kernel::class);\n\n/*\n * Bootstrap the kernel and prepare application for testing.\n */\n$kernel->bootstrap();\n\n// Register the collision service provider so that errors during the test\n// setup process are output nicely.\n(new Provider())->register();\n\n$output = new ConsoleOutput();\n\n$prefix = 'database.connections.' . config('database.default');\nif (!Str::contains(config(\"$prefix.database\"), 'test')) {\n    $output->writeln(PHP_EOL . '<error>Cannot run test process against non-testing database.</error>');\n    $output->writeln(PHP_EOL . '<error>Environment is currently pointed at: \"' . config(\"$prefix.database\") . '\".</error>');\n    exit(1);\n}\n\n/*\n * Perform database migrations and reseeding before continuing with\n * running the tests.\n */\nif (!env('SKIP_MIGRATIONS')) {\n    $output->writeln(PHP_EOL . '<info>Refreshing database for Integration tests...</info>');\n    $kernel->call('migrate:fresh');\n\n    $output->writeln('<info>Seeding database for Integration tests...</info>' . PHP_EOL);\n    $kernel->call('db:seed');\n} else {\n    $output->writeln(PHP_EOL . '<comment>Skipping database migrations...</comment>' . PHP_EOL);\n}\n"
  },
  {
    "path": "composer.json",
    "content": "{\n    \"name\": \"pterodactyl/panel\",\n    \"description\": \"The free, open-source game management panel. Supporting Minecraft, Spigot, BungeeCord, and SRCDS servers.\",\n    \"license\": \"MIT\",\n    \"authors\": [\n        {\n            \"name\": \"Matthew Penner\",\n            \"email\": \"matthew@pterodactyl.io\",\n            \"homepage\": \"https://github.com/matthewpi\",\n            \"role\": \"Lead Developer\"\n        },\n        {\n            \"name\": \"Dane Everitt\",\n            \"email\": \"dane@daneeveritt.com\",\n            \"homepage\": \"https://github.com/DaneEveritt\",\n            \"role\": \"Developer\"\n        }\n    ],\n    \"require\": {\n        \"php\": \"^8.2 || ^8.3\",\n        \"ext-json\": \"*\",\n        \"ext-mbstring\": \"*\",\n        \"ext-pdo\": \"*\",\n        \"ext-pdo_mysql\": \"*\",\n        \"ext-posix\": \"*\",\n        \"ext-zip\": \"*\",\n        \"aws/aws-sdk-php\": \"^3.369\",\n        \"guzzlehttp/guzzle\": \"^7.9.2\",\n        \"hashids/hashids\": \"^5.0.2\",\n        \"laracasts/utilities\": \"~3.2.3\",\n        \"laravel/framework\": \"^11.31.0\",\n        \"laravel/helpers\": \"^1.8.0\",\n        \"laravel/sanctum\": \"^4.2.0\",\n        \"laravel/tinker\": \"^2.10.0\",\n        \"laravel/ui\": \"~4.5.2\",\n        \"lcobucci/jwt\": \"^5.6.0\",\n        \"league/flysystem-aws-s3-v3\": \"^3.30.1\",\n        \"league/flysystem-memory\": \"^3.29.0\",\n        \"matriphe/iso-639\": \"~2.0\",\n        \"phpseclib/phpseclib\": \"^3.0.47\",\n        \"pragmarx/google2fa\": \"~8.0.3\",\n        \"predis/predis\": \"^3.3.0\",\n        \"prologue/alerts\": \"^1.3.0\",\n        \"psr/cache\": \"^3.0.0\",\n        \"s1lentium/iptools\": \"~1.2.0\",\n        \"spatie/laravel-fractal\": \"^6.3.2\",\n        \"spatie/laravel-query-builder\": \"^6.3.6\",\n        \"staudenmeir/belongs-to-through\": \"^2.16.0\",\n        \"symfony/http-client\": \"^7.4.0\",\n        \"symfony/mailgun-mailer\": \"^7.4.0\",\n        \"symfony/postmark-mailer\": \"^7.4.0\",\n        \"symfony/yaml\": \"^7.4.0\",\n        \"webmozart/assert\": \"^1.11.0\"\n    },\n    \"require-dev\": {\n        \"barryvdh/laravel-ide-helper\": \"^3.6\",\n        \"fakerphp/faker\": \"^1.24\",\n        \"friendsofphp/php-cs-fixer\": \"~3.64.0\",\n        \"itsgoingd/clockwork\": \"^5.3\",\n        \"larastan/larastan\": \"^3.8\",\n        \"mockery/mockery\": \"^1.6\",\n        \"nunomaduro/collision\": \"^8.5\",\n        \"phpstan/phpstan\": \"^2.1\",\n        \"phpstan/phpstan-webmozart-assert\": \"^2.0\",\n        \"phpunit/phpunit\": \"^10.5.62\",\n        \"spatie/laravel-ignition\": \"^2.9\"\n    },\n    \"autoload\": {\n        \"files\": [\n            \"app/helpers.php\"\n        ],\n        \"psr-4\": {\n            \"Pterodactyl\\\\\": \"app/\",\n            \"Database\\\\Factories\\\\\": \"database/Factories/\",\n            \"Database\\\\Seeders\\\\\": \"database/Seeders/\"\n        }\n    },\n    \"autoload-dev\": {\n        \"psr-4\": {\n            \"Pterodactyl\\\\Tests\\\\\": \"tests/\"\n        }\n    },\n    \"scripts\": {\n        \"cs:fix\": \"php-cs-fixer fix\",\n        \"cs:check\": \"php-cs-fixer fix --dry-run --diff --verbose\",\n        \"post-autoload-dump\": [\n            \"Illuminate\\\\Foundation\\\\ComposerScripts::postAutoloadDump\",\n            \"@php artisan package:discover --ansi || true\"\n        ],\n        \"post-root-package-install\": [\n            \"@php -r \\\"file_exists('.env') || copy('.env.example', '.env');\\\"\"\n        ],\n        \"post-create-project-cmd\": [\n            \"@php artisan key:generate --ansi\",\n            \"@php -r \\\"file_exists('database/database.sqlite') || touch('database/database.sqlite');\\\"\",\n            \"@php artisan migrate --graceful --ansi\"\n        ]\n    },\n    \"config\": {\n        \"optimize-autoloader\": true,\n        \"preferred-install\": \"dist\",\n        \"sort-packages\": true,\n        \"platform\": {\n            \"php\": \"8.2.0\"\n        }\n    },\n    \"minimum-stability\": \"stable\",\n    \"prefer-stable\": true\n}\n"
  },
  {
    "path": "config/activity.php",
    "content": "<?php\n\nreturn [\n    // The number of days elapsed before old activity log entries are deleted.\n    'prune_days' => env('APP_ACTIVITY_PRUNE_DAYS', 90),\n\n    // If set to true activity log entries generated by an admin user that is not also\n    // a part of the server in question will be hidden from the activity logs API response.\n    //\n    // Activity will still be properly tracked, just not displayed.\n    'hide_admin_activity' => env('APP_ACTIVITY_HIDE_ADMIN', false),\n];\n"
  },
  {
    "path": "config/app.php",
    "content": "<?php\n\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Application Version\n    |--------------------------------------------------------------------------\n    | This value is set when creating a Pterodactyl release. You should not\n    | change this value if you are not maintaining your own internal versions.\n    */\n\n    'version' => 'canary',\n\n    /*\n    |--------------------------------------------------------------------------\n    | Application Name\n    |--------------------------------------------------------------------------\n    |\n    | This value is the name of your application, which will be used when the\n    | framework needs to place the application's name in a notification or\n    | other UI elements where an application name needs to be displayed.\n    |\n    */\n\n    'name' => env('APP_NAME', 'Pterodactyl'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Application Environment\n    |--------------------------------------------------------------------------\n    |\n    | This value determines the \"environment\" your application is currently\n    | running in. This may determine how you prefer to configure various\n    | services the application utilizes. Set this in your \".env\" file.\n    |\n    */\n\n    'env' => env('APP_ENV', 'production'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Application Debug Mode\n    |--------------------------------------------------------------------------\n    |\n    | When your application is in debug mode, detailed error messages with\n    | stack traces will be shown on every error that occurs within your\n    | application. If disabled, a simple generic error page is shown.\n    |\n    */\n\n    'debug' => (bool) env('APP_DEBUG', false),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Application URL\n    |--------------------------------------------------------------------------\n    |\n    | This URL is used by the console to properly generate URLs when using\n    | the Artisan command line tool. You should set this to the root of\n    | the application so that it's available within Artisan commands.\n    |\n    */\n\n    'url' => env('APP_URL', 'http://localhost'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Application Timezone\n    |--------------------------------------------------------------------------\n    |\n    | Here you may specify the default timezone for your application, which\n    | will be used by the PHP date and date-time functions. The timezone\n    | is set to \"UTC\" by default as it is suitable for most use cases.\n    |\n    */\n\n    'timezone' => env('APP_TIMEZONE', 'Asia/Shanghai'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Application Locale Configuration\n    |--------------------------------------------------------------------------\n    |\n    | The application locale determines the default locale that will be used\n    | by Laravel's translation / localization methods. This option can be\n    | set to any locale for which you plan to have translation strings.\n    |\n    */\n\n    'locale' => env('APP_LOCALE', 'zh'),\n\n    'fallback_locale' => env('APP_FALLBACK_LOCALE', 'en'),\n\n    'faker_locale' => env('APP_FAKER_LOCALE', 'zh_CN'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Encryption Key\n    |--------------------------------------------------------------------------\n    |\n    | This key is utilized by Laravel's encryption services and should be set\n    | to a random, 32 character string to ensure that all encrypted values\n    | are secure. You should do this prior to deploying the application.\n    |\n    */\n\n    'cipher' => 'AES-256-CBC',\n\n    'key' => env('APP_KEY'),\n\n    'previous_keys' => [\n        ...array_filter(\n            explode(',', env('APP_PREVIOUS_KEYS', ''))\n        ),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Maintenance Mode Driver\n    |--------------------------------------------------------------------------\n    |\n    | These configuration options determine the driver used to determine and\n    | manage Laravel's \"maintenance mode\" status. The \"cache\" driver will\n    | allow maintenance mode to be controlled across multiple machines.\n    |\n    | Supported drivers: \"file\", \"cache\"\n    |\n    */\n\n    'maintenance' => [\n        'driver' => env('APP_MAINTENANCE_DRIVER', 'file'),\n        'store' => env('APP_MAINTENANCE_STORE', 'database'),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Exception Reporter Configuration\n    |--------------------------------------------------------------------------\n    |\n    | If you're encountering weird behavior with the Panel and no exceptions\n    | are being logged try changing the environment variable below to be true.\n    | This will override the default \"don't report\" behavior of the Panel and log\n    | all exceptions. This will be quite noisy.\n    |\n    */\n\n    'exceptions' => [\n        'report_all' => env('APP_REPORT_ALL_EXCEPTIONS', false),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Autoloaded Service Providers\n    |--------------------------------------------------------------------------\n    |\n    | The service providers listed here will be automatically loaded on the\n    | request to your application. Feel free to add your own services to\n    | this array to grant expanded functionality to your applications.\n    |\n    */\n\n    'providers' => [\n        /*\n         * Laravel Framework Service Providers...\n         */\n        Illuminate\\Auth\\AuthServiceProvider::class,\n        Illuminate\\Broadcasting\\BroadcastServiceProvider::class,\n        Illuminate\\Bus\\BusServiceProvider::class,\n        Illuminate\\Cache\\CacheServiceProvider::class,\n        Illuminate\\Foundation\\Providers\\ConsoleSupportServiceProvider::class,\n        Illuminate\\Cookie\\CookieServiceProvider::class,\n        Illuminate\\Database\\DatabaseServiceProvider::class,\n        Illuminate\\Encryption\\EncryptionServiceProvider::class,\n        Illuminate\\Filesystem\\FilesystemServiceProvider::class,\n        Illuminate\\Foundation\\Providers\\FoundationServiceProvider::class,\n        Illuminate\\Hashing\\HashServiceProvider::class,\n        Illuminate\\Mail\\MailServiceProvider::class,\n        Illuminate\\Notifications\\NotificationServiceProvider::class,\n        Illuminate\\Pagination\\PaginationServiceProvider::class,\n        Illuminate\\Pipeline\\PipelineServiceProvider::class,\n        Illuminate\\Queue\\QueueServiceProvider::class,\n        Illuminate\\Redis\\RedisServiceProvider::class,\n        Illuminate\\Auth\\Passwords\\PasswordResetServiceProvider::class,\n        Illuminate\\Session\\SessionServiceProvider::class,\n        Illuminate\\Translation\\TranslationServiceProvider::class,\n        Illuminate\\Validation\\ValidationServiceProvider::class,\n        Illuminate\\View\\ViewServiceProvider::class,\n\n        /*\n         * Application Service Providers...\n         */\n        Pterodactyl\\Providers\\ActivityLogServiceProvider::class,\n        Pterodactyl\\Providers\\AppServiceProvider::class,\n        Pterodactyl\\Providers\\AuthServiceProvider::class,\n        Pterodactyl\\Providers\\BackupsServiceProvider::class,\n        Pterodactyl\\Providers\\BladeServiceProvider::class,\n        Pterodactyl\\Providers\\EventServiceProvider::class,\n        Pterodactyl\\Providers\\HashidsServiceProvider::class,\n        Pterodactyl\\Providers\\RouteServiceProvider::class,\n        Pterodactyl\\Providers\\RepositoryServiceProvider::class,\n        Pterodactyl\\Providers\\ViewComposerServiceProvider::class,\n\n        /*\n         * Additional Dependencies\n         */\n        Prologue\\Alerts\\AlertsServiceProvider::class,\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Class Aliases\n    |--------------------------------------------------------------------------\n    |\n    | This array of class aliases will be registered when this application\n    | is started. However, feel free to register as many as you wish as\n    | the aliases are \"lazy\" loaded, so they don't hinder performance.\n    |\n    */\n\n    'aliases' => Illuminate\\Support\\Facades\\Facade::defaultAliases()->merge([\n        'Alert' => Prologue\\Alerts\\Facades\\Alert::class,\n        'Carbon' => Carbon\\Carbon::class,\n        'JavaScript' => Laracasts\\Utilities\\JavaScript\\JavaScriptFacade::class,\n        'Theme' => Pterodactyl\\Extensions\\Facades\\Theme::class,\n\n        // Custom Facades\n        'Activity' => Pterodactyl\\Facades\\Activity::class,\n        'LogBatch' => Pterodactyl\\Facades\\LogBatch::class,\n        'LogTarget' => Pterodactyl\\Facades\\LogTarget::class,\n    ])->toArray(),\n];\n"
  },
  {
    "path": "config/auth.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Lockout Configuration\n    |--------------------------------------------------------------------------\n    |\n    | These options are Pterodactyl specific and allow you to configure how\n    | long a user should be locked out for if they input a username or\n    | password incorrectly.\n    |\n    */\n\n    'lockout' => [\n        'time' => 2,\n        'attempts' => 3,\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Authentication Defaults\n    |--------------------------------------------------------------------------\n    |\n    | This option defines the default authentication \"guard\" and password\n    | reset \"broker\" for your application. You may change these values\n    | as required, but they're a perfect start for most applications.\n    |\n    */\n\n    'defaults' => [\n        'guard' => 'web',\n        'passwords' => 'users',\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Authentication Guards\n    |--------------------------------------------------------------------------\n    |\n    | Next, you may define every authentication guard for your application.\n    | Of course, a great default configuration has been defined for you\n    | which utilizes session storage plus the Eloquent user provider.\n    |\n    | All authentication guards have a user provider, which defines how the\n    | users are actually retrieved out of your database or other storage\n    | system used by the application. Typically, Eloquent is utilized.\n    |\n    | Supported: \"session\", \"token\"\n    |\n    */\n\n    'guards' => [\n        'web' => [\n            'driver' => 'session',\n            'provider' => 'users',\n        ],\n\n        'api' => [\n            'driver' => 'token',\n            'provider' => 'users',\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | User Providers\n    |--------------------------------------------------------------------------\n    |\n    | All authentication guards have a user provider, which defines how the\n    | users are actually retrieved out of your database or other storage\n    | system used by the application. Typically, Eloquent is utilized.\n    |\n    | If you have multiple user tables or models you may configure multiple\n    | providers to represent the model / table. These providers may then\n    | be assigned to any extra authentication guards you have defined.\n    |\n    | Supported: \"database\", \"eloquent\"\n    |\n    */\n\n    'providers' => [\n        'users' => [\n            'driver' => 'eloquent',\n            'model' => Pterodactyl\\Models\\User::class,\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Resetting Passwords\n    |--------------------------------------------------------------------------\n    |\n    | These configuration options specify the behavior of Laravel's password\n    | reset functionality, including the table utilized for token storage\n    | and the user provider that is invoked to actually retrieve users.\n    |\n    | The expiry time is the number of minutes that each reset token will be\n    | considered valid. This security feature keeps tokens short-lived so\n    | they have less time to be guessed. You may change this as needed.\n    |\n    | The throttle setting is the number of seconds a user must wait before\n    | generating more password reset tokens. This prevents the user from\n    | quickly generating a very large amount of password reset tokens.\n    |\n    */\n\n    'passwords' => [\n        'users' => [\n            'provider' => 'users',\n            'table' => 'password_resets',\n            'expire' => 60,\n            'throttle' => 60,\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Password Confirmation Timeout\n    |--------------------------------------------------------------------------\n    |\n    | Here you may define the amount of seconds before a password confirmation\n    | window expires and users are asked to re-enter their password via the\n    | confirmation screen. By default, the timeout lasts for three hours.\n    |\n    */\n\n    'password_timeout' => env('AUTH_PASSWORD_TIMEOUT', 10800),\n];\n"
  },
  {
    "path": "config/backups.php",
    "content": "<?php\n\nuse Pterodactyl\\Models\\Backup;\n\nreturn [\n    // The backup driver to use for this Panel instance. All client generated server backups\n    // will be stored in this location by default. It is possible to change this once backups\n    // have been made, without losing data.\n    'default' => env('APP_BACKUP_DRIVER', Backup::ADAPTER_WINGS),\n\n    // This value is used to determine the lifespan of UploadPart presigned urls that wings\n    // uses to upload backups to S3 storage.  Value is in minutes, so this would default to an hour.\n    'presigned_url_lifespan' => (int) env('BACKUP_PRESIGNED_URL_LIFESPAN', 60),\n\n    // This value defines the maximal size of a single part for the S3 multipart upload during backups\n    // The maximal part size must be given in bytes. The default value is 5GB.\n    // Note that 5GB is the maximum for a single part when using AWS S3.\n    'max_part_size' => env('BACKUP_MAX_PART_SIZE', 5 * 1024 * 1024 * 1024),\n\n    // The time to wait before automatically failing a backup, time is in minutes and defaults\n    // to 6 hours.  To disable this feature, set the value to `0`.\n    'prune_age' => env('BACKUP_PRUNE_AGE', 360),\n\n    // Defines the backup creation throttle limits for users. In this default example, we allow\n    // a user to create two (successful or pending) backups per 10 minutes. Even if they delete\n    // a backup it will be included in the throttle count.\n    //\n    // Set the period to \"0\" to disable this throttle. The period is defined in seconds.\n    'throttles' => [\n        'limit' => env('BACKUP_THROTTLE_LIMIT', 2),\n        'period' => env('BACKUP_THROTTLE_PERIOD', 600),\n    ],\n\n    'disks' => [\n        // There is no configuration for the local disk for Wings. That configuration\n        // is determined by the Daemon configuration, and not the Panel.\n        'wings' => [\n            'adapter' => Backup::ADAPTER_WINGS,\n        ],\n\n        // Configuration for storing backups in Amazon S3. This uses the same credentials\n        // specified in filesystems.php but does include some more specific settings for\n        // backups, notably bucket, location, and use_accelerate_endpoint.\n        's3' => [\n            'adapter' => Backup::ADAPTER_AWS_S3,\n\n            'region' => env('AWS_DEFAULT_REGION'),\n            'key' => env('AWS_ACCESS_KEY_ID'),\n            'secret' => env('AWS_SECRET_ACCESS_KEY'),\n\n            // The S3 bucket to use for backups.\n            'bucket' => env('AWS_BACKUPS_BUCKET'),\n\n            // The location within the S3 bucket where backups will be stored. Backups\n            // are stored within a folder using the server's UUID as the name. Each\n            // backup for that server lives within that folder.\n            'prefix' => env('AWS_BACKUPS_BUCKET') ?? '',\n\n            'endpoint' => env('AWS_ENDPOINT'),\n            'use_path_style_endpoint' => env('AWS_USE_PATH_STYLE_ENDPOINT', false),\n            'use_accelerate_endpoint' => env('AWS_BACKUPS_USE_ACCELERATE', false),\n\n            'storage_class' => env('AWS_BACKUPS_STORAGE_CLASS'),\n        ],\n    ],\n];\n"
  },
  {
    "path": "config/broadcasting.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Default Broadcaster\n    |--------------------------------------------------------------------------\n    |\n    | This option controls the default broadcaster that will be used by the\n    | framework when an event needs to be broadcast. You may set this to\n    | any of the connections defined in the \"connections\" array below.\n    |\n    | Supported: \"pusher\", \"ably\", \"redis\", \"log\", \"null\"\n    |\n    */\n\n    'default' => env('BROADCAST_DRIVER', 'null'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Broadcast Connections\n    |--------------------------------------------------------------------------\n    |\n    | Here you may define all of the broadcast connections that will be used\n    | to broadcast events to other systems or over websockets. Samples of\n    | each available type of connection are provided inside this array.\n    |\n    */\n\n    'connections' => [\n        'pusher' => [\n            'driver' => 'pusher',\n            'key' => env('PUSHER_APP_KEY'),\n            'secret' => env('PUSHER_APP_SECRET'),\n            'app_id' => env('PUSHER_APP_ID'),\n            'options' => [\n                'host' => env('PUSHER_HOST', 'api-' . env('PUSHER_APP_CLUSTER', 'mt1') . '.pusher.com') ?: 'api-' . env('PUSHER_APP_CLUSTER', 'mt1') . '.pusher.com',\n                'port' => env('PUSHER_PORT', 443),\n                'scheme' => env('PUSHER_SCHEME', 'https'),\n                'encrypted' => true,\n                'useTLS' => env('PUSHER_SCHEME', 'https') === 'https',\n            ],\n            'client_options' => [\n                // Guzzle client options: https://docs.guzzlephp.org/en/stable/request-options.html\n            ],\n        ],\n\n        'ably' => [\n            'driver' => 'ably',\n            'key' => env('ABLY_KEY'),\n        ],\n\n        'redis' => [\n            'driver' => 'redis',\n            'connection' => 'default',\n        ],\n\n        'log' => [\n            'driver' => 'log',\n        ],\n\n        'null' => [\n            'driver' => 'null',\n        ],\n    ],\n];\n"
  },
  {
    "path": "config/cache.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Str;\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Default Cache Store\n    |--------------------------------------------------------------------------\n    |\n    | This option controls the default cache store that will be used by the\n    | framework. This connection is utilized if another isn't explicitly\n    | specified when running a cache operation inside the application.\n    |\n    */\n\n    'default' => env('CACHE_STORE', env('CACHE_DRIVER', 'redis')),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Cache Stores\n    |--------------------------------------------------------------------------\n    |\n    | Here you may define all of the cache \"stores\" for your application as\n    | well as their drivers. You may even define multiple stores for the\n    | same cache driver to group types of items stored in your caches.\n    |\n    | Supported drivers: \"array\", \"database\", \"file\", \"memcached\",\n    |                    \"redis\", \"octane\", \"null\"\n    |\n    */\n\n    'stores' => [\n        'array' => [\n            'driver' => 'array',\n            'serialize' => false,\n        ],\n\n        'database' => [\n            'driver' => 'database',\n            'connection' => env('DB_CACHE_CONNECTION'),\n            'table' => env('DB_CACHE_TABLE', 'cache'),\n            'lock_connection' => env('DB_CACHE_LOCK_CONNECTION'),\n            'lock_table' => env('DB_CACHE_LOCK_TABLE'),\n        ],\n\n        'file' => [\n            'driver' => 'file',\n            'path' => storage_path('framework/cache/data'),\n            'lock_path' => storage_path('framework/cache/data'),\n        ],\n\n        'memcached' => [\n            'driver' => 'memcached',\n            'persistent_id' => env('MEMCACHED_PERSISTENT_ID'),\n            'sasl' => [\n                env('MEMCACHED_USERNAME'),\n                env('MEMCACHED_PASSWORD'),\n            ],\n            'options' => [\n                // Memcached::OPT_CONNECT_TIMEOUT => 2000,\n            ],\n            'servers' => [\n                [\n                    'host' => env('MEMCACHED_HOST', '127.0.0.1'),\n                    'port' => env('MEMCACHED_PORT', 11211),\n                    'weight' => 100,\n                ],\n            ],\n        ],\n\n        'redis' => [\n            'driver' => 'redis',\n            'connection' => env('REDIS_CACHE_CONNECTION', 'default'),\n            'lock_connection' => env('REDIS_CACHE_LOCK_CONNECTION', 'default'),\n        ],\n\n        'sessions' => [\n            'driver' => env('SESSION_DRIVER', 'database'),\n            'table' => 'sessions',\n            'connection' => env('SESSION_DRIVER') === 'redis' ? 'sessions' : null,\n        ],\n\n        'octane' => [\n            'driver' => 'octane',\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Cache Key Prefix\n    |--------------------------------------------------------------------------\n    |\n    | When utilizing the APC, database, memcached, Redis, or DynamoDB cache\n    | stores there might be other applications using the same cache. For\n    | that reason, you may prefix every cache key to avoid collisions.\n    |\n    */\n\n    'prefix' => env('CACHE_PREFIX', Str::slug(env('APP_NAME', 'pterodactyl'), '_') . '_cache_'),\n];\n"
  },
  {
    "path": "config/compile.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Additional Compiled Classes\n    |--------------------------------------------------------------------------\n    |\n    | Here you may specify additional classes to include in the compiled file\n    | generated by the `artisan optimize` command. These should be classes\n    | that are included on basically every request into the application.\n    |\n    */\n\n    'files' => [\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Compiled File Providers\n    |--------------------------------------------------------------------------\n    |\n    | Here you may list service providers which define a \"compiles\" function\n    | that returns additional files that should be compiled, providing an\n    | easy way to get common files from any packages you are utilizing.\n    |\n    */\n\n    'providers' => [\n    ],\n];\n"
  },
  {
    "path": "config/cors.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Cross-Origin Resource Sharing (CORS) Configuration\n    |--------------------------------------------------------------------------\n    |\n    | Here you may configure your settings for cross-origin resource sharing\n    | or \"CORS\". This determines what cross-origin operations may execute\n    | in web browsers. You are free to adjust these settings as needed.\n    |\n    | To learn more: https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS\n    |\n    */\n\n    /*\n     * You can enable CORS for 1 or multiple paths.\n     * Example: ['api/*']\n     */\n    'paths' => ['/api/client', '/api/application', '/api/client/*', '/api/application/*'],\n\n    /*\n     * Matches the request method. `['*']` allows all methods.\n     */\n    'allowed_methods' => ['GET', 'POST', 'PUT', 'PATCH', 'DELETE', 'HEAD'],\n\n    /*\n     * Matches the request origin. `['*']` allows all origins. Wildcards can be used, eg `*.mydomain.com`\n     */\n    'allowed_origins' => explode(',', env('APP_CORS_ALLOWED_ORIGINS') ?? ''),\n\n    /*\n     * Patterns that can be used with `preg_match` to match the origin.\n     */\n    'allowed_origins_patterns' => [],\n\n    /*\n     * Sets the Access-Control-Allow-Headers response header. `['*']` allows all headers.\n     */\n    'allowed_headers' => ['*'],\n\n    /*\n     * Sets the Access-Control-Expose-Headers response header with these headers.\n     */\n    'exposed_headers' => [],\n\n    /*\n     * Sets the Access-Control-Max-Age response header when > 0.\n     */\n    'max_age' => 0,\n\n    /*\n     * Sets the Access-Control-Allow-Credentials header.\n     */\n    'supports_credentials' => true,\n];\n"
  },
  {
    "path": "config/database.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Helpers\\Time;\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Default Database Connection Name\n    |--------------------------------------------------------------------------\n    |\n    | Here you may specify which of the database connections below you wish\n    | to use as your default connection for database operations. This is\n    | the connection which will be utilized unless another connection\n    | is explicitly specified when you execute a query / statement.\n    |\n    */\n\n    'default' => env('DB_CONNECTION', 'mysql'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Database Connections\n    |--------------------------------------------------------------------------\n    |\n    | Here are each of the database connections setup for your application.\n    | Of course, examples of configuring each database platform that is\n    | supported by Laravel is shown below to make development simple.\n    |\n    |\n    | All database work in Laravel is done through the PHP PDO facilities\n    | so make sure you have the driver for your particular database of\n    | choice installed on your machine before you begin development.\n    |\n    */\n\n    'connections' => [\n        'mysql' => [\n            'driver' => 'mysql',\n            'url' => env('DB_URL', env('DATABASE_URL')),\n            'host' => env('DB_HOST', '127.0.0.1'),\n            'port' => env('DB_PORT', '3306'),\n            'database' => env('DB_DATABASE', 'panel'),\n            'username' => env('DB_USERNAME', 'pterodactyl'),\n            'password' => env('DB_PASSWORD', ''),\n            'unix_socket' => env('DB_SOCKET', ''),\n            'charset' => env('DB_CHARSET', 'utf8mb4'),\n            'collation' => env('DB_COLLATION', 'utf8mb4_unicode_ci'),\n            'prefix' => env('DB_PREFIX', ''),\n            'prefix_indexes' => true,\n            'strict' => env('DB_STRICT_MODE', false), // TODO: true by default\n            'engine' => null,\n            'timezone' => env('DB_TIMEZONE', Time::getMySQLTimezoneOffset(env('APP_TIMEZONE', 'UTC'))),\n            'sslmode' => env('DB_SSLMODE', 'prefer'),\n            'options' => extension_loaded('pdo_mysql') ? array_filter([\n                PDO::MYSQL_ATTR_SSL_CA => env('MYSQL_ATTR_SSL_CA'),\n                PDO::MYSQL_ATTR_SSL_CERT => env('MYSQL_ATTR_SSL_CERT'),\n                PDO::MYSQL_ATTR_SSL_KEY => env('MYSQL_ATTR_SSL_KEY'),\n                PDO::MYSQL_ATTR_SSL_VERIFY_SERVER_CERT => env('MYSQL_ATTR_SSL_VERIFY_SERVER_CERT', true),\n            ]) : [],\n        ],\n\n        'mariadb' => [\n            'driver' => 'mariadb',\n            'url' => env('DB_URL', env('DATABASE_URL')),\n            'host' => env('DB_HOST', '127.0.0.1'),\n            'port' => env('DB_PORT', '3306'),\n            'database' => env('DB_DATABASE', 'panel'),\n            'username' => env('DB_USERNAME', 'pterodactyl'),\n            'password' => env('DB_PASSWORD', ''),\n            'unix_socket' => env('DB_SOCKET', ''),\n            'charset' => env('DB_CHARSET', 'utf8mb4'),\n            'collation' => env('DB_COLLATION', 'utf8mb4_unicode_ci'),\n            'prefix' => env('DB_PREFIX', ''),\n            'prefix_indexes' => true,\n            'strict' => env('DB_STRICT_MODE', true),\n            'engine' => null,\n            'timezone' => env('DB_TIMEZONE', Time::getMySQLTimezoneOffset(env('APP_TIMEZONE', 'UTC'))),\n            'sslmode' => env('DB_SSLMODE', 'prefer'),\n            'options' => extension_loaded('pdo_mysql') ? array_filter([\n                PDO::MYSQL_ATTR_SSL_CA => env('MYSQL_ATTR_SSL_CA'),\n                PDO::MYSQL_ATTR_SSL_CERT => env('MYSQL_ATTR_SSL_CERT'),\n                PDO::MYSQL_ATTR_SSL_KEY => env('MYSQL_ATTR_SSL_KEY'),\n                PDO::MYSQL_ATTR_SSL_VERIFY_SERVER_CERT => env('MYSQL_ATTR_SSL_VERIFY_SERVER_CERT', true),\n            ]) : [],\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Migration Repository Table\n    |--------------------------------------------------------------------------\n    |\n    | This table keeps track of all the migrations that have already run for\n    | your application. Using this information, we can determine which of\n    | the migrations on disk haven't actually been run on the database.\n    |\n    */\n\n    'migrations' => [\n        'table' => 'migrations',\n        'update_date_on_publish' => true,\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Redis Databases\n    |--------------------------------------------------------------------------\n    |\n    | Redis is an open source, fast, and advanced key-value store that also\n    | provides a richer body of commands than a typical key-value system\n    | such as Memcached. You may define your connection settings here.\n    |\n    */\n\n    'redis' => [\n        'client' => env('REDIS_CLIENT', 'predis'),\n\n        'options' => [\n            'cluster' => env('REDIS_CLUSTER', 'redis'),\n            'prefix' => env('REDIS_PREFIX', Str::slug(env('APP_NAME', 'pterodactyl'), '_') . '_database_'),\n        ],\n\n        'default' => [\n            'scheme' => env('REDIS_SCHEME', 'tcp'),\n            'path' => env('REDIS_PATH', '/run/redis/redis.sock'),\n            'host' => env('REDIS_HOST', 'localhost'),\n            'username' => env('REDIS_USERNAME'),\n            'password' => env('REDIS_PASSWORD'),\n            'port' => env('REDIS_PORT', 6379),\n            'database' => env('REDIS_DATABASE', 0),\n            'context' => extension_loaded('redis') && env('REDIS_CLIENT') === 'phpredis' ? [\n                'stream' => array_filter([\n                    'verify_peer' => env('REDIS_VERIFY_PEER', true),\n                    'verify_peer_name' => env('REDIS_VERIFY_PEER_NAME', true),\n                    'cafile' => env('REDIS_CAFILE'),\n                    'local_cert' => env('REDIS_LOCAL_CERT'),\n                    'local_pk' => env('REDIS_LOCAL_PK'),\n                ]),\n            ] : [],\n        ],\n\n        'sessions' => [\n            'scheme' => env('REDIS_SCHEME', 'tcp'),\n            'path' => env('REDIS_PATH', '/run/redis/redis.sock'),\n            'host' => env('REDIS_HOST', 'localhost'),\n            'username' => env('REDIS_USERNAME'),\n            'password' => env('REDIS_PASSWORD'),\n            'port' => env('REDIS_PORT', 6379),\n            'database' => env('REDIS_DATABASE_SESSIONS', 1),\n            'context' => extension_loaded('redis') && env('REDIS_CLIENT') === 'phpredis' ? [\n                'stream' => array_filter([\n                    'verify_peer' => env('REDIS_VERIFY_PEER', true),\n                    'verify_peer_name' => env('REDIS_VERIFY_PEER_NAME', true),\n                    'cafile' => env('REDIS_CAFILE'),\n                    'local_cert' => env('REDIS_LOCAL_CERT'),\n                    'local_pk' => env('REDIS_LOCAL_PK'),\n                ]),\n            ] : [],\n        ],\n    ],\n];\n"
  },
  {
    "path": "config/egg_features/eula.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Egg Feature: EULA Popup\n    |--------------------------------------------------------------------------\n    |\n    | This popup is enabled for Minecraft eggs and allows a custom frontend\n    | hook to run that monitors the console output of the server and pops up\n    | a modal asking the user to accept it if necessary.\n    |\n    | There is no additional configuration necessary.\n    |\n    */\n];\n"
  },
  {
    "path": "config/filesystems.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Default Filesystem Disk\n    |--------------------------------------------------------------------------\n    |\n    | Here you may specify the default filesystem disk that should be used\n    | by the framework. The \"local\" disk, as well as a variety of cloud\n    | based disks are available to your application for file storage.\n    |\n    */\n\n    'default' => env('FILESYSTEM_DISK', 'local'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Filesystem Disks\n    |--------------------------------------------------------------------------\n    |\n    | Below you may configure as many filesystem disks as necessary, and you\n    | may even configure multiple disks for the same driver. Examples for\n    | most supported storage drivers are configured here for reference.\n    |\n    | Supported drivers: \"local\", \"ftp\", \"sftp\", \"s3\"\n    |\n    */\n\n    'disks' => [\n        'local' => [\n            'driver' => 'local',\n            'root' => storage_path('app/private'),\n            'serve' => true,\n            'throw' => false,\n        ],\n\n        'public' => [\n            'driver' => 'local',\n            'root' => storage_path('app/public'),\n            'url' => env('APP_URL') . '/storage',\n            'visibility' => 'public',\n            'throw' => false,\n        ],\n\n        's3' => [\n            'driver' => 's3',\n            'key' => env('AWS_ACCESS_KEY_ID'),\n            'secret' => env('AWS_SECRET_ACCESS_KEY'),\n            'region' => env('AWS_DEFAULT_REGION'),\n            'bucket' => env('AWS_BUCKET'),\n            'url' => env('AWS_URL'),\n            'endpoint' => env('AWS_ENDPOINT'),\n            'use_path_style_endpoint' => env('AWS_USE_PATH_STYLE_ENDPOINT', false),\n            'throw' => false,\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Symbolic Links\n    |--------------------------------------------------------------------------\n    |\n    | Here you may configure the symbolic links that will be created when the\n    | `storage:link` Artisan command is executed. The array keys should be\n    | the locations of the links and the values should be their targets.\n    |\n    */\n\n    'links' => [\n        public_path('storage') => storage_path('app/public'),\n    ],\n];\n"
  },
  {
    "path": "config/fractal.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Default Serializer\n    |--------------------------------------------------------------------------\n    |\n    | The default serializer to be used when performing a transformation. It\n    | may be left empty to use Fractal's default one. This can either be a\n    | string or a League\\Fractal\\Serializer\\SerializerAbstract subclass.\n    |\n    */\n\n    'default_serializer' => League\\Fractal\\Serializer\\JsonApiSerializer::class,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Auto Includes\n    |--------------------------------------------------------------------------\n    |\n    | If enabled Fractal will automatically add the includes who's\n    | names are present in the `include` request parameter.\n    |\n    */\n\n    'auto_includes' => [\n        'enabled' => true,\n        'request_key' => 'include',\n    ],\n];\n"
  },
  {
    "path": "config/hashids.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Hashids Configuration\n    |--------------------------------------------------------------------------\n    |\n    | Here are the settings that control the Hashids setup and usage in the panel.\n    |\n    */\n    'salt' => env('HASHIDS_SALT'),\n    'length' => env('HASHIDS_LENGTH', 8),\n    'alphabet' => env('HASHIDS_ALPHABET', 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890'),\n];\n"
  },
  {
    "path": "config/hashing.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Default Hash Driver\n    |--------------------------------------------------------------------------\n    |\n    | This option controls the default hash driver that will be used to hash\n    | passwords for your application. By default, the bcrypt algorithm is\n    | used; however, you remain free to modify this option if you wish.\n    |\n    | Supported: \"bcrypt\", \"argon\", \"argon2id\"\n    |\n    */\n\n    'driver' => 'bcrypt',\n\n    /*\n    |--------------------------------------------------------------------------\n    | Bcrypt Options\n    |--------------------------------------------------------------------------\n    |\n    | Here you may specify the configuration options that should be used when\n    | passwords are hashed using the Bcrypt algorithm. This will allow you\n    | to control the amount of time it takes to hash the given password.\n    |\n    */\n\n    'bcrypt' => [\n        'rounds' => env('BCRYPT_ROUNDS', 10),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Argon Options\n    |--------------------------------------------------------------------------\n    |\n    | Here you may specify the configuration options that should be used when\n    | passwords are hashed using the Argon algorithm. These will allow you\n    | to control the amount of time it takes to hash the given password.\n    |\n    */\n\n    'argon' => [\n        'memory' => 65536,\n        'threads' => 1,\n        'time' => 4,\n    ],\n];\n"
  },
  {
    "path": "config/http.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | API Rate Limits\n    |--------------------------------------------------------------------------\n    |\n    | Defines the rate limit for the number of requests per minute that can be\n    | executed against both the client and internal (application) APIs over the\n    | defined period (by default, 1 minute).\n    |\n    */\n    'rate_limit' => [\n        'client_period' => 1,\n        'client' => env('APP_API_CLIENT_RATELIMIT', 256),\n\n        'application_period' => 1,\n        'application' => env('APP_API_APPLICATION_RATELIMIT', 256),\n    ],\n];\n"
  },
  {
    "path": "config/icp.php",
    "content": "<?php\n/*\n|--------------------------------------------------------------------------\n| ICP License Configuration\n|--------------------------------------------------------------------------\n|\n| Web services in China require ICP license, a permit issued by the Chinese government\n| to permit China-based websites to operate in China. In order to fulfill the\n| conditions, you should apply for ICP license from your service provider.\n|\n*/\n\nreturn [\n    /*\n     * Enable or disable ICP\n     */\n    'enabled' => env('ICP_ENABLED', false),\n\n    /*\n     * ICP record\n     */\n    'record' => env('ICP_RECORD'),\n\n    /*\n     * Public security record\n     */\n    'security_record' => env('ICP_SECURITY_RECORD'),\n];\n"
  },
  {
    "path": "config/ide-helper.php",
    "content": "<?php\n\nreturn [\n\n    /*\n    |--------------------------------------------------------------------------\n    | Filename\n    |--------------------------------------------------------------------------\n    |\n    | The default filename.\n    |\n    */\n\n    'filename' => '_ide_helper.php',\n\n    /*\n    |--------------------------------------------------------------------------\n    | Models filename\n    |--------------------------------------------------------------------------\n    |\n    | The default filename for the models helper file.\n    |\n    */\n\n    'models_filename' => '_ide_helper_models.php',\n\n    /*\n    |--------------------------------------------------------------------------\n    | PhpStorm meta filename\n    |--------------------------------------------------------------------------\n    |\n    | PhpStorm also supports the directory `.phpstorm.meta.php/` with arbitrary\n    | files in it, should you need additional files for your project; e.g.\n    | `.phpstorm.meta.php/laravel_ide_Helper.php'.\n    |\n    */\n    'meta_filename' => '.phpstorm.meta.php',\n\n    /*\n    |--------------------------------------------------------------------------\n    | Fluent helpers\n    |--------------------------------------------------------------------------\n    |\n    | Set to true to generate commonly used Fluent methods.\n    |\n    */\n\n    'include_fluent' => false,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Factory builders\n    |--------------------------------------------------------------------------\n    |\n    | Set to true to generate factory generators for better factory()\n    | method auto-completion.\n    |\n    | Deprecated for Laravel 8 or latest.\n    |\n    */\n\n    'include_factory_builders' => false,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Write model magic methods\n    |--------------------------------------------------------------------------\n    |\n    | Set to false to disable write magic methods of model.\n    |\n    */\n\n    'write_model_magic_where' => false,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Write model external Eloquent builder methods\n    |--------------------------------------------------------------------------\n    |\n    | Set to false to disable write external Eloquent builder methods.\n    |\n    */\n\n    'write_model_external_builder_methods' => true,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Write model relation count and exists properties\n    |--------------------------------------------------------------------------\n    |\n    | Set to false to disable writing of relation count and exists properties\n    | to model DocBlocks.\n    |\n    */\n\n    'write_model_relation_count_properties' => false,\n    'write_model_relation_exists_properties' => false,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Write Eloquent model mixins\n    |--------------------------------------------------------------------------\n    |\n    | This will add the necessary DocBlock mixins to the model class\n    | contained in the Laravel framework. This helps the IDE with\n    | auto-completion.\n    |\n    | Please be aware that this setting changes a file within the /vendor directory.\n    |\n    */\n\n    'write_eloquent_model_mixins' => false,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Helper files to include\n    |--------------------------------------------------------------------------\n    |\n    | Include helper files. By default not included, but can be toggled with the\n    | -- helpers (-H) option. Extra helper files can be included.\n    |\n    */\n\n    'include_helpers' => false,\n\n    'helper_files' => [\n        base_path() . '/vendor/laravel/framework/src/Illuminate/Support/helpers.php',\n        base_path() . '/vendor/laravel/framework/src/Illuminate/Foundation/helpers.php',\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Model locations to include\n    |--------------------------------------------------------------------------\n    |\n    | Define in which directories the ide-helper:models command should look\n    | for models.\n    |\n    | glob patterns are supported to easier reach models in sub-directories,\n    | e.g. `app/Services/* /Models` (without the space).\n    |\n    */\n\n    'model_locations' => [\n        'app/Models',\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Models to ignore\n    |--------------------------------------------------------------------------\n    |\n    | Define which models should be ignored.\n    |\n    */\n\n    'ignored_models' => [\n        // App\\MyModel::class,\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Models hooks\n    |--------------------------------------------------------------------------\n    |\n    | Define which hook classes you want to run for models to add custom information.\n    |\n    | Hooks should implement Barryvdh\\LaravelIdeHelper\\Contracts\\ModelHookInterface.\n    |\n    */\n\n    'model_hooks' => [\n        // App\\Support\\IdeHelper\\MyModelHook::class\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Extra classes\n    |--------------------------------------------------------------------------\n    |\n    | These implementations are not really extended, but called with magic functions.\n    |\n    */\n\n    'extra' => [\n        'Eloquent' => ['Illuminate\\Database\\Eloquent\\Builder', 'Illuminate\\Database\\Query\\Builder'],\n        'Session' => ['Illuminate\\Session\\Store'],\n    ],\n\n    'magic' => [],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Interface implementations\n    |--------------------------------------------------------------------------\n    |\n    | These interfaces will be replaced with the implementing class. Some interfaces\n    | are detected by the helpers, others can be listed below.\n    |\n    */\n\n    'interfaces' => [\n        // App\\MyInterface::class => App\\MyImplementation::class,\n    ],\n\n    /*\n     |--------------------------------------------------------------------------\n     | Support for camel cased models\n     |--------------------------------------------------------------------------\n     |\n     | There are some Laravel packages (such as Eloquence) that allow for accessing\n     | Eloquent model properties via camel case, instead of snake case.\n     |\n     | Enabling this option will support these packages by saving all model\n     | properties as camel case, instead of snake case.\n     |\n     | For example, normally you would see this:\n     |\n     |  * @property \\Illuminate\\Support\\Carbon $created_at\n     |  * @property \\Illuminate\\Support\\Carbon $updated_at\n     |\n     | With this enabled, the properties will be this:\n     |\n     |  * @property \\Illuminate\\Support\\Carbon $createdAt\n     |  * @property \\Illuminate\\Support\\Carbon $updatedAt\n     |\n     | Note, it is currently an all-or-nothing option.\n     |\n     */\n    'model_camel_case_properties' => false,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Property casts\n    |--------------------------------------------------------------------------\n    |\n    | Cast the given \"real type\" to the given \"type\".\n    |\n    */\n    'type_overrides' => [\n        'integer' => 'int',\n        'boolean' => 'bool',\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Include DocBlocks from classes\n    |--------------------------------------------------------------------------\n    |\n    | Include DocBlocks from classes to allow additional code inspection for\n    | magic methods and properties.\n    |\n    */\n    'include_class_docblocks' => false,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Force FQN usage\n    |--------------------------------------------------------------------------\n    |\n    | Use the fully qualified (class) name in DocBlocks,\n    | even if the class exists in the same namespace\n    | or there is an import (use className) of the class.\n    |\n    */\n    'force_fqn' => true,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Use generics syntax\n    |--------------------------------------------------------------------------\n    |\n    | Use generics syntax within DocBlocks,\n    | e.g. `Collection<User>` instead of `Collection|User[]`.\n    |\n    */\n    'use_generics_annotations' => true,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Default return types for macros\n    |--------------------------------------------------------------------------\n    |\n    | Define default return types for macros without explicit return types.\n    | e.g. `\\Illuminate\\Database\\Query\\Builder::class => 'static'`,\n    |      `\\Illuminate\\Support\\Str::class => 'string'`\n    |\n    */\n    'macro_default_return_types' => [\n        Illuminate\\Http\\Client\\Factory::class => Illuminate\\Http\\Client\\PendingRequest::class,\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Additional relation types\n    |--------------------------------------------------------------------------\n    |\n    | Sometimes it's needed to create custom relation types. The key of the array\n    | is the relationship method name. The value of the array is the fully-qualified\n    | class name of the relationship, e.g. `'relationName' => RelationShipClass::class`.\n    |\n    */\n    'additional_relation_types' => [],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Additional relation return types\n    |--------------------------------------------------------------------------\n    |\n    | When using custom relation types its possible for the class name to not contain\n    | the proper return type of the relation. The key of the array is the relationship\n    | method name. The value of the array is the return type of the relation ('many'\n    | or 'morphTo').\n    | e.g. `'relationName' => 'many'`.\n    |\n    */\n    'additional_relation_return_types' => [],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Enforce nullable Eloquent relationships on not null columns\n    |--------------------------------------------------------------------------\n    |\n    | When set to true (default), this option enforces nullable Eloquent relationships.\n    | However, in cases where the application logic ensures the presence of related\n    | records it may be desirable to set this option to false to avoid unwanted null warnings.\n    |\n    | Default: true\n    | A not null column with no foreign key constraint will have a \"nullable\" relationship.\n    |  * @property int $not_null_column_with_no_foreign_key_constraint\n    |  * @property-read BelongsToVariation|null $notNullColumnWithNoForeignKeyConstraint\n    |\n    | Option: false\n    | A not null column with no foreign key constraint will have a \"not nullable\" relationship.\n    |  * @property int $not_null_column_with_no_foreign_key_constraint\n    |  * @property-read BelongsToVariation $notNullColumnWithNoForeignKeyConstraint\n    |\n    */\n\n    'enforce_nullable_relationships' => true,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Run artisan commands after migrations to generate model helpers\n    |--------------------------------------------------------------------------\n    |\n    | The specified commands should run after migrations are finished running.\n    |\n    */\n    'post_migrate' => [\n        // 'ide-helper:models --nowrite',\n    ],\n\n];\n"
  },
  {
    "path": "config/javascript.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | View to Bind JavaScript Vars To\n    |--------------------------------------------------------------------------\n    |\n    | Set this value to the name of the view (or partial) that\n    | you want to prepend all JavaScript variables to.\n    | This can be a single view, or an array of views.\n    | Example: 'footer' or ['footer', 'bottom']\n    |\n    */\n    'bind_js_vars_to_this_view' => [\n        'layouts.scripts',\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | JavaScript Namespace\n    |--------------------------------------------------------------------------\n    |\n    | By default, we'll add variables to the global window object. However,\n    | it's recommended that you change this to some namespace - anything.\n    | That way, you can access vars, like \"SomeNamespace.someVariable.\"\n    |\n    */\n    'js_namespace' => 'Pterodactyl',\n];\n"
  },
  {
    "path": "config/logging.php",
    "content": "<?php\n\nuse Monolog\\Handler\\NullHandler;\nuse Monolog\\Handler\\StreamHandler;\nuse Monolog\\Handler\\SyslogUdpHandler;\nuse Monolog\\Processor\\PsrLogMessageProcessor;\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Default Log Channel\n    |--------------------------------------------------------------------------\n    |\n    | This option defines the default log channel that is utilized to write\n    | messages to your logs. The value provided here should match one of\n    | the channels present in the list of \"channels\" configured below.\n    |\n    */\n\n    'default' => env('LOG_CHANNEL', 'daily'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Deprecations Log Channel\n    |--------------------------------------------------------------------------\n    |\n    | This option controls the log channel that should be used to log warnings\n    | regarding deprecated PHP and library features. This allows you to get\n    | your application ready for upcoming major versions of dependencies.\n    |\n    */\n\n    'deprecations' => [\n        'channel' => env('LOG_DEPRECATIONS_CHANNEL', 'null'),\n        'trace' => env('LOG_DEPRECATIONS_TRACE', false),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Log Channels\n    |--------------------------------------------------------------------------\n    |\n    | Here you may configure the log channels for your application. Laravel\n    | utilizes the Monolog PHP logging library, which includes a variety\n    | of powerful log handlers and formatters that you're free to use.\n    |\n    | Available drivers: \"single\", \"daily\", \"slack\", \"syslog\",\n    |                    \"errorlog\", \"monolog\", \"custom\", \"stack\"\n    |\n    */\n\n    'channels' => [\n        'stack' => [\n            'driver' => 'stack',\n            'channels' => explode(',', env('LOG_STACK', 'single')),\n            'ignore_exceptions' => false,\n        ],\n\n        'single' => [\n            'driver' => 'single',\n            'path' => storage_path('logs/laravel.log'),\n            'level' => env('LOG_LEVEL', 'debug'),\n            'replace_placeholders' => true,\n        ],\n\n        'daily' => [\n            'driver' => 'daily',\n            'path' => storage_path('logs/laravel.log'),\n            'level' => env('LOG_LEVEL', 'debug'),\n            'days' => env('LOG_DAILY_DAYS', 7),\n            'replace_placeholders' => true,\n        ],\n\n        'slack' => [\n            'driver' => 'slack',\n            'url' => env('LOG_SLACK_WEBHOOK_URL'),\n            'username' => env('LOG_SLACK_USERNAME', 'Laravel Log'),\n            'emoji' => env('LOG_SLACK_EMOJI', ':boom:'),\n            'level' => env('LOG_LEVEL', 'critical'),\n            'replace_placeholders' => true,\n        ],\n\n        'papertrail' => [\n            'driver' => 'monolog',\n            'level' => env('LOG_LEVEL', 'debug'),\n            'handler' => env('LOG_PAPERTRAIL_HANDLER', SyslogUdpHandler::class),\n            'handler_with' => [\n                'host' => env('PAPERTRAIL_URL'),\n                'port' => env('PAPERTRAIL_PORT'),\n                'connectionString' => 'tls://' . env('PAPERTRAIL_URL') . ':' . env('PAPERTRAIL_PORT'),\n            ],\n            'processors' => [PsrLogMessageProcessor::class],\n        ],\n\n        'stderr' => [\n            'driver' => 'monolog',\n            'level' => env('LOG_LEVEL', 'debug'),\n            'handler' => StreamHandler::class,\n            'formatter' => env('LOG_STDERR_FORMATTER'),\n            'with' => [\n                'stream' => 'php://stderr',\n            ],\n            'processors' => [PsrLogMessageProcessor::class],\n        ],\n\n        'syslog' => [\n            'driver' => 'syslog',\n            'level' => env('LOG_LEVEL', 'debug'),\n            'facility' => env('LOG_SYSLOG_FACILITY', LOG_USER),\n            'replace_placeholders' => true,\n        ],\n\n        'errorlog' => [\n            'driver' => 'errorlog',\n            'level' => env('LOG_LEVEL', 'debug'),\n            'replace_placeholders' => true,\n        ],\n\n        'null' => [\n            'driver' => 'monolog',\n            'handler' => NullHandler::class,\n        ],\n\n        'emergency' => [\n            'path' => storage_path('logs/laravel.log'),\n        ],\n    ],\n];\n"
  },
  {
    "path": "config/logo.php",
    "content": "<?php\n/*\n|--------------------------------------------------------------------------\n| Application Logo\n|--------------------------------------------------------------------------\n|\n| As the name suggests, it is the logo setting of the site.\n|\n*/\n\nreturn [\n    /*\n     * title logo\n     */\n    'title' => env('LOGO_TITLE', ''),\n\n    /*\n     * favicon logo\n     */\n    'favicon' => env('LOGO_FAVICON', '/favicons/favicon.ico'),\n\n    /*\n     * login page logo\n     */\n    'auth' => env('LOGO_AUTH', ''),\n];\n"
  },
  {
    "path": "config/mail.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Default Mailer\n    |--------------------------------------------------------------------------\n    |\n    | This option controls the default mailer that is used to send any email\n    | messages sent by your application. Alternative mailers may be setup\n    | and used as needed; however, this mailer will be used by default.\n    |\n    */\n\n    'default' => env('MAIL_MAILER', env('MAIL_DRIVER', 'smtp')),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Mailer Configurations\n    |--------------------------------------------------------------------------\n    |\n    | Here you may configure all of the mailers used by your application plus\n    | their respective settings. Several examples have been configured for\n    | you and you are free to add your own as your application requires.\n    |\n    | Laravel supports a variety of mail \"transport\" drivers to be used while\n    | sending an e-mail. You will specify which one you are using for your\n    | mailers below. You are free to add additional mailers as required.\n    |\n    | Supported: \"smtp\", \"sendmail\", \"mailgun\", \"ses\", \"ses-v2\",\n    |            \"postmark\", \"log\", \"array\", \"failover\"\n    |\n    */\n\n    'mailers' => [\n        'smtp' => [\n            'transport' => 'smtp',\n            'host' => env('MAIL_HOST', '127.0.0.1'),\n            'port' => env('MAIL_PORT', 2525),\n            'encryption' => env('MAIL_ENCRYPTION', 'tls'),\n            'username' => env('MAIL_USERNAME'),\n            'password' => env('MAIL_PASSWORD'),\n            'timeout' => null,\n            'local_domain' => env('MAIL_EHLO_DOMAIN', env('SERVER_NAME')),\n        ],\n\n        'ses' => [\n            'transport' => 'ses',\n        ],\n\n        'mailgun' => [\n            'transport' => 'mailgun',\n        ],\n\n        'postmark' => [\n            'transport' => 'postmark',\n        ],\n\n        'sendmail' => [\n            'transport' => 'sendmail',\n            'path' => env('MAIL_SENDMAIL_PATH', '/usr/sbin/sendmail -bs -i'),\n        ],\n\n        'log' => [\n            'transport' => 'log',\n            'channel' => env('MAIL_LOG_CHANNEL'),\n        ],\n\n        'array' => [\n            'transport' => 'array',\n        ],\n\n        'failover' => [\n            'transport' => 'failover',\n            'mailers' => [\n                'smtp',\n                'log',\n            ],\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Global \"From\" Address\n    |--------------------------------------------------------------------------\n    |\n    | You may wish for all emails sent by your application to be sent from\n    | the same address. Here you may specify a name and address that is\n    | used globally for all emails that are sent by your application.\n    |\n    */\n\n    'from' => [\n        'address' => env('MAIL_FROM_ADDRESS', env('MAIL_FROM', 'hello@example.com')),\n        'name' => env('MAIL_FROM_NAME', 'Pterodactyl Panel'),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Markdown Mail Settings\n    |--------------------------------------------------------------------------\n    |\n    | If you are using Markdown based email rendering, you may configure your\n    | theme and component paths here, allowing you to customize the design\n    | of the emails. Or, you may simply stick with the Laravel defaults!\n    |\n    */\n\n    'markdown' => [\n        'theme' => 'default',\n\n        'paths' => [\n            resource_path('views/vendor/mail'),\n        ],\n    ],\n];\n"
  },
  {
    "path": "config/prologue/alerts.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Alert Levels\n    |--------------------------------------------------------------------------\n    |\n    | The default sort of alert levels which can be called as functions on the\n    | AlertsMessageBag class. This gives a convenient way to add certain type's\n    | of messages.\n    |\n    | For example:\n    |\n    |     Alerts::info($message);\n    |\n    */\n\n    'levels' => [\n        'info',\n        'warning',\n        'danger',\n        'success',\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session Key\n    |--------------------------------------------------------------------------\n    |\n    | The session key which is used to store flashed messages into the current\n    | session. This can be changed if it conflicts with another key.\n    |\n    */\n\n    'session_key' => 'alert_messages',\n];\n"
  },
  {
    "path": "config/pterodactyl.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Restricted Environment\n    |--------------------------------------------------------------------------\n    |\n    | Set this environment variable to true to enable a restricted configuration\n    | setup on the panel. When set to true, configurations stored in the\n    | database will not be applied.\n    */\n\n    'load_environment_only' => (bool) env('APP_ENVIRONMENT_ONLY', false),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Service Author\n    |--------------------------------------------------------------------------\n    |\n    | Each panel installation is assigned a unique UUID to identify the\n    | author of custom services, and make upgrades easier by identifying\n    | standard Pterodactyl shipped services.\n    */\n\n    'service' => [\n        'author' => env('APP_SERVICE_AUTHOR', 'unknown@unknown.com'),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Authentication\n    |--------------------------------------------------------------------------\n    |\n    | Should login success and failure events trigger an email to the user?\n    */\n\n    'auth' => [\n        '2fa_required' => env('APP_2FA_REQUIRED', 0),\n        '2fa' => [\n            'bytes' => 32,\n            'window' => env('APP_2FA_WINDOW', 4),\n            'verify_newer' => true,\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Pagination\n    |--------------------------------------------------------------------------\n    |\n    | Certain pagination result counts can be configured here and will take\n    | effect globally.\n    */\n\n    'paginate' => [\n        'frontend' => [\n            'servers' => env('APP_PAGINATE_FRONT_SERVERS', 15),\n        ],\n        'admin' => [\n            'servers' => env('APP_PAGINATE_ADMIN_SERVERS', 25),\n            'users' => env('APP_PAGINATE_ADMIN_USERS', 25),\n        ],\n        'api' => [\n            'nodes' => env('APP_PAGINATE_API_NODES', 25),\n            'servers' => env('APP_PAGINATE_API_SERVERS', 25),\n            'users' => env('APP_PAGINATE_API_USERS', 25),\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Guzzle Connections\n    |--------------------------------------------------------------------------\n    |\n    | Configure the timeout to be used for Guzzle connections here.\n    */\n\n    'guzzle' => [\n        'timeout' => env('GUZZLE_TIMEOUT', 15),\n        'connect_timeout' => env('GUZZLE_CONNECT_TIMEOUT', 5),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | CDN\n    |--------------------------------------------------------------------------\n    |\n    | Information for the panel to use when contacting the CDN to confirm\n    | if panel is up to date.\n    */\n\n    'cdn' => [\n        'cache_time' => 60,\n        'url' => 'https://api.pterodactyl.top/releases/latest.json',\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Client Features\n    |--------------------------------------------------------------------------\n    |\n    | Allow clients to create their own databases.\n    */\n\n    'client_features' => [\n        'databases' => [\n            'enabled' => env('PTERODACTYL_CLIENT_DATABASES_ENABLED', true),\n            'allow_random' => env('PTERODACTYL_CLIENT_DATABASES_ALLOW_RANDOM', true),\n        ],\n\n        'schedules' => [\n            // The total number of tasks that can exist for any given schedule at once.\n            'per_schedule_task_limit' => env('PTERODACTYL_PER_SCHEDULE_TASK_LIMIT', 10),\n        ],\n\n        'allocations' => [\n            'enabled' => env('PTERODACTYL_CLIENT_ALLOCATIONS_ENABLED', false),\n            'range_start' => env('PTERODACTYL_CLIENT_ALLOCATIONS_RANGE_START'),\n            'range_end' => env('PTERODACTYL_CLIENT_ALLOCATIONS_RANGE_END'),\n            'consecutive_enabled' => env('PTERODACTYL_CLIENT_ALLOCATIONS_CONSECUTIVE_ENABLED', false),\n            'consecutive_limit' => env('PTERODACTYL_CLIENT_ALLOCATIONS_CONSECUTIVE_LIMIT', 3),\n        ],\n\n        'egg_change' => [\n            // Allowed values: disabled, egg_only, nest_only, both\n            'mode' => env('PTERODACTYL_CLIENT_EGG_CHANGE_MODE', 'disabled'),\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | File Editor\n    |--------------------------------------------------------------------------\n    |\n    | This array includes the MIME filetypes that can be edited via the web.\n    */\n\n    'files' => [\n        'max_edit_size' => env('PTERODACTYL_FILES_MAX_EDIT_SIZE', 1024 * 1024 * 4),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Dynamic Environment Variables\n    |--------------------------------------------------------------------------\n    |\n    | Place dynamic environment variables here that should be auto-appended\n    | to server environment fields when the server is created or updated.\n    |\n    | Items should be in 'key' => 'value' format, where key is the environment\n    | variable name, and value is the server-object key. For example:\n    |\n    | 'P_SERVER_CREATED_AT' => 'created_at'\n    */\n\n    'environment_variables' => [\n        'P_SERVER_ALLOCATION_LIMIT' => 'allocation_limit',\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Asset Verification\n    |--------------------------------------------------------------------------\n    |\n    | This section controls the output format for JS & CSS assets.\n    */\n\n    'assets' => [\n        'use_hash' => env('PTERODACTYL_USE_ASSET_HASH', false),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Email Notification Settings\n    |--------------------------------------------------------------------------\n    |\n    | This section controls what notifications are sent to users.\n    */\n\n    'email' => [\n        // Should an email be sent to a server owner once their server has completed it's first install process?\n        'send_install_notification' => env('PTERODACTYL_SEND_INSTALL_NOTIFICATION', true),\n        // Should an email be sent to a server owner whenever their server is reinstalled?\n        'send_reinstall_notification' => env('PTERODACTYL_SEND_REINSTALL_NOTIFICATION', true),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Telemetry Settings\n    |--------------------------------------------------------------------------\n    |\n    | This section controls the telemetry sent by Pterodactyl.\n    | 按理说，此功能应默认打开，但由于中国国内访问外网困难，所以我们将此设置设为默认关闭\n    */\n\n    'telemetry' => [\n        'enabled' => env('PTERODACTYL_TELEMETRY_ENABLED', false),\n    ],\n\n    'features' => [\n        'new_server_identifiers' => (bool) env('PTERODACTYL_USE_SERVER_IDENTIFIERS', false),\n    ],\n];\n"
  },
  {
    "path": "config/queue.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Default Queue Connection Name\n    |--------------------------------------------------------------------------\n    |\n    | Laravel's queue supports a variety of backends via a single, unified\n    | API, giving you convenient access to each backend using identical\n    | syntax for each. The default queue connection is defined below.\n    |\n    */\n\n    'default' => env('QUEUE_CONNECTION', env('QUEUE_DRIVER', 'redis')),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Queue Connections\n    |--------------------------------------------------------------------------\n    |\n    | Here you may configure the connection options for every queue backend\n    | used by your application. An example configuration is provided for\n    | each backend supported by Laravel. You're also free to add more.\n    |\n    | Drivers: \"sync\", \"database\", \"beanstalkd\", \"sqs\", \"redis\", \"null\"\n    |\n    */\n\n    'connections' => [\n        'sync' => [\n            'driver' => 'sync',\n        ],\n\n        'database' => [\n            'driver' => 'database',\n            'connection' => env('DB_QUEUE_CONNECTION'),\n            'table' => env('DB_QUEUE_TABLE', 'jobs'),\n            'queue' => env('DB_QUEUE', 'standard'),\n            'retry_after' => (int) env('DB_QUEUE_RETRY_AFTER', 90),\n            'after_commit' => false,\n        ],\n\n        'beanstalkd' => [\n            'driver' => 'beanstalkd',\n            'host' => env('BEANSTALKD_QUEUE_HOST', 'localhost'),\n            'queue' => env('BEANSTALKD_QUEUE', 'default'),\n            'retry_after' => (int) env('BEANSTALKD_QUEUE_RETRY_AFTER', 90),\n            'block_for' => 0,\n            'after_commit' => false,\n        ],\n\n        'sqs' => [\n            'driver' => 'sqs',\n            'key' => env('AWS_ACCESS_KEY_ID'),\n            'secret' => env('AWS_SECRET_ACCESS_KEY'),\n            'prefix' => env('SQS_PREFIX', 'https://sqs.us-east-1.amazonaws.com/your-account-id'),\n            'queue' => env('SQS_QUEUE', 'default'),\n            'suffix' => env('SQS_SUFFIX'),\n            'region' => env('AWS_DEFAULT_REGION', 'us-east-1'),\n            'after_commit' => false,\n        ],\n\n        'redis' => [\n            'driver' => 'redis',\n            'connection' => env('REDIS_QUEUE_CONNECTION', 'default'),\n            'queue' => env('REDIS_QUEUE', env('QUEUE_STANDARD', 'standard')),\n            'retry_after' => (int) env('REDIS_QUEUE_RETRY_AFTER', 90),\n            'block_for' => null,\n            'after_commit' => false,\n        ],\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Failed Queue Jobs\n    |--------------------------------------------------------------------------\n    |\n    | These options configure the behavior of failed queue job logging so you\n    | can control how and where failed jobs are stored. Laravel ships with\n    | support for storing failed jobs in a simple file or in a database.\n    |\n    | Supported drivers: \"database-uuids\", \"dynamodb\", \"file\", \"null\"\n    |\n    */\n\n    'failed' => [\n        'driver' => env('QUEUE_FAILED_DRIVER', 'database-uuids'),\n        'database' => env('DB_CONNECTION', 'mysql'),\n        'table' => 'failed_jobs',\n    ],\n];\n"
  },
  {
    "path": "config/recaptcha.php",
    "content": "<?php\n\nreturn [\n    /*\n     * Enable or disable captchas\n     */\n    'enabled' => env('RECAPTCHA_ENABLED', true),\n\n    /*\n     * API endpoint for recaptcha checks. You should not edit this.\n     */\n    'domain' => env('RECAPTCHA_DOMAIN', 'https://www.recaptcha.net/recaptcha/api/siteverify'),\n\n    /*\n     * Use a custom secret key, we use our public one by default\n     */\n    'secret_key' => env('RECAPTCHA_SECRET_KEY', '6LcJcjwUAAAAALOcDJqAEYKTDhwELCkzUkNDQ0J5'),\n    '_shipped_secret_key' => '6LcJcjwUAAAAALOcDJqAEYKTDhwELCkzUkNDQ0J5',\n\n    /*\n     * Use a custom website key, we use our public one by default\n     */\n    'website_key' => env('RECAPTCHA_WEBSITE_KEY', '6LcJcjwUAAAAAO_Xqjrtj9wWufUpYRnK6BW8lnfn'),\n    '_shipped_website_key' => '6LcJcjwUAAAAAO_Xqjrtj9wWufUpYRnK6BW8lnfn',\n\n    /*\n     * Domain verification is enabled by default and compares the domain used when solving the captcha\n     * as public keys can't have domain verification on google's side enabled (obviously).\n     */\n    'verify_domain' => true,\n];\n"
  },
  {
    "path": "config/sanctum.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Stateful Domains\n    |--------------------------------------------------------------------------\n    |\n    | Requests from the following domains / hosts will receive stateful API\n    | authentication cookies. Typically, these should include your local\n    | and production domains which access your API via a frontend SPA.\n    |\n    */\n\n    'stateful' => explode(',', env('SANCTUM_STATEFUL_DOMAINS', sprintf(\n        '%s%s',\n        'localhost,localhost:3000,127.0.0.1,127.0.0.1:8000,::1',\n        Laravel\\Sanctum\\Sanctum::currentApplicationUrlWithPort()\n    ))),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Sanctum Guards\n    |--------------------------------------------------------------------------\n    |\n    | This array contains the authentication guards that will be checked when\n    | Sanctum is trying to authenticate a request. If none of these guards\n    | are able to authenticate the request, Sanctum will use the bearer\n    | token that's present on an incoming request for authentication.\n    |\n    */\n\n    'guard' => ['web'],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Expiration Minutes\n    |--------------------------------------------------------------------------\n    |\n    | This value controls the number of minutes until an issued token will be\n    | considered expired. If this value is null, personal access tokens do\n    | not expire. This won't tweak the lifetime of first-party sessions.\n    |\n    */\n\n    'expiration' => null,\n\n    /*\n    |--------------------------------------------------------------------------\n    | Sanctum Middleware\n    |--------------------------------------------------------------------------\n    |\n    | When authenticating your first-party SPA with Sanctum you may need to\n    | customize some of the middleware Sanctum uses while processing the\n    | request. You may change the middleware listed below as required.\n    |\n    */\n\n    'middleware' => [\n        'authenticate_session' => Laravel\\Sanctum\\Http\\Middleware\\AuthenticateSession::class,\n        'encrypt_cookies' => Pterodactyl\\Http\\Middleware\\EncryptCookies::class,\n        'verify_csrf_token' => Pterodactyl\\Http\\Middleware\\VerifyCsrfToken::class,\n    ],\n];\n"
  },
  {
    "path": "config/services.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Third Party Services\n    |--------------------------------------------------------------------------\n    |\n    | This file is for storing the credentials for third party services such\n    | as Mailgun, Postmark, AWS and more. This file provides the de facto\n    | location for this type of information, allowing packages to have\n    | a conventional file to locate the various service credentials.\n    |\n    */\n\n    'postmark' => [\n        'token' => env('POSTMARK_TOKEN'),\n    ],\n\n    'ses' => [\n        'key' => env('AWS_ACCESS_KEY_ID'),\n        'secret' => env('AWS_SECRET_ACCESS_KEY'),\n        'region' => env('AWS_DEFAULT_REGION', 'us-east-1'),\n    ],\n\n    'resend' => [\n        'key' => env('RESEND_KEY'),\n    ],\n\n    'slack' => [\n        'notifications' => [\n            'bot_user_oauth_token' => env('SLACK_BOT_USER_OAUTH_TOKEN'),\n            'channel' => env('SLACK_BOT_USER_DEFAULT_CHANNEL'),\n        ],\n    ],\n];\n"
  },
  {
    "path": "config/session.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Str;\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Default Session Driver\n    |--------------------------------------------------------------------------\n    |\n    | This option determines the default session driver that is utilized for\n    | incoming requests. Laravel supports a variety of storage options to\n    | persist session data. Database storage is a great default choice.\n    |\n    | Supported: \"file\", \"cookie\", \"database\", \"apc\",\n    |            \"memcached\", \"redis\", \"dynamodb\", \"array\"\n    |\n    */\n\n    'driver' => env('SESSION_DRIVER', 'redis'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session Lifetime\n    |--------------------------------------------------------------------------\n    |\n    | Here you may specify the number of minutes that you wish the session\n    | to be allowed to remain idle before it expires. If you want them\n    | to expire immediately when the browser is closed then you may\n    | indicate that via the expire_on_close configuration option.\n    |\n    */\n\n    'lifetime' => env('SESSION_LIFETIME', 720),\n\n    'expire_on_close' => env('SESSION_EXPIRE_ON_CLOSE', false),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session Encryption\n    |--------------------------------------------------------------------------\n    |\n    | This option allows you to easily specify that all of your session data\n    | should be encrypted before it's stored. All encryption is performed\n    | automatically by Laravel and you may use the session like normal.\n    |\n    */\n\n    'encrypt' => env('SESSION_ENCRYPT', true),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session File Location\n    |--------------------------------------------------------------------------\n    |\n    | When utilizing the \"file\" session driver, the session files are placed\n    | on disk. The default storage location is defined here; however, you\n    | are free to provide another location where they should be stored.\n    |\n    */\n\n    'files' => storage_path('framework/sessions'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session Database Connection\n    |--------------------------------------------------------------------------\n    |\n    | When using the \"database\" or \"redis\" session drivers, you may specify a\n    | connection that should be used to manage these sessions. This should\n    | correspond to a connection in your database configuration options.\n    |\n    */\n\n    'connection' => env('SESSION_CONNECTION'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session Database Table\n    |--------------------------------------------------------------------------\n    |\n    | When using the \"database\" session driver, you may specify the table to\n    | be used to store sessions. Of course, a sensible default is defined\n    | for you; however, you're welcome to change this to another table.\n    |\n    */\n\n    'table' => env('SESSION_TABLE', 'sessions'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session Cache Store\n    |--------------------------------------------------------------------------\n    |\n    | When using one of the framework's cache driven session backends, you may\n    | define the cache store which should be used to store the session data\n    | between requests. This must match one of your defined cache stores.\n    |\n    | Affects: \"apc\", \"dynamodb\", \"memcached\", \"redis\"\n    |\n    */\n\n    'store' => env('SESSION_STORE'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session Sweeping Lottery\n    |--------------------------------------------------------------------------\n    |\n    | Some session drivers must manually sweep their storage location to get\n    | rid of old sessions from storage. Here are the chances that it will\n    | happen on a given request. By default, the odds are 2 out of 100.\n    |\n    */\n\n    'lottery' => [2, 100],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session Cookie Name\n    |--------------------------------------------------------------------------\n    |\n    | Here you may change the name of the session cookie that is created by\n    | the framework. Typically, you should not need to change this value\n    | since doing so does not grant a meaningful security improvement.\n    |\n    */\n\n    'cookie' => env(\n        'SESSION_COOKIE',\n        Str::slug(env('APP_NAME', 'pterodactyl'), '_') . '_session'\n    ),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session Cookie Path\n    |--------------------------------------------------------------------------\n    |\n    | The session cookie path determines the path for which the cookie will\n    | be regarded as available. Typically, this will be the root path of\n    | your application, but you're free to change this when necessary.\n    |\n    */\n\n    'path' => env('SESSION_PATH', '/'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Session Cookie Domain\n    |--------------------------------------------------------------------------\n    |\n    | This value determines the domain and subdomains the session cookie is\n    | available to. By default, the cookie will be available to the root\n    | domain and all subdomains. Typically, this shouldn't be changed.\n    |\n    */\n\n    'domain' => env('SESSION_DOMAIN'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | HTTPS Only Cookies\n    |--------------------------------------------------------------------------\n    |\n    | By setting this option to true, session cookies will only be sent back\n    | to the server if the browser has a HTTPS connection. This will keep\n    | the cookie from being sent to you when it can't be done securely.\n    |\n    */\n\n    'secure' => env('SESSION_SECURE_COOKIE'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | HTTP Access Only\n    |--------------------------------------------------------------------------\n    |\n    | Setting this value to true will prevent JavaScript from accessing the\n    | value of the cookie and the cookie will only be accessible through\n    | the HTTP protocol. It's unlikely you should disable this option.\n    |\n    */\n\n    'http_only' => env('SESSION_HTTP_ONLY', true),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Same-Site Cookies\n    |--------------------------------------------------------------------------\n    |\n    | This option determines how your cookies behave when cross-site requests\n    | take place, and can be used to mitigate CSRF attacks. By default, we\n    | will set this value to \"lax\" to permit secure cross-site requests.\n    |\n    | See: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Set-Cookie#samesitesamesite-value\n    |\n    | Supported: \"lax\", \"strict\", \"none\", null\n    |\n    */\n\n    'same_site' => env('SESSION_SAME_SITE', 'lax'),\n\n    /*\n    |--------------------------------------------------------------------------\n    | Partitioned Cookies\n    |--------------------------------------------------------------------------\n    |\n    | Setting this value to true will tie the cookie to the top-level site for\n    | a cross-site context. Partitioned cookies are accepted by the browser\n    | when flagged \"secure\" and the Same-Site attribute is set to \"none\".\n    |\n    */\n\n    'partitioned' => env('SESSION_PARTITIONED_COOKIE', false),\n];\n"
  },
  {
    "path": "config/trustedproxy.php",
    "content": "<?php\n\nreturn [\n    /*\n     * Set trusted proxy IP addresses.\n     *\n     * Both IPv4 and IPv6 addresses are\n     * supported, along with CIDR notation.\n     *\n     * The \"*\" character is syntactic sugar\n     * within TrustedProxy to trust any proxy\n     * that connects directly to your server,\n     * a requirement when you cannot know the address\n     * of your proxy (e.g. if using Rackspace balancers).\n     *\n     * The \"**\" character is syntactic sugar within\n     * TrustedProxy to trust not just any proxy that\n     * connects directly to your server, but also\n     * proxies that connect to those proxies, and all\n     * the way back until you reach the original source\n     * IP. It will mean that $request->getClientIp()\n     * always gets the originating client IP, no matter\n     * how many proxies that client's request has\n     * subsequently passed through.\n     */\n    'proxies' => in_array(env('TRUSTED_PROXIES', []), ['*', '**']) ?\n        env('TRUSTED_PROXIES') : explode(',', env('TRUSTED_PROXIES') ?? ''),\n];\n"
  },
  {
    "path": "config/view.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | View Storage Paths\n    |--------------------------------------------------------------------------\n    |\n    | Most templating systems load templates from disk. Here you may specify\n    | an array of paths that should be checked for your views. Of course\n    | the usual Laravel view path has already been registered for you.\n    |\n    */\n\n    'paths' => [\n        resource_path('views'),\n    ],\n\n    /*\n    |--------------------------------------------------------------------------\n    | Compiled View Path\n    |--------------------------------------------------------------------------\n    |\n    | This option determines where all the compiled Blade templates will be\n    | stored for your application. Typically, this is within the storage\n    | directory. However, as usual, you are free to change this value.\n    |\n    */\n\n    'compiled' => env(\n        'VIEW_COMPILED_PATH',\n        realpath(storage_path('framework/views'))\n    ),\n];\n"
  },
  {
    "path": "database/.gitignore",
    "content": "*.sqlite\n"
  },
  {
    "path": "database/Factories/AllocationFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Allocation;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass AllocationFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = Allocation::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'ip' => $this->faker->unique()->ipv4,\n            'port' => $this->faker->unique()->numberBetween(1024, 65535),\n        ];\n    }\n\n    /**\n     * Attaches the allocation to a specific server model.\n     */\n    public function forServer(Server $server): self\n    {\n        return $this->for($server)->for($server->node);\n    }\n}\n"
  },
  {
    "path": "database/Factories/ApiKeyFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Carbon\\Carbon;\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\ApiKey;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass ApiKeyFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = ApiKey::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        static $token;\n\n        return [\n            'key_type' => ApiKey::TYPE_APPLICATION,\n            'identifier' => ApiKey::generateTokenIdentifier(ApiKey::TYPE_APPLICATION),\n            'token' => $token ?: $token = encrypt(Str::random(ApiKey::KEY_LENGTH)),\n            'allowed_ips' => null,\n            'memo' => 'Test Function Key',\n            'created_at' => Carbon::now(),\n            'updated_at' => Carbon::now(),\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/BackupFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Carbon\\CarbonImmutable;\nuse Pterodactyl\\Models\\Backup;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass BackupFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = Backup::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'uuid' => Uuid::uuid4()->toString(),\n            'name' => $this->faker->sentence,\n            'disk' => Backup::ADAPTER_WINGS,\n            'is_successful' => true,\n            'created_at' => CarbonImmutable::now(),\n            'completed_at' => CarbonImmutable::now(),\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/DatabaseFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Carbon\\Carbon;\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\Database;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass DatabaseFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = Database::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        static $password;\n\n        return [\n            'database' => Str::random(10),\n            'username' => Str::random(10),\n            'remote' => '%',\n            'password' => $password ?: encrypt('test123'),\n            'created_at' => Carbon::now(),\n            'updated_at' => Carbon::now(),\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/DatabaseHostFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Illuminate\\Support\\Facades\\Crypt;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass DatabaseHostFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = DatabaseHost::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'name' => $this->faker->colorName,\n            'host' => $this->faker->unique()->ipv4,\n            'port' => 3306,\n            'username' => $this->faker->colorName,\n            'password' => Crypt::encrypt($this->faker->word),\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/EggFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Pterodactyl\\Models\\Egg;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass EggFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = Egg::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'uuid' => Uuid::uuid4()->toString(),\n            'name' => $this->faker->name,\n            'description' => implode(' ', $this->faker->sentences()),\n            'startup' => 'java -jar test.jar',\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/EggVariableFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\EggVariable;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass EggVariableFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = EggVariable::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'name' => $this->faker->unique()->firstName,\n            'description' => $this->faker->sentence(),\n            'env_variable' => Str::upper(Str::replaceArray(' ', ['_'], $this->faker->words(2, true))),\n            'default_value' => $this->faker->colorName,\n            'user_viewable' => 0,\n            'user_editable' => 0,\n            'rules' => 'required|string',\n        ];\n    }\n\n    /**\n     * Indicate that the egg variable is viewable.\n     */\n    public function viewable(): static\n    {\n        return $this->state(function (array $attributes) {\n            return [\n                'user_viewable' => 1,\n            ];\n        });\n    }\n\n    /**\n     * Indicate that the egg variable is editable.\n     */\n    public function editable(): static\n    {\n        return $this->state(function (array $attributes) {\n            return [\n                'user_editable' => 1,\n            ];\n        });\n    }\n}\n"
  },
  {
    "path": "database/Factories/LocationFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\n/**\n * @extends \\Illuminate\\Database\\Eloquent\\Factories\\Factory<\\Pterodactyl\\Models\\Location>\n */\nclass LocationFactory extends Factory\n{\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'short' => Str::random(8),\n            'long' => Str::random(32),\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/NestFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Pterodactyl\\Models\\Nest;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass NestFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = Nest::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'uuid' => Uuid::uuid4()->toString(),\n            'author' => 'testauthor@example.com',\n            'name' => $this->faker->word,\n            'description' => null,\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/NodeFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Support\\Facades\\Crypt;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass NodeFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = Node::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'uuid' => Uuid::uuid4()->toString(),\n            'public' => true,\n            'name' => 'FactoryNode_' . Str::random(10),\n            'fqdn' => $this->faker->unique()->ipv4,\n            'scheme' => 'http',\n            'behind_proxy' => false,\n            'memory' => 1024,\n            'memory_overallocate' => 0,\n            'disk' => 10240,\n            'disk_overallocate' => 0,\n            'upload_size' => 100,\n            'daemon_token_id' => Str::random(Node::DAEMON_TOKEN_ID_LENGTH),\n            'daemon_token' => Crypt::encrypt(Str::random(Node::DAEMON_TOKEN_LENGTH)),\n            'daemonListen' => 8080,\n            'daemonSFTP' => 2022,\n            'daemonBase' => '/var/lib/pterodactyl/volumes',\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/ScheduleFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Pterodactyl\\Models\\Schedule;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass ScheduleFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = Schedule::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'name' => $this->faker->firstName(),\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/ServerFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Carbon\\Carbon;\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass ServerFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = Server::class;\n\n    /**\n     * Define the model's default state.\n     *\n     * @return array\n     */\n    public function definition()\n    {\n        return [\n            'uuid' => Uuid::uuid4()->toString(),\n            'uuidShort' => Str::lower(Str::random(8)),\n            'name' => $this->faker->firstName,\n            'description' => implode(' ', $this->faker->sentences()),\n            'skip_scripts' => 0,\n            'status' => null,\n            'memory' => 512,\n            'swap' => 0,\n            'disk' => 512,\n            'io' => 500,\n            'cpu' => 0,\n            'threads' => null,\n            'oom_disabled' => 0,\n            'startup' => '/bin/bash echo \"hello world\"',\n            'image' => 'foo/bar:latest',\n            'allocation_limit' => null,\n            'database_limit' => null,\n            'backup_limit' => 0,\n            'created_at' => Carbon::now(),\n            'updated_at' => Carbon::now(),\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/ServerTransferFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Pterodactyl\\Models\\ServerTransfer;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass ServerTransferFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = ServerTransfer::class;\n\n    /**\n     * Define the model's default state.\n     *\n     * @return array\n     */\n    public function definition()\n    {\n        return [\n            'old_additional_allocations' => [],\n            'new_additional_allocations' => [],\n            'successful' => null,\n            'archived' => false,\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/SubuserFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass SubuserFactory extends Factory\n{\n    /**\n     * The name of the factory's corresponding model.\n     *\n     * @var string\n     */\n    protected $model = Subuser::class;\n\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'permissions' => [\n                Permission::ACTION_WEBSOCKET_CONNECT,\n            ],\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/TaskFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass TaskFactory extends Factory\n{\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        return [\n            'sequence_id' => $this->faker->numberBetween(1, 10),\n            'action' => 'command',\n            'payload' => 'test command',\n            'time_offset' => 120,\n            'is_queued' => false,\n        ];\n    }\n}\n"
  },
  {
    "path": "database/Factories/UserFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse Carbon\\Carbon;\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\n/**\n * @extends \\Illuminate\\Database\\Eloquent\\Factories\\Factory<\\Pterodactyl\\Models\\User>\n */\nclass UserFactory extends Factory\n{\n    /**\n     * Define the model's default state.\n     */\n    public function definition(): array\n    {\n        static $password;\n\n        return [\n            'external_id' => null,\n            'uuid' => Uuid::uuid4()->toString(),\n            'username' => $this->faker->userName . '_' . Str::random(10),\n            'email' => Str::random(32) . '@example.com',\n            'name_first' => $this->faker->firstName,\n            'name_last' => $this->faker->lastName,\n            'password' => $password ?: $password = bcrypt('password'),\n            'language' => 'zh',\n            'root_admin' => false,\n            'use_totp' => false,\n            'created_at' => Carbon::now(),\n            'updated_at' => Carbon::now(),\n        ];\n    }\n\n    /**\n     * Indicate that the user is an admin.\n     */\n    public function admin(): static\n    {\n        return $this->state(['root_admin' => true]);\n    }\n}\n"
  },
  {
    "path": "database/Factories/UserSSHKeyFactory.php",
    "content": "<?php\n\nnamespace Database\\Factories;\n\nuse phpseclib3\\Crypt\\PublicKeyLoader;\nuse Illuminate\\Database\\Eloquent\\Factories\\Factory;\n\nclass UserSSHKeyFactory extends Factory\n{\n    /**\n     * Some fake public keys generated for test purposes.\n     *\n     * @var string[]\n     */\n    protected static array $keys = [\n        'dsa' => 'ssh-dss AAAAB3NzaC1kc3MAAACBAPfiWwEFvBOafdUmHDPjXsUttt+65FHSZSCVVeEFOTaL7Y3d0CJyrtck8KS1vmXHSb8QFBY2B1yVSb/reaQvNreWZN3KDYfLbF57/zimBn+IrHrJR+ZglhOxDRHoGPWK7q9jYIrOLwoOjkNKXxz1eOHKUgufFfSNtIRLycEXczLrAAAAFQC6LnBErezotG52jN4JostfC/TfEwAAAIACuTxRzYFDXHAxFICeqqY9w+y+v2yQfdeQ1BgCq2GMagUYfOdqnjizTO9M614r/nXZK1SV10TqhUcQtkJzDQIUtBqzBF5cIC/1cIFKzXi5rNHs8Y4bz/PBD+EbQJdiy+1so1oi790r710bqnkzTravAOJ5rGyfuQRLt+f+kuS9NAAAAIEA7tjGtJuXGUtPIXfnrMYS1iOWryO4irqnvaWfel002/DaGaNjRghNe/cUBYlAsjPhGJ1F7BQlLAY1koliTY6l0svs7ZPBM5QOumrr8OaNXGGVIq/RkkxuZHmRoUL2qH3DGYaktPUn4vFPliiAmGWOHAEu1K6B4g4vG/SKgMRpIvc=',\n        'rsa_2048' => 'ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC4VVsHFO5MxvCtAPyoKGANWyuwZ4fvllvFog5RJbfpDpw8etDFVGEXl+uRR8p79g9oV7MscoFo6HiWrJc4/4vlP665msjosILdIcbnuzMhvXnKisaGh9zflkpyR3KhUxoHxqYp2q8XtffjKKAHz1a8o7OUG6fwaKIqu+d0PoICZQ==',\n        'rsa_4096' => 'ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAACAQCo/YLm2SPSlOIG7AagBSmEe5c0b2PLPzUGFp3gARhD6n6ydBS40TlWzeg2qV95lh6fWBd8LsNgPOFmmuKuNZdBjAGeTY4gxKfHY1vK5/zOI4jPPqAMcCMNfd82aM97kx6dO8Hw1R79OyVpOZylpXLHayVPGHUK37Tpih4W7TeVSMrOqQF9F72lzhwgEtkdjm4gLBL6RpdNXrdnjIaNVnuade0Sb3w384vecZPe+S/997WirOMNy2JU4NdMHEnSjd1/i463RpN96AsXFAu1zl9nrXVhA7DVfSHoigXAqbs/xav8PRpLgAKjYpPohxQ9Nu6tP5jRUhfWdYwNFFp/aWloD/0JdP9LqcBBc9sO9TLkz3fBiUf11VM/QT1UhO84G+ahMxVn95jA472VPUe8uKff69lzbvSavEE6qcQX2TzVKOSi1E26Fzc6IZ/tHEuGEbGFxTsiQ1GysVZ0wr1p6ftd1SVqH5F/oaEK7UO8+xn/syEqaPf6A0eJWRNc0+lHA1sIRjmo9MOBvbkKExkx5JLHgGG81DYDFdZUuHY1BgSxJJcmNWV5BKRm350EbgRngoYI5tB3tCiZVW1PI8qyff9mBae11LY5GPlUeDnPrMvSdCKMIWrg7nC8SbndBCO3Fx4z7G2dTQy4ZmY7Ae9jR4pyg7tTOI3qgl8Z462GZi/jzw==',\n        'ed25519' => 'ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIOaXIq09NH4a93EVdrvHYiZ67Wj+GBEBQ9ou4W0qSYm2',\n    ];\n\n    /**\n     * Returns a fake public key for use on the system.\n     *\n     * @return array\n     */\n    public function definition()\n    {\n        $key = PublicKeyLoader::loadPublicKey(static::$keys['ed25519']);\n\n        return [\n            'name' => $this->faker->name(),\n            'public_key' => $key->toString('PKCS8'),\n            'fingerprint' => $key->getFingerprint('sha256'),\n        ];\n    }\n\n    /**\n     * Returns a DSA public key.\n     */\n    public function dsa(): self\n    {\n        $key = PublicKeyLoader::loadPublicKey(static::$keys['dsa']);\n\n        return $this->state([\n            'public_key' => $key->toString('PKCS8'),\n            'fingerprint' => $key->getFingerprint('sha256'),\n        ]);\n    }\n\n    /**\n     * Returns an RSA public key, if \"weak\" is specified a 1024-bit RSA key is returned\n     * which should fail validation when being stored.\n     */\n    public function rsa(bool $weak = false): self\n    {\n        $key = PublicKeyLoader::loadPublicKey(static::$keys[$weak ? 'rsa_2048' : 'rsa_4096']);\n\n        return $this->state([\n            'public_key' => $key->toString('PKCS8'),\n            'fingerprint' => $key->getFingerprint('sha256'),\n        ]);\n    }\n}\n"
  },
  {
    "path": "database/Seeders/.gitkeep",
    "content": ""
  },
  {
    "path": "database/Seeders/DatabaseSeeder.php",
    "content": "<?php\n\nnamespace Database\\Seeders;\n\nuse Illuminate\\Database\\Seeder;\n\nclass DatabaseSeeder extends Seeder\n{\n    /**\n     * Run the database seeds.\n     */\n    public function run()\n    {\n        $this->call(NestSeeder::class);\n        $this->call(EggSeeder::class);\n    }\n}\n"
  },
  {
    "path": "database/Seeders/EggSeeder.php",
    "content": "<?php\n\nnamespace Database\\Seeders;\n\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\Nest;\nuse Illuminate\\Database\\Seeder;\nuse Illuminate\\Http\\UploadedFile;\nuse Pterodactyl\\Services\\Eggs\\Sharing\\EggImporterService;\nuse Pterodactyl\\Services\\Eggs\\Sharing\\EggUpdateImporterService;\n\nclass EggSeeder extends Seeder\n{\n    protected EggImporterService $importerService;\n\n    protected EggUpdateImporterService $updateImporterService;\n\n    /**\n     * @var string[]\n     */\n    public static array $import = [\n        'Minecraft',\n        'Source Engine',\n        'Voice Servers',\n        'Rust',\n    ];\n\n    /**\n     * EggSeeder constructor.\n     */\n    public function __construct(\n        EggImporterService $importerService,\n        EggUpdateImporterService $updateImporterService,\n    ) {\n        $this->importerService = $importerService;\n        $this->updateImporterService = $updateImporterService;\n    }\n\n    /**\n     * Run the egg seeder.\n     */\n    public function run()\n    {\n        foreach (static::$import as $nest) {\n            /* @noinspection PhpParamsInspection */\n            $this->parseEggFiles(\n                Nest::query()->where('author', 'support@pterodactyl.io')->where('name', $nest)->firstOrFail()\n            );\n        }\n    }\n\n    /**\n     * Loop through the list of egg files and import them.\n     */\n    protected function parseEggFiles(Nest $nest)\n    {\n        $files = new \\DirectoryIterator(database_path('Seeders/eggs/' . kebab_case($nest->name)));\n\n        $this->command->alert('更新预设组的预设: ' . $nest->name);\n        /** @var \\DirectoryIterator $file */\n        foreach ($files as $file) {\n            if (!$file->isFile() || !$file->isReadable()) {\n                continue;\n            }\n\n            $decoded = json_decode(file_get_contents($file->getRealPath()), true, 512, JSON_THROW_ON_ERROR);\n            $file = new UploadedFile($file->getPathname(), $file->getFilename(), 'application/json');\n\n            $egg = $nest->eggs()\n                ->where('author', $decoded['author'])\n                ->where('name', $decoded['name'])\n                ->first();\n\n            if ($egg instanceof Egg) {\n                $this->updateImporterService->handle($egg, $file);\n                $this->command->info('已更新 ' . $decoded['name']);\n            } else {\n                $this->importerService->handle($file, $nest->id);\n                $this->command->comment('已创建 ' . $decoded['name']);\n            }\n        }\n\n        $this->command->line('');\n    }\n}\n"
  },
  {
    "path": "database/Seeders/NestSeeder.php",
    "content": "<?php\n\nnamespace Database\\Seeders;\n\nuse Illuminate\\Database\\Seeder;\nuse Pterodactyl\\Services\\Nests\\NestCreationService;\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\n\nclass NestSeeder extends Seeder\n{\n    /**\n     * @var NestCreationService\n     */\n    private $creationService;\n\n    /**\n     * @var NestRepositoryInterface\n     */\n    private $repository;\n\n    /**\n     * NestSeeder constructor.\n     */\n    public function __construct(\n        NestCreationService $creationService,\n        NestRepositoryInterface $repository,\n    ) {\n        $this->creationService = $creationService;\n        $this->repository = $repository;\n    }\n\n    /**\n     * Run the seeder to add missing nests to the Panel.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    public function run()\n    {\n        $items = $this->repository->findWhere([\n            'author' => 'support@pterodactyl.io',\n        ])->keyBy('name')->toArray();\n\n        $this->createMinecraftNest(array_get($items, 'Minecraft'));\n        $this->createSourceEngineNest(array_get($items, 'Source Engine'));\n        $this->createVoiceServersNest(array_get($items, 'Voice Servers'));\n        $this->createRustNest(array_get($items, 'Rust'));\n    }\n\n    /**\n     * Create the Minecraft nest to be used later on.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    private function createMinecraftNest(?array $nest = null)\n    {\n        if (is_null($nest)) {\n            $this->creationService->handle([\n                'name' => 'Minecraft',\n                'description' => '我的世界 - Mojang 的经典游戏。 支持 Vanilla MC、Spigot 等！',\n            ], 'support@pterodactyl.io');\n        }\n    }\n\n    /**\n     * Create the Source Engine Games nest to be used later on.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    private function createSourceEngineNest(?array $nest = null)\n    {\n        if (is_null($nest)) {\n            $this->creationService->handle([\n                'name' => 'Source Engine',\n                'description' => '包括对大多数 Source 专用服务器游戏的支持。',\n            ], 'support@pterodactyl.io');\n        }\n    }\n\n    /**\n     * Create the Voice Servers nest to be used later on.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    private function createVoiceServersNest(?array $nest = null)\n    {\n        if (is_null($nest)) {\n            $this->creationService->handle([\n                'name' => 'Voice Servers',\n                'description' => 'Mumble 和 Teamspeak 3 等语音服务器。',\n            ], 'support@pterodactyl.io');\n        }\n    }\n\n    /**\n     * Create the Rust nest to be used later on.\n     *\n     * @throws \\Pterodactyl\\Exceptions\\Model\\DataValidationException\n     */\n    private function createRustNest(?array $nest = null)\n    {\n        if (is_null($nest)) {\n            $this->creationService->handle([\n                'name' => 'Rust',\n                'description' => '腐蚀 - 一款您必须为生存而战的游戏。',\n            ], 'support@pterodactyl.io');\n        }\n    }\n}\n"
  },
  {
    "path": "database/Seeders/eggs/minecraft/egg-bungeecord.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v2\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2026-04-05T20:12:58+02:00\",\n    \"name\": \"Bungeecord\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"长期以来，Minecraft 服务器腐竹们一直梦想着以一种免费、简单且可靠的方式，将多个 Minecraft 服务器变成一个整体。而 BungeeCord！实现了大家的梦想。 无论您是希望将多个游戏模式串在一起的小型服务器，还是 ShotBow 网络的腐竹，BungeeCord 都是您的理想解决方案。在 BungeeCord 的帮助下，您社区的全部潜力将会释放。\",\n    \"features\": [\n        \"eula\",\n        \"java_version\",\n        \"pid_limit\"\n    ],\n    \"docker_images\": {\n        \"Java 25\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_25\",\n        \"Java 21\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_21\",\n        \"Java 17\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_17\",\n        \"Java 16\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_16\",\n        \"Java 11\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_11\",\n        \"Java 8\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_8\"\n    },\n    \"file_denylist\": [],\n    \"startup\": \"java -Xms128M -XX:MaxRAMPercentage=95.0 -jar {{SERVER_JARFILE}}\",\n    \"config\": {\n        \"files\": \"{\\r\\n    \\\"config.yml\\\": {\\r\\n        \\\"parser\\\": \\\"yaml\\\",\\r\\n        \\\"find\\\": {\\r\\n            \\\"listeners[0].query_port\\\": \\\"{{server.build.default.port}}\\\",\\r\\n            \\\"listeners[0].host\\\": \\\"0.0.0.0:{{server.build.default.port}}\\\",\\r\\n            \\\"servers.*.address\\\": {\\r\\n                \\\"regex:^(127\\\\\\\\.0\\\\\\\\.0\\\\\\\\.1|localhost)(:\\\\\\\\d{1,5})?$\\\": \\\"{{config.docker.interface}}$2\\\"\\r\\n            }\\r\\n        }\\r\\n    }\\r\\n}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\"Listening on \\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"end\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/ash\\r\\n# Bungeecord Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\n\\r\\ncd \\/mnt\\/server\\r\\n\\r\\nif [ -z \\\"${BUNGEE_VERSION}\\\" ] || [ \\\"${BUNGEE_VERSION}\\\" == \\\"latest\\\" ]; then\\r\\n    BUNGEE_VERSION=\\\"lastStableBuild\\\"\\r\\nfi\\r\\n\\r\\ncurl -o ${SERVER_JARFILE} https:\\/\\/ci.md-5.net\\/job\\/BungeeCord\\/${BUNGEE_VERSION}\\/artifact\\/bootstrap\\/target\\/BungeeCord.jar\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:alpine\",\n            \"entrypoint\": \"ash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"Bungeecord 版本\",\n            \"description\": \"下载并使用的 Bungeecord 版本。\",\n            \"env_variable\": \"BUNGEE_VERSION\",\n            \"default_value\": \"latest\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|alpha_num|between:1,6\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"Bungeecord Jar 文件\",\n            \"description\": \"运行 Bungeecord 时要使用的核心名称。\",\n            \"env_variable\": \"SERVER_JARFILE\",\n            \"default_value\": \"bungeecord.jar\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|regex:\\/^([\\\\w\\\\d._-]+)(\\\\.jar)$\\/\",\n            \"field_type\": \"text\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/minecraft/egg-forge-minecraft.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v2\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2026-04-05T20:12:54+02:00\",\n    \"name\": \"Forge Minecraft\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"Minecraft Forge 服务器。Minecraft Forge 是一个模组 API（应用程序编程接口），它可以更轻松地创建模组，并确保模组彼此兼容。\",\n    \"features\": [\n        \"eula\",\n        \"java_version\",\n        \"pid_limit\"\n    ],\n    \"docker_images\": {\n        \"Java 25\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_25\",\n        \"Java 21\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_21\",\n        \"Java 17\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_17\",\n        \"Java 16\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_16\",\n        \"Java 11\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_11\",\n        \"Java 8\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_8\"\n    },\n    \"file_denylist\": [],\n    \"startup\": \"java -Xms128M -XX:MaxRAMPercentage=95.0 -Dterminal.jline=false -Dterminal.ansi=true $( [[  ! -f unix_args.txt ]] && printf %s \\\"-jar {{SERVER_JARFILE}}\\\" || printf %s \\\"@unix_args.txt\\\" )\",\n    \"config\": {\n        \"files\": \"{\\r\\n    \\\"server.properties\\\": {\\r\\n        \\\"parser\\\": \\\"properties\\\",\\r\\n        \\\"find\\\": {\\r\\n            \\\"server-ip\\\": \\\"0.0.0.0\\\",\\r\\n            \\\"server-port\\\": \\\"{{server.build.default.port}}\\\",\\r\\n            \\\"query.port\\\": \\\"{{server.build.default.port}}\\\"\\r\\n        }\\r\\n    }\\r\\n}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\")! For help, type \\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"stop\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/bash\\r\\n# Forge Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\napt update\\r\\napt install -y curl jq\\r\\n\\r\\nif [[ ! -d \\/mnt\\/server ]]; then\\r\\n  mkdir \\/mnt\\/server\\r\\nfi\\r\\n\\r\\ncd \\/mnt\\/server\\r\\n\\r\\n# Remove spaces from the version number to avoid issues with curl\\r\\nFORGE_VERSION=\\\"$(echo \\\"$FORGE_VERSION\\\" | tr -d ' ')\\\"\\r\\nMC_VERSION=\\\"$(echo \\\"$MC_VERSION\\\" | tr -d ' ')\\\"\\r\\n\\r\\nif [[ ! -z ${FORGE_VERSION} ]]; then\\r\\n  DOWNLOAD_LINK=https:\\/\\/maven.minecraftforge.net\\/net\\/minecraftforge\\/forge\\/${FORGE_VERSION}\\/forge-${FORGE_VERSION}\\r\\n  FORGE_JAR=forge-${FORGE_VERSION}*.jar\\r\\nelse\\r\\n  JSON_DATA=$(curl -sSL https:\\/\\/files.minecraftforge.net\\/maven\\/net\\/minecraftforge\\/forge\\/promotions_slim.json)\\r\\n\\r\\n  if [[ \\\"${MC_VERSION}\\\" == \\\"latest\\\" ]] || [[ \\\"${MC_VERSION}\\\" == \\\"\\\" ]]; then\\r\\n    echo -e \\\"getting latest version of forge.\\\"\\r\\n    MC_VERSION=$(echo -e ${JSON_DATA} | jq -r '.promos | del(.\\\"latest-1.7.10\\\") | del(.\\\"1.7.10-latest-1.7.10\\\") | to_entries[] | .key | select(contains(\\\"latest\\\")) | split(\\\"-\\\")[0]' | sort -t. -k 1,1n -k 2,2n -k 3,3n -k 4,4n | tail -1)\\r\\n    BUILD_TYPE=latest\\r\\n  fi\\r\\n\\r\\n  if [[ \\\"${BUILD_TYPE}\\\" != \\\"recommended\\\" ]] && [[ \\\"${BUILD_TYPE}\\\" != \\\"latest\\\" ]]; then\\r\\n    BUILD_TYPE=recommended\\r\\n  fi\\r\\n\\r\\n  echo -e \\\"minecraft version: ${MC_VERSION}\\\"\\r\\n  echo -e \\\"build type: ${BUILD_TYPE}\\\"\\r\\n\\r\\n  ## some variables for getting versions and things\\r\\n  FILE_SITE=https:\\/\\/maven.minecraftforge.net\\/net\\/minecraftforge\\/forge\\/\\r\\n  VERSION_KEY=$(echo -e ${JSON_DATA} | jq -r --arg MC_VERSION \\\"${MC_VERSION}\\\" --arg BUILD_TYPE \\\"${BUILD_TYPE}\\\" '.promos | del(.\\\"latest-1.7.10\\\") | del(.\\\"1.7.10-latest-1.7.10\\\") | to_entries[] | .key | select(contains($MC_VERSION)) | select(contains($BUILD_TYPE))')\\r\\n\\r\\n  ## locating the forge version\\r\\n  if [[ \\\"${VERSION_KEY}\\\" == \\\"\\\" ]] && [[ \\\"${BUILD_TYPE}\\\" == \\\"recommended\\\" ]]; then\\r\\n    echo -e \\\"dropping back to latest from recommended due to there not being a recommended version of forge for the mc version requested.\\\"\\r\\n    VERSION_KEY=$(echo -e ${JSON_DATA} | jq -r --arg MC_VERSION \\\"${MC_VERSION}\\\" '.promos | del(.\\\"latest-1.7.10\\\") | del(.\\\"1.7.10-latest-1.7.10\\\") | to_entries[] | .key | select(contains($MC_VERSION)) | select(contains(\\\"latest\\\"))')\\r\\n  fi\\r\\n\\r\\n  ## Error if the mc version set wasn't valid.\\r\\n  if [ \\\"${VERSION_KEY}\\\" == \\\"\\\" ] || [ \\\"${VERSION_KEY}\\\" == \\\"null\\\" ]; then\\r\\n    echo -e \\\"The install failed because there is no valid version of forge for the version of minecraft selected.\\\"\\r\\n    exit 1\\r\\n  fi\\r\\n\\r\\n  FORGE_VERSION=$(echo -e ${JSON_DATA} | jq -r --arg VERSION_KEY \\\"$VERSION_KEY\\\" '.promos | .[$VERSION_KEY]')\\r\\n\\r\\n  if [[ \\\"${MC_VERSION}\\\" == \\\"1.7.10\\\" ]] || [[ \\\"${MC_VERSION}\\\" == \\\"1.8.9\\\" ]]; then\\r\\n    DOWNLOAD_LINK=${FILE_SITE}${MC_VERSION}-${FORGE_VERSION}-${MC_VERSION}\\/forge-${MC_VERSION}-${FORGE_VERSION}-${MC_VERSION}\\r\\n    FORGE_JAR=forge-${MC_VERSION}-${FORGE_VERSION}-${MC_VERSION}.jar\\r\\n    if [[ \\\"${MC_VERSION}\\\" == \\\"1.7.10\\\" ]]; then\\r\\n      FORGE_JAR=forge-${MC_VERSION}-${FORGE_VERSION}-${MC_VERSION}-universal.jar\\r\\n    fi\\r\\n  else\\r\\n    DOWNLOAD_LINK=${FILE_SITE}${MC_VERSION}-${FORGE_VERSION}\\/forge-${MC_VERSION}-${FORGE_VERSION}\\r\\n    FORGE_JAR=forge-${MC_VERSION}-${FORGE_VERSION}.jar\\r\\n  fi\\r\\nfi\\r\\n\\r\\n#Adding .jar when not eding by SERVER_JARFILE\\r\\nif [[ ! $SERVER_JARFILE = *\\\\.jar ]]; then\\r\\n  SERVER_JARFILE=\\\"$SERVER_JARFILE.jar\\\"\\r\\nfi\\r\\n\\r\\n#Downloading jars\\r\\necho -e \\\"Downloading forge version ${FORGE_VERSION}\\\"\\r\\necho -e \\\"Download link is ${DOWNLOAD_LINK}\\\"\\r\\n\\r\\nif [[ ! -z \\\"${DOWNLOAD_LINK}\\\" ]]; then\\r\\n  if curl --output \\/dev\\/null --silent --head --fail ${DOWNLOAD_LINK}-installer.jar; then\\r\\n    echo -e \\\"installer jar download link is valid.\\\"\\r\\n  else\\r\\n    echo -e \\\"link is invalid. Exiting now\\\"\\r\\n    exit 2\\r\\n  fi\\r\\nelse\\r\\n  echo -e \\\"no download link provided. Exiting now\\\"\\r\\n  exit 3\\r\\nfi\\r\\n\\r\\ncurl -s -o installer.jar -sS ${DOWNLOAD_LINK}-installer.jar\\r\\n\\r\\n#Checking if downloaded jars exist\\r\\nif [[ ! -f .\\/installer.jar ]]; then\\r\\n  echo \\\"!!! Error downloading forge version ${FORGE_VERSION} !!!\\\"\\r\\n  exit\\r\\nfi\\r\\n\\r\\nfunction  unix_args {\\r\\n  echo -e \\\"Detected Forge 1.17 or newer version. Setting up forge unix args.\\\"\\r\\n  ln -sf libraries\\/net\\/minecraftforge\\/forge\\/*\\/unix_args.txt unix_args.txt\\r\\n}\\r\\n\\r\\n# Delete args to support downgrading\\/upgrading\\r\\nrm -rf libraries\\/net\\/minecraftforge\\/forge\\r\\nrm unix_args.txt\\r\\n\\r\\n#Installing server\\r\\necho -e \\\"Installing forge server.\\\\n\\\"\\r\\njava -jar installer.jar --installServer || { echo -e \\\"\\\\nInstall failed using Forge version ${FORGE_VERSION} and Minecraft version ${MINECRAFT_VERSION}.\\\\nShould you be using unlimited memory value of 0, make sure to increase the default install resource limits in the Wings config or specify exact allocated memory in the server Build Configuration instead of 0! \\\\nOtherwise, the Forge installer will not have enough memory.\\\"; exit 4; }\\r\\n\\r\\n# Check if we need a symlink for 1.17+ Forge JPMS args\\r\\nif [[ $MC_VERSION =~ ^1\\\\.(17|18|19|20|21|22|23) || $FORGE_VERSION =~ ^1\\\\.(17|18|19|20|21|22|23) ]]; then\\r\\n  unix_args\\r\\n\\r\\n# Check if someone has set MC to latest but overwrote it with older Forge version, otherwise we would have false positives\\r\\nelif [[ $MC_VERSION == \\\"latest\\\" && $FORGE_VERSION =~ ^1\\\\.(17|18|19|20|21|22|23) ]]; then\\r\\n  unix_args\\r\\nelse\\r\\n  # For versions below 1.17 that ship with jar\\r\\n  mv $FORGE_JAR $SERVER_JARFILE\\r\\nfi\\r\\n\\r\\necho -e \\\"Deleting installer.jar file.\\\\n\\\"\\r\\nrm -rf installer.jar\\r\\necho -e \\\"Installation process is completed\\\"\",\n            \"container\": \"eclipse-temurin:8-jdk-jammy\",\n            \"entrypoint\": \"bash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"服务器 Jar 文件\",\n            \"description\": \"运行低于 1.17 Forge 版本时使用的核心名称。如果你的核心不对记得修改哦！\",\n            \"env_variable\": \"SERVER_JARFILE\",\n            \"default_value\": \"server.jar\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|regex:\\/^([\\\\w\\\\d._-]+)(\\\\.jar)$\\/\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"Minecraft 版本\",\n            \"description\": \"您要为其安装的 minecraft 版本。\\r\\n\\r\\n如果设置为 latest 将安装最新版本。\",\n            \"env_variable\": \"MC_VERSION\",\n            \"default_value\": \"latest\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|max:9\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"构建类型\",\n            \"description\": \"从 forge 网站上要下载的服务器 jar 类型。\\r\\n\\r\\n有效类型为 \\\"recommended\\\" (推荐版本) 和 \\\"latest\\\" (最新版本)。\",\n            \"env_variable\": \"BUILD_TYPE\",\n            \"default_value\": \"recommended\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|in:recommended,latest\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"Forge 版本\",\n            \"description\": \"获取准确的版本。\\r\\n\\r\\n例如。1.15.2-31.2.4\\r\\n\\r\\n覆盖 MC_VERSION 和 BUILD_TYPE。如果下载服务器文件失败，则安装失败。\",\n            \"env_variable\": \"FORGE_VERSION\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|regex:\\/^[0-9\\\\.\\\\-]+$\\/\",\n            \"field_type\": \"text\"\n        }\n    ]\n}"
  },
  {
    "path": "database/Seeders/eggs/minecraft/egg-paper.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v2\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2026-03-26T10:34:12+01:00\",\n    \"name\": \"Paper\",\n    \"author\": \"parker@pterodactyl.io\",\n    \"description\": \"旨在修复游戏玩法和机制不一致的高性能 Spigot 分支。\",\n    \"features\": [\n        \"eula\",\n        \"java_version\",\n        \"pid_limit\"\n    ],\n    \"docker_images\": {\n        \"Java 25\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_25\",\n        \"Java 21\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_21\",\n        \"Java 17\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_17\",\n        \"Java 16\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_16\",\n        \"Java 11\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_11\",\n        \"Java 8\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_8\"\n    },\n    \"file_denylist\": [],\n    \"startup\": \"java -Xms128M -XX:MaxRAMPercentage=95.0 -Dterminal.jline=false -Dterminal.ansi=true -jar {{SERVER_JARFILE}}\",\n    \"config\": {\n        \"files\": \"{\\r\\n    \\\"server.properties\\\": {\\r\\n        \\\"parser\\\": \\\"properties\\\",\\r\\n        \\\"find\\\": {\\r\\n            \\\"server-ip\\\": \\\"0.0.0.0\\\",\\r\\n            \\\"server-port\\\": \\\"{{server.build.default.port}}\\\",\\r\\n            \\\"query.port\\\": \\\"{{server.build.default.port}}\\\"\\r\\n        }\\r\\n    }\\r\\n}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\")! For help, type \\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"stop\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/ash\\r\\n# Paper Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\nPROJECT=paper\\r\\nUSER_AGENT=\\\"Pterodactyl (https:\\/\\/Pterodactyl.top)\\\"\\r\\n\\r\\nif [ -n \\\"${DL_PATH}\\\" ]; then\\r\\n\\techo -e \\\"Using supplied download url: ${DL_PATH}\\\"\\r\\n\\tDOWNLOAD_URL=`eval echo $(echo ${DL_PATH} | sed -e 's\\/{{\\/${\\/g' -e 's\\/}}\\/}\\/g')`\\r\\nelse\\r\\n\\tVER_EXISTS=`curl --user-agent \\\"${USER_AGENT}\\\"  -s https:\\/\\/fill.papermc.io\\/v3\\/projects\\/${PROJECT} | jq -r --arg VERSION $MINECRAFT_VERSION '.versions | any(.[]; index($VERSION))' | grep -m1 true`\\r\\n\\tLATEST_VERSION=`curl --user-agent \\\"${USER_AGENT}\\\"  -s https:\\/\\/fill.papermc.io\\/v3\\/projects\\/${PROJECT} | jq -r '.versions | to_entries | .[0].value[0]'`\\r\\n\\r\\n\\tif [ \\\"${VER_EXISTS}\\\" == \\\"true\\\" ]; then\\r\\n\\t\\techo -e \\\"Version is valid. Using version ${MINECRAFT_VERSION}\\\"\\r\\n\\telse\\r\\n\\t\\techo -e \\\"Specified version not found. Defaulting to the latest ${PROJECT} version\\\"\\r\\n\\t\\tMINECRAFT_VERSION=${LATEST_VERSION}\\r\\n\\tfi\\r\\n\\r\\n\\tBUILD_EXISTS=`curl --user-agent \\\"${USER_AGENT}\\\"  -s https:\\/\\/fill.papermc.io\\/v3\\/projects\\/${PROJECT}\\/versions\\/${MINECRAFT_VERSION} | jq -r --arg BUILD ${BUILD_NUMBER} '.builds[] | tostring | contains($BUILD)' | grep -m1 true`\\r\\n\\tLATEST_BUILD=`curl --user-agent \\\"${USER_AGENT}\\\"  -s https:\\/\\/fill.papermc.io\\/v3\\/projects\\/${PROJECT}\\/versions\\/${MINECRAFT_VERSION} | jq -r '.builds' | jq -r '.[0]'`\\r\\n\\r\\n\\tif [ \\\"${BUILD_EXISTS}\\\" == \\\"true\\\" ]; then\\r\\n\\t\\techo -e \\\"Build is valid for version ${MINECRAFT_VERSION}. Using build ${BUILD_NUMBER}\\\"\\r\\n\\telse\\r\\n\\t\\techo -e \\\"Using the latest ${PROJECT} build for version ${MINECRAFT_VERSION}\\\"\\r\\n\\t\\tBUILD_NUMBER=${LATEST_BUILD}\\r\\n\\tfi\\r\\n\\r\\n\\techo \\\"Version being downloaded\\\"\\r\\n\\techo -e \\\"Project: ${PROJECT}\\\"\\r\\n\\techo -e \\\"MC Version: ${MINECRAFT_VERSION}\\\"\\r\\n\\techo -e \\\"Build: ${BUILD_NUMBER}\\\"\\r\\n\\tDOWNLOAD_URL=`curl --user-agent \\\"${USER_AGENT}\\\"  -s https:\\/\\/fill.papermc.io\\/v3\\/projects\\/${PROJECT}\\/versions\\/${MINECRAFT_VERSION}\\/builds\\/${BUILD_NUMBER} | jq -r '.downloads.\\\"server:default\\\".url'`\\r\\nfi\\r\\n\\r\\ncd \\/mnt\\/server\\r\\n\\r\\necho -e \\\"Running curl --user-agent \\\\\\\"${USER_AGENT}\\\\\\\"  -o ${SERVER_JARFILE} ${DOWNLOAD_URL}\\\"\\r\\n\\r\\nif [ -f ${SERVER_JARFILE} ]; then\\r\\n\\tmv ${SERVER_JARFILE} ${SERVER_JARFILE}.old\\r\\nfi\\r\\n\\r\\ncurl --user-agent \\\"${USER_AGENT}\\\"  -o ${SERVER_JARFILE} ${DOWNLOAD_URL}\\r\\n\\r\\nif [ ! -f server.properties ]; then\\r\\n    echo -e \\\"Downloading MC server.properties\\\"\\r\\n    curl --user-agent \\\"${USER_AGENT}\\\"  -o server.properties https:\\/\\/ghfast.top\\/https:\\/\\/raw.githubusercontent.com\\/pterodactyl\\/game-eggs\\/main\\/minecraft\\/java\\/server.properties\\r\\nfi\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:alpine\",\n            \"entrypoint\": \"ash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"Minecraft 版本\",\n            \"description\": \"要下载的 Minecraft 版本。\\r\\n\\r\\n如果设置为 latest 将安装最新版本。无效版本将默认为最新版本。\",\n            \"env_variable\": \"MINECRAFT_VERSION\",\n            \"default_value\": \"latest\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|string|max:20\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"服务器 Jar 文件\",\n            \"description\": \"用于运行服务器的服务器核心文件名称。\",\n            \"env_variable\": \"SERVER_JARFILE\",\n            \"default_value\": \"server.jar\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|regex:\\/^([\\\\w\\\\d._-]+)(\\\\.jar)$\\/\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"下载地址\",\n            \"description\": \"用于下载 server.jar 的 URL，而不是安装脚本中的 URL。这条变量用户不可见。\",\n            \"env_variable\": \"DL_PATH\",\n            \"default_value\": \"\",\n            \"user_viewable\": false,\n            \"user_editable\": false,\n            \"rules\": \"nullable|string\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"构建版本号\",\n            \"description\": \"paper 版本的构建版本号。\\r\\n\\r\\n如果设置为 latest 将安装最新版本。无效版本将默认为最新版本。\",\n            \"env_variable\": \"BUILD_NUMBER\",\n            \"default_value\": \"latest\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|max:20\",\n            \"field_type\": \"text\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/minecraft/egg-sponge--sponge-vanilla.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v2\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2026-04-05T20:12:50+02:00\",\n    \"name\": \"Sponge (SpongeVanilla)\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"SpongeVanilla 是建立在独立的原版 Minecraft 服务端上的 SpongeAPI 实现。\",\n    \"features\": [\n        \"eula\",\n        \"java_version\",\n        \"pid_limit\"\n    ],\n    \"docker_images\": {\n        \"Java 25\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_25\",\n        \"Java 21\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_21\",\n        \"Java 16\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_16\",\n        \"Java 11\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_11\",\n        \"Java 8\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_8\"\n    },\n    \"file_denylist\": [],\n    \"startup\": \"java -Xms128M -XX:MaxRAMPercentage=95.0 -jar {{SERVER_JARFILE}}\",\n    \"config\": {\n        \"files\": \"{\\r\\n    \\\"server.properties\\\": {\\r\\n        \\\"parser\\\": \\\"properties\\\",\\r\\n        \\\"find\\\": {\\r\\n            \\\"server-ip\\\": \\\"0.0.0.0\\\",\\r\\n            \\\"server-port\\\": \\\"{{server.build.default.port}}\\\",\\r\\n            \\\"query.port\\\": \\\"{{server.build.default.port}}\\\"\\r\\n        }\\r\\n    }\\r\\n}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\")! For help, type \\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"stop\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/ash\\r\\n# Sponge Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\n\\r\\ncd \\/mnt\\/server\\r\\n\\r\\ncurl -sSL \\\"https:\\/\\/repo.spongepowered.org\\/maven\\/org\\/spongepowered\\/spongevanilla\\/${SPONGE_VERSION}\\/spongevanilla-${SPONGE_VERSION}.jar\\\" -o ${SERVER_JARFILE}\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:alpine\",\n            \"entrypoint\": \"ash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"Sponge 版本\",\n            \"description\": \"下载并使用的 SpongeVanilla 版本。\",\n            \"env_variable\": \"SPONGE_VERSION\",\n            \"default_value\": \"1.12.2-7.3.0\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|regex:\\/^([a-zA-Z0-9.\\\\-_]+)$\\/\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"服务器 Jar 文件\",\n            \"description\": \"运行 SpongeVanilla 时使用的核心文件名称。\",\n            \"env_variable\": \"SERVER_JARFILE\",\n            \"default_value\": \"server.jar\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|regex:\\/^([\\\\w\\\\d._-]+)(\\\\.jar)$\\/\",\n            \"field_type\": \"text\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/minecraft/egg-vanilla-minecraft.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v2\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2026-04-05T20:12:45+02:00\",\n    \"name\": \"Vanilla Minecraft\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"Minecraft 是一款关于放置积木和进行冒险的游戏。探索随机生成的世界，建造从最简单的房屋到最宏伟的城堡。在创造模式下用无限资源的玩游戏，或在生存模式中深入挖掘，制作武器和盔甲以抵御危险的怪物。独自或与朋友一起探险这个世界吧！\",\n    \"features\": [\n        \"eula\",\n        \"java_version\",\n        \"pid_limit\"\n    ],\n    \"docker_images\": {\n        \"Java 25\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_25\",\n        \"Java 21\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_21\",\n        \"Java 17\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_17\",\n        \"Java 16\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_16\",\n        \"Java 11\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_11\",\n        \"Java 8\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:java_8\"\n    },\n    \"file_denylist\": [],\n    \"startup\": \"java -Xms128M -XX:MaxRAMPercentage=95.0 -jar {{SERVER_JARFILE}}\",\n    \"config\": {\n        \"files\": \"{\\r\\n    \\\"server.properties\\\": {\\r\\n        \\\"parser\\\": \\\"properties\\\",\\r\\n        \\\"find\\\": {\\r\\n            \\\"server-ip\\\": \\\"0.0.0.0\\\",\\r\\n            \\\"server-port\\\": \\\"{{server.build.default.port}}\\\",\\r\\n            \\\"query.port\\\": \\\"{{server.build.default.port}}\\\"\\r\\n        }\\r\\n    }\\r\\n}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\")! For help, type \\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"stop\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/ash\\r\\n# Vanilla MC Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\nmkdir -p \\/mnt\\/server\\r\\ncd \\/mnt\\/server\\r\\n\\r\\nLATEST_VERSION=`curl https:\\/\\/launchermeta.mojang.com\\/mc\\/game\\/version_manifest.json | jq -r '.latest.release'`\\r\\nLATEST_SNAPSHOT_VERSION=`curl https:\\/\\/launchermeta.mojang.com\\/mc\\/game\\/version_manifest.json | jq -r '.latest.snapshot'`\\r\\n\\r\\necho -e \\\"latest version is $LATEST_VERSION\\\"\\r\\necho -e \\\"latest snapshot is $LATEST_SNAPSHOT_VERSION\\\"\\r\\n\\r\\nif [ -z \\\"$VANILLA_VERSION\\\" ] || [ \\\"$VANILLA_VERSION\\\" == \\\"latest\\\" ]; then\\r\\n  MANIFEST_URL=$(curl -sSL https:\\/\\/launchermeta.mojang.com\\/mc\\/game\\/version_manifest.json | jq --arg VERSION $LATEST_VERSION -r '.versions | .[] | select(.id== $VERSION )|.url')\\r\\nelif [ \\\"$VANILLA_VERSION\\\" == \\\"snapshot\\\" ]; then\\r\\n  MANIFEST_URL=$(curl -sSL https:\\/\\/launchermeta.mojang.com\\/mc\\/game\\/version_manifest.json | jq --arg VERSION $LATEST_SNAPSHOT_VERSION -r '.versions | .[] | select(.id== $VERSION )|.url')\\r\\nelse\\r\\n  MANIFEST_URL=$(curl -sSL https:\\/\\/launchermeta.mojang.com\\/mc\\/game\\/version_manifest.json | jq --arg VERSION $VANILLA_VERSION -r '.versions | .[] | select(.id== $VERSION )|.url')\\r\\nfi\\r\\n\\r\\nDOWNLOAD_URL=$(curl ${MANIFEST_URL} | jq .downloads.server | jq -r '. | .url')\\r\\n\\r\\necho -e \\\"running: curl -o ${SERVER_JARFILE} $DOWNLOAD_URL\\\"\\r\\ncurl -o ${SERVER_JARFILE} $DOWNLOAD_URL\\r\\n\\r\\necho -e \\\"Install Complete\\\"\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:alpine\",\n            \"entrypoint\": \"ash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"服务器 Jar 文件\",\n            \"description\": \"用于运行服务器的服务器核心文件名称。\",\n            \"env_variable\": \"SERVER_JARFILE\",\n            \"default_value\": \"server.jar\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|regex:\\/^([\\\\w\\\\d._-]+)(\\\\.jar)$\\/\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"服务器版本\",\n            \"description\": \"要安装的原版 Minecraft 版本。使用 \\\"latest\\\" 将安装最新版本，或使用 \\\"snapshot\\\" 安装最新快照版本。转到设置 > 重新安装服务器以应用此次更改。\",\n            \"env_variable\": \"VANILLA_VERSION\",\n            \"default_value\": \"latest\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|between:3,15\",\n            \"field_type\": \"text\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/rust/egg-rust.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v2\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2023-03-25T13:37:00+00:00\",\n    \"name\": \"Rust\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"Rust(腐蚀) 一款尽一切努力生存的游戏。为此，您需要克服饥饿、干渴和寒冷等风险。建立庇护所。杀死动物以获取肉。保护自己免受其他玩家的攻击，甚至是朋友的背叛。与其他玩家建立联盟并组建城镇。尽一切努力生存吧。\",\n    \"features\": [\n        \"steam_disk_space\"\n    ],\n    \"docker_images\": {\n        \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/games:rust\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/games:rust\"\n    },\n    \"file_denylist\": [],\n    \"startup\": \".\\/RustDedicated -batchmode +server.port {{SERVER_PORT}} +server.queryport {{QUERY_PORT}} +server.identity \\\"rust\\\" +rcon.port {{RCON_PORT}} +rcon.web true +server.hostname \\\\\\\"{{HOSTNAME}}\\\\\\\" +server.level \\\\\\\"{{LEVEL}}\\\\\\\" +server.description \\\\\\\"{{DESCRIPTION}}\\\\\\\" +server.url \\\\\\\"{{SERVER_URL}}\\\\\\\" +server.headerimage \\\\\\\"{{SERVER_IMG}}\\\\\\\" +server.logoimage \\\\\\\"{{SERVER_LOGO}}\\\\\\\" +server.maxplayers {{MAX_PLAYERS}} +rcon.password \\\\\\\"{{RCON_PASS}}\\\\\\\" +server.saveinterval {{SAVEINTERVAL}} +app.port {{APP_PORT}}  $( [ -z ${MAP_URL} ] && printf %s \\\"+server.worldsize \\\\\\\"{{WORLD_SIZE}}\\\\\\\" +server.seed \\\\\\\"{{WORLD_SEED}}\\\\\\\"\\\" || printf %s \\\"+server.levelurl {{MAP_URL}}\\\" ) {{ADDITIONAL_ARGS}}\",\n    \"config\": {\n        \"files\": \"{}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\"Server startup complete\\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"quit\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/bash\\r\\n# steamcmd Base Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\n\\r\\nSRCDS_APPID=258550\\r\\n\\r\\n## just in case someone removed the defaults.\\r\\nif [ \\\"${STEAM_USER}\\\" == \\\"\\\" ]; then\\r\\n    echo -e \\\"steam user is not set.\\\\n\\\"\\r\\n    echo -e \\\"Using anonymous user.\\\\n\\\"\\r\\n    STEAM_USER=anonymous\\r\\n    STEAM_PASS=\\\"\\\"\\r\\n    STEAM_AUTH=\\\"\\\"\\r\\nelse\\r\\n    echo -e \\\"user set to ${STEAM_USER}\\\"\\r\\nfi\\r\\n\\r\\n## download and install steamcmd\\r\\ncd \\/tmp\\r\\nmkdir -p \\/mnt\\/server\\/steamcmd\\r\\ncurl -sSL -o steamcmd.tar.gz https:\\/\\/steamcdn-a.akamaihd.net\\/client\\/installer\\/steamcmd_linux.tar.gz\\r\\ntar -xzvf steamcmd.tar.gz -C \\/mnt\\/server\\/steamcmd\\r\\nmkdir -p \\/mnt\\/server\\/steamapps # Fix steamcmd disk write error when this folder is missing\\r\\ncd \\/mnt\\/server\\/steamcmd\\r\\n\\r\\n# SteamCMD fails otherwise for some reason, even running as root.\\r\\n# This is changed at the end of the install process anyways.\\r\\nchown -R root:root \\/mnt\\r\\nexport HOME=\\/mnt\\/server\\r\\n\\r\\n## install game using steamcmd\\r\\n.\\/steamcmd.sh +force_install_dir \\/mnt\\/server +login ${STEAM_USER} ${STEAM_PASS} ${STEAM_AUTH} +app_update ${SRCDS_APPID} ${EXTRA_FLAGS} validate +quit ## other flags may be needed depending on install. looking at you cs 1.6\\r\\n\\r\\n## set up 32 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk32\\r\\ncp -v linux32\\/steamclient.so ..\\/.steam\\/sdk32\\/steamclient.so\\r\\n\\r\\n## set up 64 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk64\\r\\ncp -v linux64\\/steamclient.so ..\\/.steam\\/sdk64\\/steamclient.so\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:debian\",\n            \"entrypoint\": \"bash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"服务器名称\",\n            \"description\": \"您的服务器在公共服务器列表中的名称。\",\n            \"env_variable\": \"HOSTNAME\",\n            \"default_value\": \"A Rust Server\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|max:60\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"模组框架\",\n            \"description\": \"可以使用的模组框架: carbon, oxide, vanilla.\\r\\n对于非模组的，服务器默认安装\\\"vanilla\\\"\",\n            \"env_variable\": \"FRAMEWORK\",\n            \"default_value\": \"vanilla\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|in:vanilla,oxide,carbon\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"Level\",\n            \"description\": \"Rust 使用的 world 文件。\",\n            \"env_variable\": \"LEVEL\",\n            \"default_value\": \"Procedural Map\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|max:20\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"描述\",\n            \"description\": \"服务器标题下的描述。通常用于规则&信息。使用 \\\\n 换行。\",\n            \"env_variable\": \"DESCRIPTION\",\n            \"default_value\": \"Powered by Pterodactyl\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"URL\",\n            \"description\": \"服务器的 URL。这是单击“访问网站”按钮时出现的内容。\",\n            \"env_variable\": \"SERVER_URL\",\n            \"default_value\": \"http:\\/\\/pterodactyl.io\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|url\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"世界规模\",\n            \"description\": \"程序性地图的世界大小。\",\n            \"env_variable\": \"WORLD_SIZE\",\n            \"default_value\": \"3000\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|integer\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"世界种子\",\n            \"description\": \"程序性地图的种子。\",\n            \"env_variable\": \"WORLD_SEED\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|string\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"最大玩家数\",\n            \"description\": \"服务器允许的最大玩家数量。\",\n            \"env_variable\": \"MAX_PLAYERS\",\n            \"default_value\": \"40\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|integer\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"服务器图片\",\n            \"description\": \"服务器列表顶部的标题图像。\",\n            \"env_variable\": \"SERVER_IMG\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|url\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"查询端口\",\n            \"description\": \"服务器查询端口。不能与游戏的主端口相同。\",\n            \"env_variable\": \"QUERY_PORT\",\n            \"default_value\": \"27017\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|integer\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"RCON 端口\",\n            \"description\": \"RCON 连接的端口。\",\n            \"env_variable\": \"RCON_PORT\",\n            \"default_value\": \"28016\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|integer\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"RCON 密码\",\n            \"description\": \"RCON 访问密码。\",\n            \"env_variable\": \"RCON_PASS\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|regex:\\/^[\\\\w.-]*$\\/|max:64\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"保存时间间隔\",\n            \"description\": \"以秒为单位设置服务器自动保存时间间隔。\",\n            \"env_variable\": \"SAVEINTERVAL\",\n            \"default_value\": \"60\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|integer\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"附加参数\",\n            \"description\": \"向服务器添加其他启动参数。\",\n            \"env_variable\": \"ADDITIONAL_ARGS\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|string\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"应用程序端口\",\n            \"description\": \"Rust+ 应用程序的端口。-1 以禁用。\",\n            \"env_variable\": \"APP_PORT\",\n            \"default_value\": \"28082\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|integer\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"服务器 Logo\",\n            \"description\": \"Rust+ 应用程序的服务器 Logo。\",\n            \"env_variable\": \"SERVER_LOGO\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|url\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"自定义地图 URL\",\n            \"description\": \"从 URL 中下载的地图将会覆盖现有地图。无效的 URL 将导致服务器崩溃。\",\n            \"env_variable\": \"MAP_URL\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|url\",\n            \"field_type\": \"text\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/source-engine/egg-ark--survival-evolved.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v2\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2025-06-12T18:44:29+02:00\",\n    \"name\": \"Ark: Survival Evolved\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"《方舟：生存进化》故事主要讲述，一群男女从在岸边醒来后，发现自己身处一个充满恐龙的神秘岛屿“ARK”。游戏中除了狩猎、资源搜刮、物品打造、种植、科研、调查技术和建造房子来抵抗炎热的白天，冰冷的夜晚，易变的天气系统，危险的野外和潜在的敌人等之外，玩家还必须面对其他玩家所扮演的幸存者，合作或者是相互厮杀。并且有80多种恐龙和其他史前生物，玩家们可以驯服这些庞大的生物，并利用它们来和更强的敌人战斗。当然恐龙并非岛上的危险生物，其他的玩家也正在组织自己的部落，积累各种资源和经验来建立庞大的村庄和城市，他们还能不断发展技术来跨越原始的石器时代并进入现代的电气时代，而且他们还会不断战斗来摧毁威胁到他们的人。\",\n    \"features\": [\n        \"steam_disk_space\"\n    ],\n    \"docker_images\": [\n        \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/games:source\"\n    ],\n    \"file_denylist\": [],\n    \"startup\": \"rmv() { echo  \\\"stopping server\\\"; rcon -t rcon -a 127.0.0.1:${RCON_PORT} -p ${ARK_ADMIN_PASSWORD} saveworld &&rcon -t rcon -a 127.0.0.1:${RCON_PORT} -p ${ARK_ADMIN_PASSWORD} DoExit && wait ${ARK_PID}; echo \\\"Server Closed\\\"; exit; }; trap rmv 15 2; cd ShooterGame\\/Binaries\\/Linux && .\\/ShooterGameServer {{SERVER_MAP}}?listen?SessionName=\\\"{{SESSION_NAME}}\\\"?ServerPassword={{ARK_PASSWORD}}?ServerAdminPassword={{ARK_ADMIN_PASSWORD}}?Port={{SERVER_PORT}}?RCONPort={{RCON_PORT}}?QueryPort={{QUERY_PORT}}?RCONEnabled=True?MaxPlayers={{MAX_PLAYERS}}?GameModIds={{MOD_ID}}$( [ \\\"$BATTLE_EYE\\\" == \\\"1\\\" ] || printf %s ' -NoBattlEye' ) -server -automanagedmods {{ARGS}} -log & ARK_PID=$! ; until echo \\\"waiting for rcon connection...\\\"; (rcon -t rcon -a 127.0.0.1:${RCON_PORT} -p ${ARK_ADMIN_PASSWORD})<&0 & wait $!; do sleep 5; done\",\n    \"config\": {\n        \"files\": \"{}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\"Waiting commands for 127.0.0.1:\\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"^C\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/bash\\r\\n# steamcmd Base Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\n# Image to install with is 'ubuntu:18.04'\\r\\napt -y update\\r\\napt -y --no-install-recommends --no-install-suggests install curl lib32gcc-s1 ca-certificates\\r\\n\\r\\n## just in case someone removed the defaults.\\r\\nif [ \\\"${STEAM_USER}\\\" == \\\"\\\" ]; then\\r\\n    STEAM_USER=anonymous\\r\\n    STEAM_PASS=\\\"\\\"\\r\\n    STEAM_AUTH=\\\"\\\"\\r\\nfi\\r\\n\\r\\n## download and install steamcmd\\r\\ncd \\/tmp\\r\\nmkdir -p \\/mnt\\/server\\/steamcmd\\r\\ncurl -sSL -o steamcmd.tar.gz https:\\/\\/steamcdn-a.akamaihd.net\\/client\\/installer\\/steamcmd_linux.tar.gz\\r\\ntar -xzvf steamcmd.tar.gz -C \\/mnt\\/server\\/steamcmd\\r\\n\\r\\nmkdir -p \\/mnt\\/server\\/Engine\\/Binaries\\/ThirdParty\\/SteamCMD\\/Linux\\r\\ntar -xzvf steamcmd.tar.gz -C \\/mnt\\/server\\/Engine\\/Binaries\\/ThirdParty\\/SteamCMD\\/Linux\\r\\nmkdir -p \\/mnt\\/server\\/steamapps # Fix steamcmd disk write error when this folder is missing\\r\\ncd \\/mnt\\/server\\/steamcmd\\r\\n\\r\\n# SteamCMD fails otherwise for some reason, even running as root.\\r\\n# This is changed at the end of the install process anyways.\\r\\nchown -R root:root \\/mnt\\r\\nexport HOME=\\/mnt\\/server\\r\\n\\r\\n## install game using steamcmd\\r\\n.\\/steamcmd.sh +login ${STEAM_USER} ${STEAM_PASS} ${STEAM_AUTH} +force_install_dir \\/mnt\\/server +app_update ${SRCDS_APPID} ${EXTRA_FLAGS} +quit ## other flags may be needed depending on install. looking at you cs 1.6\\r\\n\\r\\n## set up 32 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk32\\r\\ncp -v linux32\\/steamclient.so ..\\/.steam\\/sdk32\\/steamclient.so\\r\\n\\r\\n## set up 64 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk64\\r\\ncp -v linux64\\/steamclient.so ..\\/.steam\\/sdk64\\/steamclient.so\\r\\n\\r\\n## create a symbolic link for loading mods\\r\\ncd \\/mnt\\/server\\/Engine\\/Binaries\\/ThirdParty\\/SteamCMD\\/Linux\\r\\nln -sf ..\\/..\\/..\\/..\\/..\\/Steam\\/steamapps steamapps\\r\\ncd \\/mnt\\/server\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:debian\",\n            \"entrypoint\": \"bash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"服务器密码\",\n            \"description\": \"如果指定，玩家必须提供此密码才能加入服务器。\",\n            \"env_variable\": \"ARK_PASSWORD\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|alpha_dash|between:1,100\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"管理员密码\",\n            \"description\": \"如果指定，玩家必须提供此密码（通过游戏内控制台）才能访问使用管理员命令。\",\n            \"env_variable\": \"ARK_ADMIN_PASSWORD\",\n            \"default_value\": \"PleaseChangeMe\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|alpha_dash|between:1,100\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"服务器地图\",\n            \"description\": \"可用地图：TheIsland、TheCenter、Ragnarok、ScorchedEarth_P、Aberration_P、Extinction、Valguero_P、Genesis、CrystalIsles、Gen2、Fjordur\",\n            \"env_variable\": \"SERVER_MAP\",\n            \"default_value\": \"TheIsland\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|max:20\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"服务器名称\",\n            \"description\": \"方舟服务器名称\",\n            \"env_variable\": \"SESSION_NAME\",\n            \"default_value\": \"A Pterodactyl Hosted ARK Server\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|max:128\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"Rcon 端口\",\n            \"description\": \"rcon 工具使用的方舟 rcon 端口。\",\n            \"env_variable\": \"RCON_PORT\",\n            \"default_value\": \"27020\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|numeric\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"查询端口\",\n            \"description\": \"steam服务器列表和方舟客户端服务器列表使用的方舟查询端口。\",\n            \"env_variable\": \"QUERY_PORT\",\n            \"default_value\": \"27015\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|numeric\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"自动更新服务器\",\n            \"description\": \"服务器是否启用自动更新。\\r\\n\\r\\n默认值为 0。设置为 1 以更新\",\n            \"env_variable\": \"AUTO_UPDATE\",\n            \"default_value\": \"0\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|boolean\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"Battle Eye\",\n            \"description\": \"是否启用BattleEye反作弊程序\\r\\n\\r\\n0 为禁用\\r\\n1 为启用\\r\\n\\r\\n默认=\\\"1\\\"\",\n            \"env_variable\": \"BATTLE_EYE\",\n            \"default_value\": \"1\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|boolean\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"App ID\",\n            \"description\": \"方舟 Steam 应用程序 ID 用于自动更新。留空以避免自动更新。\",\n            \"env_variable\": \"SRCDS_APPID\",\n            \"default_value\": \"376030\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"nullable|numeric\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"附加参数\",\n            \"description\": \"指定额外的启动参数，例如 -crossplay。您必须包含破折号 - 并用空格分隔每个参数：-crossplay -exclusivejoin\",\n            \"env_variable\": \"ARGS\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|string\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"Mods\",\n            \"description\": \"指定加载顺序和模组。ModID 需要用逗号分隔，例如：ModID1,ModID2\",\n            \"env_variable\": \"MOD_ID\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|string\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"最大玩家数\",\n            \"description\": \"指定能够加入服务器的玩家的最大数量。\",\n            \"env_variable\": \"MAX_PLAYERS\",\n            \"default_value\": \"12\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"numeric\",\n            \"field_type\": \"text\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/source-engine/egg-counter--strike--global-offensive.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v1\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2022-01-18T07:01:54-05:00\",\n    \"name\": \"Counter-Strike: Global Offensive\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"《反恐精英：全球攻势》又称 CSGO 是一款多人第一人称射击游戏，由 Hidden Path Entertainment 和 Valve Corporation 开发。\",\n    \"features\": [\n        \"gsl_token\",\n        \"steam_disk_space\"\n    ],\n    \"images\": [\n        \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/games:source\"\n    ],\n    \"file_denylist\": [],\n    \"startup\": \".\\/srcds_run -game csgo -console -port {{SERVER_PORT}} +ip 0.0.0.0 +map {{SRCDS_MAP}} -strictportbind -norestart +sv_setsteamaccount {{STEAM_ACC}}\",\n    \"config\": {\n        \"files\": \"{}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\"Connection to Steam servers successful\\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"quit\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/bash\\r\\n# steamcmd Base Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\n\\r\\n## just in case someone removed the defaults.\\r\\nif [ \\\"${STEAM_USER}\\\" == \\\"\\\" ]; then\\r\\n    STEAM_USER=anonymous\\r\\n    STEAM_PASS=\\\"\\\"\\r\\n    STEAM_AUTH=\\\"\\\"\\r\\nfi\\r\\n\\r\\n## download and install steamcmd\\r\\ncd \\/tmp\\r\\nmkdir -p \\/mnt\\/server\\/steamcmd\\r\\ncurl -sSL -o steamcmd.tar.gz https:\\/\\/steamcdn-a.akamaihd.net\\/client\\/installer\\/steamcmd_linux.tar.gz\\r\\ntar -xzvf steamcmd.tar.gz -C \\/mnt\\/server\\/steamcmd\\r\\nmkdir -p \\/mnt\\/server\\/steamapps # Fix steamcmd disk write error when this folder is missing\\r\\ncd \\/mnt\\/server\\/steamcmd\\r\\n\\r\\n# SteamCMD fails otherwise for some reason, even running as root.\\r\\n# This is changed at the end of the install process anyways.\\r\\nchown -R root:root \\/mnt\\r\\nexport HOME=\\/mnt\\/server\\r\\n\\r\\n## install game using steamcmd\\r\\n.\\/steamcmd.sh +force_install_dir \\/mnt\\/server +login ${STEAM_USER} ${STEAM_PASS} ${STEAM_AUTH} +app_update ${SRCDS_APPID} ${EXTRA_FLAGS} +quit ## other flags may be needed depending on install. looking at you cs 1.6\\r\\n\\r\\n## set up 32 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk32\\r\\ncp -v linux32\\/steamclient.so ..\\/.steam\\/sdk32\\/steamclient.so\\r\\n\\r\\n## set up 64 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk64\\r\\ncp -v linux64\\/steamclient.so ..\\/.steam\\/sdk64\\/steamclient.so\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:debian\",\n            \"entrypoint\": \"bash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"地图\",\n            \"description\": \"服务器的默认地图。\",\n            \"env_variable\": \"SRCDS_MAP\",\n            \"default_value\": \"de_dust2\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|alpha_dash\"\n        },\n        {\n            \"name\": \"Steam 帐户令牌\",\n            \"description\": \"服务器公开显示所需的 Steam 帐户令牌。\",\n            \"env_variable\": \"STEAM_ACC\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|alpha_num|size:32\"\n        },\n        {\n            \"name\": \"Source AppID\",\n            \"description\": \"游戏在服务器重新启动时更新的必要内容。请不要修改这个。\",\n            \"env_variable\": \"SRCDS_APPID\",\n            \"default_value\": \"740\",\n            \"user_viewable\": false,\n            \"user_editable\": false,\n            \"rules\": \"required|string|max:20\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/source-engine/egg-custom-source-engine-game.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v1\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2022-01-18T07:03:08-05:00\",\n    \"name\": \"Custom Source Engine Game\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"此选项允许修改启动参数和其他详细信息以在面板上运行基于 SRCDS 的自定义游戏。\",\n    \"features\": [\n        \"steam_disk_space\"\n    ],\n    \"images\": [\n        \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/games:source\"\n    ],\n    \"file_denylist\": [],\n    \"startup\": \".\\/srcds_run -game {{SRCDS_GAME}} -console -port {{SERVER_PORT}} +map {{SRCDS_MAP}} +ip 0.0.0.0 -strictportbind -norestart\",\n    \"config\": {\n        \"files\": \"{}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\"gameserver Steam ID\\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"quit\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/bash\\r\\n# steamcmd Base Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\n\\r\\n##\\r\\n#\\r\\n# Variables\\r\\n# STEAM_USER, STEAM_PASS, STEAM_AUTH - Steam user setup. If a user has 2fa enabled it will most likely fail due to timeout. Leave blank for anon install.\\r\\n# WINDOWS_INSTALL - if it's a windows server you want to install set to 1\\r\\n# SRCDS_APPID - steam app id ffound here - https:\\/\\/developer.valvesoftware.com\\/wiki\\/Dedicated_Servers_List\\r\\n# EXTRA_FLAGS - when a server has extra glas for things like beta installs or updates.\\r\\n#\\r\\n##\\r\\n\\r\\n\\r\\n## just in case someone removed the defaults.\\r\\nif [ \\\"${STEAM_USER}\\\" == \\\"\\\" ]; then\\r\\n    echo -e \\\"steam user is not set.\\\\n\\\"\\r\\n    echo -e \\\"Using anonymous user.\\\\n\\\"\\r\\n    STEAM_USER=anonymous\\r\\n    STEAM_PASS=\\\"\\\"\\r\\n    STEAM_AUTH=\\\"\\\"\\r\\nelse\\r\\n    echo -e \\\"user set to ${STEAM_USER}\\\"\\r\\nfi\\r\\n\\r\\n## download and install steamcmd\\r\\ncd \\/tmp\\r\\nmkdir -p \\/mnt\\/server\\/steamcmd\\r\\ncurl -sSL -o steamcmd.tar.gz https:\\/\\/steamcdn-a.akamaihd.net\\/client\\/installer\\/steamcmd_linux.tar.gz\\r\\ntar -xzvf steamcmd.tar.gz -C \\/mnt\\/server\\/steamcmd\\r\\nmkdir -p \\/mnt\\/server\\/steamapps # Fix steamcmd disk write error when this folder is missing\\r\\ncd \\/mnt\\/server\\/steamcmd\\r\\n\\r\\n# SteamCMD fails otherwise for some reason, even running as root.\\r\\n# This is changed at the end of the install process anyways.\\r\\nchown -R root:root \\/mnt\\r\\nexport HOME=\\/mnt\\/server\\r\\n\\r\\n## install game using steamcmd\\r\\n.\\/steamcmd.sh +force_install_dir \\/mnt\\/server +login ${STEAM_USER} ${STEAM_PASS} ${STEAM_AUTH} $( [[ \\\"${WINDOWS_INSTALL}\\\" == \\\"1\\\" ]] && printf %s '+@sSteamCmdForcePlatformType windows' ) +app_update ${SRCDS_APPID} ${EXTRA_FLAGS} validate +quit ## other flags may be needed depending on install. looking at you cs 1.6\\r\\n\\r\\n## set up 32 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk32\\r\\ncp -v linux32\\/steamclient.so ..\\/.steam\\/sdk32\\/steamclient.so\\r\\n\\r\\n## set up 64 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk64\\r\\ncp -v linux64\\/steamclient.so ..\\/.steam\\/sdk64\\/steamclient.so\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:debian\",\n            \"entrypoint\": \"bash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"游戏 ID\",\n            \"description\": \"使用 SRCDS 下载并运行的游戏对应 ID。\",\n            \"env_variable\": \"SRCDS_APPID\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|numeric|digits_between:1,6\"\n        },\n        {\n            \"name\": \"游戏名称\",\n            \"description\": \"对应于使用 SRCDS 下载并运行的游戏名称。\",\n            \"env_variable\": \"SRCDS_GAME\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|alpha_dash|between:1,100\"\n        },\n        {\n            \"name\": \"地图\",\n            \"description\": \"服务器的默认地图。\",\n            \"env_variable\": \"SRCDS_MAP\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|alpha_dash\"\n        },\n        {\n            \"name\": \"Steam 用户名\",\n            \"description\": \"\",\n            \"env_variable\": \"STEAM_USER\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|string\"\n        },\n        {\n            \"name\": \"Steam 密码\",\n            \"description\": \"\",\n            \"env_variable\": \"STEAM_PASS\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|string\"\n        },\n        {\n            \"name\": \"Steam 身份验证\",\n            \"description\": \"\",\n            \"env_variable\": \"STEAM_AUTH\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|string\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/source-engine/egg-garrys-mod.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v1\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2022-01-18T07:04:20-05:00\",\n    \"name\": \"Garrys Mod\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"盖瑞模组，原名 Garrys Mod 是一款由 Garry Newman 创建并由其公司 Facepunch Studios 开发的沙盒物理游戏。\",\n    \"features\": [\n        \"gsl_token\",\n        \"steam_disk_space\"\n    ],\n    \"images\": [\n        \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/games:source\"\n    ],\n    \"file_denylist\": [],\n    \"startup\": \".\\/srcds_run -game garrysmod -console -port {{SERVER_PORT}} +ip 0.0.0.0 +host_workshop_collection {{WORKSHOP_ID}} +map {{SRCDS_MAP}} +gamemode {{GAMEMODE}} -strictportbind -norestart +sv_setsteamaccount {{STEAM_ACC}} +maxplayers {{MAX_PLAYERS}}  -tickrate {{TICKRATE}}  $( [ \\\"$LUA_REFRESH\\\" == \\\"1\\\" ] || printf %s '-disableluarefresh' )\",\n    \"config\": {\n        \"files\": \"{}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\"gameserver Steam ID\\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"quit\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/bash\\r\\n# steamcmd Base Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\n\\r\\n## just in case someone removed the defaults.\\r\\nif [ \\\"${STEAM_USER}\\\" == \\\"\\\" ]; then\\r\\n    echo -e \\\"steam user is not set.\\\\n\\\"\\r\\n    echo -e \\\"Using anonymous user.\\\\n\\\"\\r\\n    STEAM_USER=anonymous\\r\\n    STEAM_PASS=\\\"\\\"\\r\\n    STEAM_AUTH=\\\"\\\"\\r\\nelse\\r\\n    echo -e \\\"user set to ${STEAM_USER}\\\"\\r\\nfi\\r\\n\\r\\n## download and install steamcmd\\r\\ncd \\/tmp\\r\\nmkdir -p \\/mnt\\/server\\/steamcmd\\r\\ncurl -sSL -o steamcmd.tar.gz https:\\/\\/steamcdn-a.akamaihd.net\\/client\\/installer\\/steamcmd_linux.tar.gz\\r\\ntar -xzvf steamcmd.tar.gz -C \\/mnt\\/server\\/steamcmd\\r\\nmkdir -p \\/mnt\\/server\\/steamapps # Fix steamcmd disk write error when this folder is missing\\r\\ncd \\/mnt\\/server\\/steamcmd\\r\\n\\r\\n# SteamCMD fails otherwise for some reason, even running as root.\\r\\n# This is changed at the end of the install process anyways.\\r\\nchown -R root:root \\/mnt\\r\\nexport HOME=\\/mnt\\/server\\r\\n\\r\\n## install game using steamcmd\\r\\n.\\/steamcmd.sh +force_install_dir \\/mnt\\/server +login ${STEAM_USER} ${STEAM_PASS} ${STEAM_AUTH} $( [[ \\\"${WINDOWS_INSTALL}\\\" == \\\"1\\\" ]] && printf %s '+@sSteamCmdForcePlatformType windows' ) +app_update ${SRCDS_APPID} ${EXTRA_FLAGS} validate +quit ## other flags may be needed depending on install. looking at you cs 1.6\\r\\n\\r\\n## set up 32 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk32\\r\\ncp -v linux32\\/steamclient.so ..\\/.steam\\/sdk32\\/steamclient.so\\r\\n\\r\\n## set up 64 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk64\\r\\ncp -v linux64\\/steamclient.so ..\\/.steam\\/sdk64\\/steamclient.so\\r\\n\\r\\n# Creating needed default files for the game\\r\\ncd \\/mnt\\/server\\/garrysmod\\/lua\\/autorun\\/server\\r\\necho '\\r\\n-- Docs: https:\\/\\/wiki.garrysmod.com\\/page\\/resource\\/AddWorkshop\\r\\n-- Place the ID of the workshop addon you want to be downloaded to people who join your server, not the collection ID\\r\\n-- Use https:\\/\\/beta.configcreator.com\\/create\\/gmod\\/resources.lua to easily create a list based on your collection ID\\r\\n\\r\\nresource.AddWorkshop( \\\"\\\" )\\r\\n' > workshop.lua\\r\\n\\r\\ncd \\/mnt\\/server\\/garrysmod\\/cfg\\r\\necho '\\r\\n\\/\\/ Please do not set RCon in here, use the startup parameters.\\r\\n\\r\\nhostname\\t\\t\\\"New Gmod Server\\\"\\r\\nsv_password\\t\\t\\\"\\\"\\r\\nsv_loadingurl   \\\"\\\"\\r\\nsv_downloadurl  \\\"\\\"\\r\\n\\r\\n\\/\\/ Steam Server List Settings\\r\\n\\/\\/ sv_location \\\"eu\\\"\\r\\nsv_region \\\"255\\\"\\r\\nsv_lan \\\"0\\\"\\r\\nsv_max_queries_sec_global \\\"30000\\\"\\r\\nsv_max_queries_window \\\"45\\\"\\r\\nsv_max_queries_sec \\\"5\\\"\\r\\n\\r\\n\\/\\/ Server Limits\\r\\nsbox_maxprops\\t\\t100\\r\\nsbox_maxragdolls\\t5\\r\\nsbox_maxnpcs\\t\\t10\\r\\nsbox_maxballoons\\t10\\r\\nsbox_maxeffects\\t\\t10\\r\\nsbox_maxdynamite\\t10\\r\\nsbox_maxlamps\\t\\t10\\r\\nsbox_maxthrusters\\t10\\r\\nsbox_maxwheels\\t\\t10\\r\\nsbox_maxhoverballs\\t10\\r\\nsbox_maxvehicles\\t20\\r\\nsbox_maxbuttons\\t\\t10\\r\\nsbox_maxsents\\t\\t20\\r\\nsbox_maxemitters\\t5\\r\\nsbox_godmode\\t\\t0\\r\\nsbox_noclip\\t\\t    0\\r\\n\\r\\n\\/\\/ Network Settings - Please keep these set to default.\\r\\n\\r\\nsv_minrate\\t\\t75000\\r\\nsv_maxrate\\t\\t0\\r\\ngmod_physiterations\\t2\\r\\nnet_splitpacket_maxrate\\t45000\\r\\ndecalfrequency\\t\\t12 \\r\\n\\r\\n\\/\\/ Execute Ban Files - Please do not edit\\r\\nexec banned_ip.cfg \\r\\nexec banned_user.cfg \\r\\n\\r\\n\\/\\/ Add custom lines under here\\r\\n' > server.cfg\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:debian\",\n            \"entrypoint\": \"bash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"地图\",\n            \"description\": \"服务器的默认地图。\",\n            \"env_variable\": \"SRCDS_MAP\",\n            \"default_value\": \"gm_flatgrass\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|alpha_dash\"\n        },\n        {\n            \"name\": \"Steam 帐户令牌\",\n            \"description\": \"服务器公开显示所需的 Steam 帐户令牌。\",\n            \"env_variable\": \"STEAM_ACC\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|string|alpha_num|size:32\"\n        },\n        {\n            \"name\": \"Source AppID\",\n            \"description\": \"游戏在服务器重新启动时更新的必要内容。请不要修改这个。\",\n            \"env_variable\": \"SRCDS_APPID\",\n            \"default_value\": \"4020\",\n            \"user_viewable\": false,\n            \"user_editable\": false,\n            \"rules\": \"required|string|max:20\"\n        },\n        {\n            \"name\": \"创意工坊 ID\",\n            \"description\": \"您的创意工坊收藏 ID（网址末尾的数字）\",\n            \"env_variable\": \"WORKSHOP_ID\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|integer\"\n        },\n        {\n            \"name\": \"游戏模式\",\n            \"description\": \"服务器的游戏模式。\",\n            \"env_variable\": \"GAMEMODE\",\n            \"default_value\": \"sandbox\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string\"\n        },\n        {\n            \"name\": \"最大玩家数\",\n            \"description\": \"您的游戏服务器上允许的最大玩家数。\",\n            \"env_variable\": \"MAX_PLAYERS\",\n            \"default_value\": \"32\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|integer|max:128\"\n        },\n        {\n            \"name\": \"Tickrate\",\n            \"description\": \"tickrate 定义了服务器更新每个实体位置的速度。\",\n            \"env_variable\": \"TICKRATE\",\n            \"default_value\": \"22\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|integer|max:100\"\n        },\n        {\n            \"name\": \"Lua 热重载\",\n            \"description\": \"0 = 禁用 Lua 热重载，\\r\\n1 = 启用 Lua 热重载\",\n            \"env_variable\": \"LUA_REFRESH\",\n            \"default_value\": \"0\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|boolean\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/source-engine/egg-insurgency.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v1\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2022-01-18T07:07:27-05:00\",\n    \"name\": \"Insurgency\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"《Insurgency》是一款现代战争背景下的FPS游戏，是一款代表着现代战场中个人以及战术水平的游戏。只有技术最好的玩家才能成为指挥官，并有机会带领整个团队走向胜利。\",\n    \"features\": [\n        \"steam_disk_space\"\n    ],\n    \"images\": [\n        \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/games:source\"\n    ],\n    \"file_denylist\": [],\n    \"startup\": \".\\/srcds_run -game insurgency -console -port {{SERVER_PORT}} +map {{SRCDS_MAP}} +ip 0.0.0.0 -strictportbind -norestart\",\n    \"config\": {\n        \"files\": \"{}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\"gameserver Steam ID\\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"quit\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/bash\\r\\n# steamcmd Base Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\n\\r\\n## download and install steamcmd\\r\\ncd \\/tmp\\r\\nmkdir -p \\/mnt\\/server\\/steamcmd\\r\\ncurl -sSL -o steamcmd.tar.gz https:\\/\\/steamcdn-a.akamaihd.net\\/client\\/installer\\/steamcmd_linux.tar.gz\\r\\ntar -xzvf steamcmd.tar.gz -C \\/mnt\\/server\\/steamcmd\\r\\ncd \\/mnt\\/server\\/steamcmd\\r\\n\\r\\n# SteamCMD fails otherwise for some reason, even running as root.\\r\\n# This is changed at the end of the install process anyways.\\r\\nchown -R root:root \\/mnt\\r\\nexport HOME=\\/mnt\\/server\\r\\n\\r\\n## install game using steamcmd\\r\\n.\\/steamcmd.sh +force_install_dir \\/mnt\\/server +login anonymous +app_update ${SRCDS_APPID} ${EXTRA_FLAGS} +quit\\r\\n\\r\\n## set up 32 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk32\\r\\ncp -v linux32\\/steamclient.so ..\\/.steam\\/sdk32\\/steamclient.so\\r\\n\\r\\n## set up 64 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk64\\r\\ncp -v linux64\\/steamclient.so ..\\/.steam\\/sdk64\\/steamclient.so\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:debian\",\n            \"entrypoint\": \"bash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"游戏 ID\",\n            \"description\": \"使用 SRCDS 下载并运行的游戏对应 ID。\",\n            \"env_variable\": \"SRCDS_APPID\",\n            \"default_value\": \"237410\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|regex:\\/^(237410)$\\/\"\n        },\n        {\n            \"name\": \"默认地图\",\n            \"description\": \"启动服务器时要使用的默认地图。\",\n            \"env_variable\": \"SRCDS_MAP\",\n            \"default_value\": \"sinjar\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|regex:\\/^(\\\\w{1,20})$\\/\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/source-engine/egg-team-fortress2.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v1\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2022-01-30T14:09:22-05:00\",\n    \"name\": \"Team Fortress 2\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"《军团要塞2》(Team Fortress 2，简称TF2)是由维尔福软件公司(Valve)开发的一个团队作战型在线多人第一人称射击游戏。该游戏是Valve先前作品《军团要塞·经典》(Team Fortress Classic)的续作，于2007年10月10日以橙盒(The Orange Box)三合一方式在Windows和Xbox 360平台上发行。\",\n    \"features\": [\n        \"gsl_token\",\n        \"steam_disk_space\"\n    ],\n    \"images\": [\n        \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/games:source\"\n    ],\n    \"file_denylist\": [],\n    \"startup\": \".\\/srcds_run -game tf -console -port {{SERVER_PORT}} +map {{SRCDS_MAP}} +ip 0.0.0.0 -strictportbind -norestart +sv_setsteamaccount {{STEAM_ACC}}\",\n    \"config\": {\n        \"files\": \"{}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\"gameserver Steam ID\\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"quit\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/bash\\r\\n# steamcmd Base Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\n# Image to install with is 'debian:buster-slim'\\r\\n\\r\\n##\\r\\n#\\r\\n# Variables\\r\\n# STEAM_USER, STEAM_PASS, STEAM_AUTH - Steam user setup. If a user has 2fa enabled it will most likely fail due to timeout. Leave blank for anon install.\\r\\n# WINDOWS_INSTALL - if it's a windows server you want to install set to 1\\r\\n# SRCDS_APPID - steam app id ffound here - https:\\/\\/developer.valvesoftware.com\\/wiki\\/Dedicated_Servers_List\\r\\n# EXTRA_FLAGS - when a server has extra glas for things like beta installs or updates.\\r\\n#\\r\\n##\\r\\n\\r\\n## just in case someone removed the defaults.\\r\\nif [ \\\"${STEAM_USER}\\\" == \\\"\\\" ]; then\\r\\n    echo -e \\\"steam user is not set.\\\\n\\\"\\r\\n    echo -e \\\"Using anonymous user.\\\\n\\\"\\r\\n    STEAM_USER=anonymous\\r\\n    STEAM_PASS=\\\"\\\"\\r\\n    STEAM_AUTH=\\\"\\\"\\r\\nelse\\r\\n    echo -e \\\"user set to ${STEAM_USER}\\\"\\r\\nfi\\r\\n\\r\\n## download and install steamcmd\\r\\ncd \\/tmp\\r\\nmkdir -p \\/mnt\\/server\\/steamcmd\\r\\ncurl -sSL -o steamcmd.tar.gz https:\\/\\/steamcdn-a.akamaihd.net\\/client\\/installer\\/steamcmd_linux.tar.gz\\r\\ntar -xzvf steamcmd.tar.gz -C \\/mnt\\/server\\/steamcmd\\r\\nmkdir -p \\/mnt\\/server\\/steamapps # Fix steamcmd disk write error when this folder is missing\\r\\ncd \\/mnt\\/server\\/steamcmd\\r\\n\\r\\n# SteamCMD fails otherwise for some reason, even running as root.\\r\\n# This is changed at the end of the install process anyways.\\r\\nchown -R root:root \\/mnt\\r\\nexport HOME=\\/mnt\\/server\\r\\n\\r\\n## install game using steamcmd\\r\\n.\\/steamcmd.sh +force_install_dir \\/mnt\\/server +login ${STEAM_USER} ${STEAM_PASS} ${STEAM_AUTH} $( [[ \\\"${WINDOWS_INSTALL}\\\" == \\\"1\\\" ]] && printf %s '+@sSteamCmdForcePlatformType windows' ) +app_update ${SRCDS_APPID} ${EXTRA_FLAGS} validate +quit ## other flags may be needed depending on install. looking at you cs 1.6\\r\\n\\r\\n## set up 32 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk32\\r\\ncp -v linux32\\/steamclient.so ..\\/.steam\\/sdk32\\/steamclient.so\\r\\n\\r\\n## set up 64 bit libraries\\r\\nmkdir -p \\/mnt\\/server\\/.steam\\/sdk64\\r\\ncp -v linux64\\/steamclient.so ..\\/.steam\\/sdk64\\/steamclient.so\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:debian\",\n            \"entrypoint\": \"bash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"游戏 ID\",\n            \"description\": \"使用 SRCDS 下载并运行的游戏对应 ID。\",\n            \"env_variable\": \"SRCDS_APPID\",\n            \"default_value\": \"232250\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|regex:\\/^(232250)$\\/\"\n        },\n        {\n            \"name\": \"默认地图\",\n            \"description\": \"启动服务器时要使用的默认地图。\",\n            \"env_variable\": \"SRCDS_MAP\",\n            \"default_value\": \"cp_dustbowl\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|regex:\\/^(\\\\w{1,20})$\\/\"\n        },\n        {\n            \"name\": \"Steam\",\n            \"description\": \"用于公开显示服务器的 Steam 游戏服务器登录令牌。在 https:\\/\\/steamcommunity.com\\/dev\\/managegameservers 处生成一个\",\n            \"env_variable\": \"STEAM_ACC\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|alpha_num|size:32\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/voice-servers/egg-mumble-server.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v2\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2022-10-15T12:38:18+02:00\",\n    \"name\": \"Mumble Server\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"Mumble 是一款开源、低延迟、高质量的语音聊天软件，主要用于游戏时使用。\",\n    \"features\": null,\n    \"docker_images\": {\n        \"Mumble\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-images\\/yolks:voice_mumble\"\n    },\n    \"file_denylist\": [],\n    \"startup\": \"mumble-server -fg -ini murmur.ini\",\n    \"config\": {\n        \"files\": \"{\\r\\n    \\\"murmur.ini\\\": {\\r\\n        \\\"parser\\\": \\\"ini\\\",\\r\\n        \\\"find\\\": {\\r\\n            \\\"database\\\": \\\"\\/home\\/container\\/murmur.sqlite\\\",\\r\\n            \\\"logfile\\\": \\\"\\/home\\/container\\/murmur.log\\\",\\r\\n            \\\"port\\\": \\\"{{server.build.default.port}}\\\",\\r\\n            \\\"host\\\": \\\"0.0.0.0\\\",\\r\\n            \\\"users\\\": \\\"{{server.build.env.MAX_USERS}}\\\"\\r\\n        }\\r\\n    }\\r\\n}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\"Server listening on\\\"\\r\\n}\",\n        \"logs\": \"{}\",\n        \"stop\": \"^C\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/ash\\r\\n\\r\\nif [ ! -d \\/mnt\\/server\\/ ]; then\\r\\n    mkdir \\/mnt\\/server\\/\\r\\nfi\\r\\n\\r\\ncd \\/mnt\\/server\\r\\n\\r\\nFILE=\\/mnt\\/server\\/murmur.ini\\r\\nif [ -f \\\"$FILE\\\" ]; then\\r\\n    echo \\\"Config file already exists.\\\"\\r\\nelse \\r\\n    echo \\\"Downloading the config file.\\\"\\r\\n    apk add --no-cache murmur\\r\\n    cp \\/etc\\/murmur.ini \\/mnt\\/server\\/murmur.ini\\r\\n    apk del murmur\\r\\nfi\\r\\necho \\\"done\\\"\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:alpine\",\n            \"entrypoint\": \"ash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"最大用户数\",\n            \"description\": \"Mumble 服务器上的最大并发用户数。\",\n            \"env_variable\": \"MAX_USERS\",\n            \"default_value\": \"100\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|numeric|digits_between:1,5\",\n            \"field_type\": \"text\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/Seeders/eggs/voice-servers/egg-teamspeak3-server.json",
    "content": "{\n    \"_comment\": \"DO NOT EDIT: FILE GENERATED AUTOMATICALLY BY PTERODACTYL PANEL - PTERODACTYL.IO\",\n    \"meta\": {\n        \"version\": \"PTDL_v2\",\n        \"update_url\": null\n    },\n    \"exported_at\": \"2023-01-28T00:52:56+01:00\",\n    \"name\": \"Teamspeak3 Server\",\n    \"author\": \"support@pterodactyl.io\",\n    \"description\": \"VoIP 软件在设计时考虑了安全性，具有清晰的语音质量、无限的自定义选项以及可扩展到数千名用户同时使用的功能。\",\n    \"features\": null,\n    \"docker_images\": {\n        \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:debian\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/yolks:debian\"\n    },\n    \"file_denylist\": [],\n    \"startup\": \".\\/ts3server default_voice_port={{SERVER_PORT}} query_port={{QUERY_PORT}} filetransfer_ip=0.0.0.0 filetransfer_port={{FILE_TRANSFER}} query_http_port={{QUERY_HTTP}} query_ssh_port={{QUERY_SSH}} query_protocols={{QUERY_PROTOCOLS_VAR}} serveradmin_password={{SERVERADMIN_PASSWORD}} license_accepted=1\",\n    \"config\": {\n        \"files\": \"{}\",\n        \"startup\": \"{\\r\\n    \\\"done\\\": \\\"listening on 0.0.0.0:\\\"\\r\\n}\",\n        \"logs\": \"{\\r\\n    \\\"custom\\\": true,\\r\\n    \\\"location\\\": \\\"logs\\/ts3.log\\\"\\r\\n}\",\n        \"stop\": \"^C\"\n    },\n    \"scripts\": {\n        \"installation\": {\n            \"script\": \"#!\\/bin\\/ash\\r\\n# TS3 Installation Script\\r\\n#\\r\\n# Server Files: \\/mnt\\/server\\r\\n\\r\\nif [ -z ${TS_VERSION} ] || [ ${TS_VERSION} == latest ]; then\\r\\n    TS_VERSION=$(curl -sSL https:\\/\\/teamspeak.com\\/versions\\/server.json | jq -r '.linux.x86_64.version')\\r\\nfi\\r\\n\\r\\ncd \\/mnt\\/server\\r\\n\\r\\necho -e \\\"getting files from http:\\/\\/files.teamspeak-services.com\\/releases\\/server\\/${TS_VERSION}\\/teamspeak3-server_linux_amd64-${TS_VERSION}.tar.bz2\\\" \\r\\ncurl -L http:\\/\\/files.teamspeak-services.com\\/releases\\/server\\/${TS_VERSION}\\/teamspeak3-server_linux_amd64-${TS_VERSION}.tar.bz2 | tar -xvj --strip-components=1\\r\\ncp .\\/redist\\/libmariadb.so.2 .\\/\",\n            \"container\": \"registry.cn-shanghai.aliyuncs.com\\/pterodactyl-china\\/installers:alpine\",\n            \"entrypoint\": \"ash\"\n        }\n    },\n    \"variables\": [\n        {\n            \"name\": \"服务器版本\",\n            \"description\": \"运行服务器时使用的 Teamspeak 3 版本。\",\n            \"env_variable\": \"TS_VERSION\",\n            \"default_value\": \"latest\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|max:6\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"文件传输端口\",\n            \"description\": \"Teamspeak 文件传输端口\",\n            \"env_variable\": \"FILE_TRANSFER\",\n            \"default_value\": \"30033\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|integer|between:1025,65535\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"查询端口\",\n            \"description\": \"Teamspeak 查询端口\",\n            \"env_variable\": \"QUERY_PORT\",\n            \"default_value\": \"10011\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|integer|between:1025,65535\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"查询协议\",\n            \"description\": \"逗号分隔的协议列表，可用于连接到服务器查询| \\r\\n可能的值为 raw、ssh 和 http | \\r\\n例如：raw,ssh,http\",\n            \"env_variable\": \"QUERY_PROTOCOLS_VAR\",\n            \"default_value\": \"raw,http,ssh\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"required|string|max:12\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"查询 SSH 端口\",\n            \"description\": \"使用 SSH 为服务器查询连接打开的 TCP 端口\",\n            \"env_variable\": \"QUERY_SSH\",\n            \"default_value\": \"10022\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|integer|between:1025,65535\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"查询 HTTP 端口\",\n            \"description\": \"使用 http 为服务器查询连接打开的 TCP 端口\",\n            \"env_variable\": \"QUERY_HTTP\",\n            \"default_value\": \"10080\",\n            \"user_viewable\": true,\n            \"user_editable\": false,\n            \"rules\": \"required|integer|between:1025,65535\",\n            \"field_type\": \"text\"\n        },\n        {\n            \"name\": \"服务器查询管理员密码\",\n            \"description\": \"用于服务器查询管理员用户的密码。\",\n            \"env_variable\": \"SERVERADMIN_PASSWORD\",\n            \"default_value\": \"\",\n            \"user_viewable\": true,\n            \"user_editable\": true,\n            \"rules\": \"nullable|string|max:32\",\n            \"field_type\": \"text\"\n        }\n    ]\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_195641_add_allocations_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddAllocationsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('allocations', function (Blueprint $table) {\n            $table->increments('id');\n            $table->mediumInteger('node')->unsigned();\n            $table->string('ip');\n            $table->mediumInteger('port')->unsigned();\n            $table->mediumInteger('assigned_to')->unsigned()->nullable();\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('allocations');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_195851_add_api_keys.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddApiKeys extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('api_keys', function (Blueprint $table) {\n            $table->increments('id');\n            $table->char('public', 16);\n            $table->text('secret');\n            $table->text('allowed_ips')->nullable();\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('api_keys');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_200044_add_api_permissions.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddApiPermissions extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('api_permissions', function (Blueprint $table) {\n            $table->increments('id');\n            $table->mediumInteger('key_id')->unsigned();\n            $table->string('permission');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('api_permissions');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_200159_add_downloads.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddDownloads extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('downloads', function (Blueprint $table) {\n            $table->increments('id');\n            $table->char('token', 36)->unique();\n            $table->char('server', 36);\n            $table->text('path');\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('downloads');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_200421_create_failed_jobs_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateFailedJobsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('failed_jobs', function (Blueprint $table) {\n            $table->increments('id');\n            $table->text('connection');\n            $table->text('queue');\n            $table->longText('payload');\n            $table->timestamp('failed_at');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('failed_jobs');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_200440_create_jobs_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateJobsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('jobs', function (Blueprint $table) {\n            $table->bigIncrements('id');\n            $table->string('queue');\n            $table->longText('payload');\n            $table->tinyInteger('attempts')->unsigned();\n            $table->tinyInteger('reserved')->unsigned();\n            $table->unsignedInteger('reserved_at')->nullable();\n            $table->unsignedInteger('available_at');\n            $table->unsignedInteger('created_at');\n\n            $table->index(['queue', 'reserved', 'reserved_at']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('jobs');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_200528_add_locations.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddLocations extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('locations', function (Blueprint $table) {\n            $table->increments('id');\n            $table->string('short')->unique();\n            $table->string('long');\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('locations');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_200648_add_nodes.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddNodes extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('nodes', function (Blueprint $table) {\n            $table->increments('id');\n            $table->smallInteger('public')->unsigned();\n            $table->string('name');\n            $table->mediumInteger('location')->unsigned();\n            $table->string('fqdn');\n            $table->string('scheme')->default('https');\n            $table->integer('memory')->unsigned();\n            $table->mediumInteger('memory_overallocate')->unsigned()->nullable();\n            $table->integer('disk')->unsigned();\n            $table->mediumInteger('disk_overallocate')->unsigned()->nullable();\n            $table->char('daemonSecret', 36)->unique();\n            $table->smallInteger('daemonListen')->unsigned()->default(8080);\n            $table->smallInteger('daemonSFTP')->unsigned()->default(2022);\n            $table->string('daemonBase')->default('/home/daemon-files');\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('nodes');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_201433_add_password_resets.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddPasswordResets extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('password_resets', function (Blueprint $table) {\n            $table->string('email')->index();\n            $table->string('token')->index();\n            $table->timestamp('created_at');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('password_resets');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_201531_add_permissions.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddPermissions extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('permissions', function (Blueprint $table) {\n            $table->increments('id');\n            $table->integer('user_id')->unsigned();\n            $table->integer('server_id')->unsigned();\n            $table->string('permissions');\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('permissions');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_201649_add_server_variables.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddServerVariables extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('server_variables', function (Blueprint $table) {\n            $table->increments('id');\n            $table->mediumInteger('server_id')->unsigned();\n            $table->mediumInteger('variable_id')->unsigned();\n            $table->string('variable_value');\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('server_variables');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_201748_add_servers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddServers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('servers', function (Blueprint $table) {\n            $table->increments('id');\n            $table->char('uuid', 36)->unique();\n            $table->char('uuidShort', 8)->unique();\n            $table->mediumInteger('node')->unsigned();\n            $table->string('name');\n            $table->tinyInteger('active')->unsigned();\n            $table->mediumInteger('owner')->unsigned();\n            $table->integer('memory')->unsigned();\n            $table->integer('swap')->unsigned();\n            $table->integer('disk')->unsigned();\n            $table->integer('io')->unsigned();\n            $table->integer('cpu')->unsigned();\n            $table->tinyInteger('oom_disabled')->unsigned()->default(0);\n            $table->string('ip');\n            $table->integer('port')->unsigned();\n            $table->mediumInteger('service')->unsigned();\n            $table->mediumInteger('option')->unsigned();\n            $table->text('startup');\n            $table->char('daemonSecret', 36)->unique();\n            $table->string('username')->unique();\n            $table->tinyInteger('installed')->unsigned()->default(0);\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('servers');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_202544_add_service_options.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddServiceOptions extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('service_options', function (Blueprint $table) {\n            $table->increments('id');\n            $table->mediumInteger('parent_service')->unsigned();\n            $table->string('name');\n            $table->text('description');\n            $table->string('tag');\n            $table->text('docker_image');\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('service_options');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_202731_add_service_varibles.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddServiceVaribles extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('service_variables', function (Blueprint $table) {\n            $table->increments('id');\n            $table->mediumInteger('option_id')->unsigned();\n            $table->string('name');\n            $table->text('description');\n            $table->string('env_variable');\n            $table->string('default_value');\n            $table->tinyInteger('user_viewable')->unsigned();\n            $table->tinyInteger('user_editable')->unsigned();\n            $table->tinyInteger('required')->unsigned();\n            $table->string('regex')->nullable();\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('service_variables');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_202943_add_services.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddServices extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('services', function (Blueprint $table) {\n            $table->increments('id');\n            $table->string('name');\n            $table->text('description');\n            $table->string('file');\n            $table->string('executable');\n            $table->text('startup');\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('services');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_203119_create_settings_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateSettingsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('settings', function (Blueprint $table) {\n            $table->string('key')->unique();\n            $table->text('value');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('settings');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_203150_add_subusers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddSubusers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('subusers', function (Blueprint $table) {\n            $table->increments('id');\n            $table->integer('user_id')->unsigned();\n            $table->integer('server_id')->unsigned();\n            $table->char('daemonSecret', 36)->unique();\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('subusers');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_203159_add_users.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddUsers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('users', function (Blueprint $table) {\n            $table->increments('id');\n            $table->char('uuid', 36)->unique();\n            $table->string('email')->unique();\n            $table->text('password');\n            $table->string('remember_token')->nullable();\n            $table->char('language', 5)->default('zh');\n            $table->tinyInteger('root_admin')->unsigned()->default(0);\n            $table->tinyInteger('use_totp')->unsigned();\n            $table->char('totp_secret', 16)->nullable();\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('users');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_23_203947_create_sessions_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateSessionsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('sessions', function (Blueprint $table) {\n            $table->string('id')->unique();\n            $table->integer('user_id')->nullable();\n            $table->string('ip_address', 45)->nullable();\n            $table->text('user_agent')->nullable();\n            $table->text('payload');\n            $table->integer('last_activity');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::drop('sessions');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_01_25_234418_rename_permissions_column.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RenamePermissionsColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('permissions', function (Blueprint $table) {\n            $table->renameColumn('permissions', 'permission');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('permissions', function (Blueprint $table) {\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_02_07_172148_add_databases_tables.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddDatabasesTables extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('databases', function (Blueprint $table) {\n            $table->increments('id');\n            $table->integer('server')->unsigned();\n            $table->integer('db_server')->unsigned();\n            $table->string('database')->unique();\n            $table->string('username')->unique();\n            $table->string('remote')->default('%');\n            $table->text('password');\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::drop('databases');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_02_07_181319_add_database_servers_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddDatabaseServersTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('database_servers', function (Blueprint $table) {\n            $table->increments('id');\n            $table->string('name');\n            $table->string('host');\n            $table->integer('port')->unsigned();\n            $table->string('username');\n            $table->text('password');\n            $table->integer('max_databases')->unsigned()->nullable();\n            $table->integer('linked_node')->unsigned()->nullable();\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::drop('database_servers');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_02_13_154306_add_service_option_default_startup.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddServiceOptionDefaultStartup extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->text('executable')->after('docker_image')->nullable()->default(null);\n            $table->text('startup')->after('executable')->nullable()->default(null);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropColumn('executable');\n            $table->dropColumn('startup');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_02_20_155318_add_unique_service_field.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddUniqueServiceField extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->string('file')->unique()->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->dropUnique(['file']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_02_27_163411_add_tasks_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddTasksTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('tasks', function (Blueprint $table) {\n            $table->increments('id');\n            $table->integer('server')->unsigned();\n            $table->tinyInteger('active')->default(1);\n            $table->string('action');\n            $table->text('data');\n            $table->tinyInteger('queued')->unsigned()->default(0);\n            $table->string('year')->default('*');\n            $table->string('day_of_week')->default('*');\n            $table->string('month')->default('*');\n            $table->string('day_of_month')->default('*');\n            $table->string('hour')->default('*');\n            $table->string('minute')->default('*');\n            $table->timestamp('last_run')->nullable();\n            $table->timestamp('next_run')->nullable();\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::drop('tasks');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_02_27_163447_add_tasks_log_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddTasksLogTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('tasks_log', function (Blueprint $table) {\n            $table->increments('id');\n            $table->integer('task_id')->unsigned();\n            $table->timestamp('run_time');\n            $table->integer('run_status')->unsigned();\n            $table->text('response');\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::drop('tasks_log');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_03_18_155649_add_nullable_field_lastrun.php",
    "content": "<?php\n\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddNullableFieldLastrun extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up()\n    {\n        $table = DB::getQueryGrammar()->wrapTable('tasks');\n        DB::statement('ALTER TABLE ' . $table . ' CHANGE `last_run` `last_run` TIMESTAMP NULL;');\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down()\n    {\n        $table = DB::getQueryGrammar()->wrapTable('tasks');\n        DB::statement('ALTER TABLE ' . $table . ' CHANGE `last_run` `last_run` TIMESTAMP;');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_08_30_212718_add_ip_alias.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddIpAlias extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->text('ip_alias')->nullable()->after('ip');\n        });\n\n        $allocations = DB::select('SELECT id, ip FROM allocations');\n        foreach ($allocations as $allocation) {\n            DB::update(\n                'UPDATE allocations SET ip_alias = :ip WHERE id = :id',\n                [\n                    'ip' => $allocation->ip,\n                    'id' => $allocation->id,\n                ]\n            );\n        }\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->dropColumn('ip_alias');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_08_30_213301_modify_ip_storage_method.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ModifyIpStorageMethod extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->mediumInteger('allocation')->unsigned()->after('oom_disabled');\n        });\n\n        // Parse All Servers\n        $servers = DB::select('SELECT id, ip, port, node FROM servers');\n        foreach ($servers as $server) {\n            $allocation = DB::select(\n                'SELECT id FROM allocations WHERE ip = :ip AND port = :port AND node = :node',\n                [\n                    'ip' => $server->ip,\n                    'port' => $server->port,\n                    'node' => $server->node,\n                ]\n            );\n\n            if (isset($allocation[0])) {\n                DB::update(\n                    'UPDATE servers SET allocation = :alocid WHERE id = :id',\n                    [\n                        'alocid' => $allocation[0]->id,\n                        'id' => $server->id,\n                    ]\n                );\n            }\n        }\n\n        // Updated the server allocations, remove old fields\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('ip');\n            $table->dropColumn('port');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->text('ip')->after('allocation');\n            $table->integer('port')->unsigned()->after('ip');\n        });\n\n        // Find the allocations and reset the servers...\n        $servers = DB::select('SELECT id, allocation FROM servers');\n        foreach ($servers as $server) {\n            $allocation = DB::select('SELECT * FROM allocations WHERE id = :alocid', ['alocid' => $server->allocation]);\n\n            if (isset($allocation[0])) {\n                DB::update(\n                    'UPDATE servers SET ip = :ip, port = :port WHERE id = :id',\n                    [\n                        'ip' => $allocation[0]->ip,\n                        'port' => $allocation[0]->port,\n                        'id' => $server->id,\n                    ]\n                );\n            }\n        }\n\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('allocation');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_01_193520_add_suspension_for_servers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddSuspensionForServers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->tinyInteger('suspended')->unsigned()->default(0)->after('active');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('suspended');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_01_211924_remove_active_column.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RemoveActiveColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('active');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->tinyInteger('active')->after('name')->unsigned()->default(0);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_02_190647_add_sftp_password_storage.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddSftpPasswordStorage extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->text('sftp_password')->after('username')->nullable();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('sftp_password');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_04_171338_update_jobs_tables.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateJobsTables extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('jobs', function (Blueprint $table) {\n            $table->dropIndex(['queue', 'reserved', 'reserved_at']);\n            $table->dropColumn('reserved');\n\n            $table->index(['queue', 'reserved_at']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('jobs', function (Blueprint $table) {\n            $table->dropIndex(['queue', 'reserved_at']);\n\n            $table->tinyInteger('reserved')->unsigned();\n            $table->index(['queue', 'reserved', 'reserved_at']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_04_172028_update_failed_jobs_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateFailedJobsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('failed_jobs', function (Blueprint $table) {\n            $table->text('exception');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('failed_jobs', function (Blueprint $table) {\n            $table->dropColumn('exception');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_04_182835_create_notifications_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateNotificationsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('notifications', function (Blueprint $table) {\n            $table->string('id')->primary();\n            $table->string('type');\n            $table->morphs('notifiable');\n            $table->text('data');\n            $table->timestamp('read_at')->nullable();\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::drop('notifications');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_07_163017_add_unique_identifier.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddUniqueIdentifier extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->char('author', 36)->after('id');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->dropColumn('author');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_14_145945_allow_longer_regex_field.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AllowLongerRegexField extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->text('regex')->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->string('regex')->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_17_194246_add_docker_image_column.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddDockerImageColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->string('image')->after('daemonSecret');\n        });\n\n        // Populate the column\n        DB::transaction(function () {\n            $servers = DB::table('servers')->select(\n                'servers.id',\n                'service_options.docker_image as s_optionImage'\n            )->join('service_options', 'service_options.id', '=', 'servers.option')->get();\n\n            foreach ($servers as $server) {\n                $server->image = $server->s_optionImage;\n                $server->save();\n            }\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('image');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_21_165554_update_servers_column_name.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateServersColumnName extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->renameColumn('server', 'server_id');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->renameColumn('server_id', 'server');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_09_29_213518_rename_double_insurgency.php",
    "content": "<?php\n\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RenameDoubleInsurgency extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::transaction(function () {\n            $model = DB::table('service_options')->where('parent_service', 2)->where('id', 3)->where('name', 'Insurgency')->first();\n            if ($model) {\n                $model->name = 'Team Fortress 2';\n                $model->save();\n            }\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_07_152117_build_api_log_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass BuildApiLogTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('api_logs', function (Blueprint $table) {\n            $table->increments('id');\n            $table->boolean('authorized');\n            $table->text('error')->nullable();\n            $table->char('key', 16)->nullable();\n            $table->char('method', 6);\n            $table->text('route');\n            $table->text('content')->nullable();\n            $table->text('user_agent');\n            $table->ipAddress('request_ip');\n            $table->timestampsTz();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::drop('api_logs');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_14_164802_update_api_keys.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateApiKeys extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->unsignedInteger('user')->after('id');\n            $table->text('memo')->after('allowed_ips')->nullable();\n            $table->timestamp('expires_at')->after('memo')->nullable();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropColumn('user');\n            $table->dropColumn('memo');\n            $table->dropColumn('expires_at');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_181719_update_misnamed_bungee.php",
    "content": "<?php\n\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateMisnamedBungee extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::table('service_variables')->select('env_variable')->where('env_variable', 'BUNGE_VERSION')->update([\n            'env_variable' => 'BUNGEE_VERSION',\n        ]);\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_193810_add_foreign_keys_servers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignKeysServers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->integer('node', false, true)->change();\n            $table->integer('owner', false, true)->change();\n            $table->integer('allocation', false, true)->change();\n            $table->integer('service', false, true)->change();\n            $table->integer('option', false, true)->change();\n\n            $table->foreign('node')->references('id')->on('nodes');\n            $table->foreign('owner')->references('id')->on('users');\n            $table->foreign('allocation')->references('id')->on('allocations');\n            $table->foreign('service')->references('id')->on('services');\n            $table->foreign('option')->references('id')->on('service_options');\n\n            $table->softDeletes();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['node']);\n            $table->dropIndex(['node']);\n\n            $table->dropForeign(['owner']);\n            $table->dropIndex(['owner']);\n\n            $table->dropForeign(['allocation']);\n            $table->dropIndex(['allocation']);\n\n            $table->dropForeign(['service']);\n            $table->dropIndex(['service']);\n\n            $table->dropForeign(['option']);\n            $table->dropIndex(['option']);\n\n            $table->dropColumn('deleted_at');\n\n            $table->mediumInteger('node', false, true)->change();\n            $table->mediumInteger('owner', false, true)->change();\n            $table->mediumInteger('allocation', false, true)->change();\n            $table->mediumInteger('service', false, true)->change();\n            $table->mediumInteger('option', false, true)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_201624_add_foreign_allocations.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignAllocations extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->integer('assigned_to', false, true)->nullable()->change();\n            $table->integer('node', false, true)->nullable(false)->change();\n            $table->foreign('assigned_to')->references('id')->on('servers');\n            $table->foreign('node')->references('id')->on('nodes');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->dropForeign(['assigned_to']);\n            $table->dropIndex(['assigned_to']);\n\n            $table->dropForeign(['node']);\n            $table->dropIndex(['node']);\n\n            $table->mediumInteger('assigned_to', false, true)->nullable()->change();\n            $table->mediumInteger('node', false, true)->nullable(false)->change();\n        });\n\n        DB::statement('ALTER TABLE allocations\n             MODIFY COLUMN assigned_to MEDIUMINT(8) UNSIGNED NULL,\n             MODIFY COLUMN node MEDIUMINT(8) UNSIGNED NOT NULL\n         ');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_202222_add_foreign_api_keys.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignApiKeys extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->foreign('user')->references('id')->on('users');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropForeign(['user']);\n            $table->dropIndex(['user']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_202703_add_foreign_api_permissions.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignApiPermissions extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('api_permissions', function (Blueprint $table) {\n            $table->integer('key_id', false, true)->nullable(false)->change();\n            $table->foreign('key_id')->references('id')->on('api_keys');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('api_permissions', function (Blueprint $table) {\n            $table->dropForeign(['key_id']);\n            $table->dropIndex(['key_id']);\n\n            $table->mediumInteger('key_id', false, true)->nullable(false)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_202953_add_foreign_database_servers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignDatabaseServers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('database_servers', function (Blueprint $table) {\n            $table->foreign('linked_node')->references('id')->on('nodes');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('database_servers', function (Blueprint $table) {\n            $table->dropForeign(['linked_node']);\n            $table->dropIndex(['linked_node']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_203105_add_foreign_databases.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignDatabases extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->foreign('server_id')->references('id')->on('servers');\n            $table->foreign('db_server')->references('id')->on('database_servers');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->dropForeign(['server_id']);\n            $table->dropIndex(['server_id']);\n\n            $table->dropForeign(['db_server']);\n            $table->dropIndex(['db_server']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_203335_add_foreign_nodes.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignNodes extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->integer('location', false, true)->nullable(false)->change();\n            $table->foreign('location')->references('id')->on('locations');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->dropForeign(['location']);\n            $table->dropIndex(['location']);\n\n            $table->mediumInteger('location', false, true)->nullable(false)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_203522_add_foreign_permissions.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignPermissions extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('permissions', function (Blueprint $table) {\n            $table->foreign('user_id')->references('id')->on('users');\n            $table->foreign('server_id')->references('id')->on('servers');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('permissions', function (Blueprint $table) {\n            $table->dropForeign(['user_id']);\n            $table->dropIndex(['user_id']);\n\n            $table->dropForeign(['server_id']);\n            $table->dropIndex(['server_id']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_203857_add_foreign_server_variables.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignServerVariables extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('server_variables', function (Blueprint $table) {\n            $table->integer('server_id', false, true)->nullable()->change();\n            $table->integer('variable_id', false, true)->nullable(false)->change();\n            $table->foreign('server_id')->references('id')->on('servers');\n            $table->foreign('variable_id')->references('id')->on('service_variables');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('server_variables', function (Blueprint $table) {\n            $table->dropForeign(['server_id']);\n            $table->dropForeign(['variable_id']);\n            $table->mediumInteger('server_id', false, true)->nullable()->change();\n            $table->mediumInteger('variable_id', false, true)->nullable(false)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_204157_add_foreign_service_options.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignServiceOptions extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->integer('parent_service', false, true)->change();\n            $table->foreign('parent_service')->references('id')->on('services');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropForeign(['parent_service']);\n            $table->dropIndex(['parent_service']);\n\n            $table->mediumInteger('parent_service', false, true)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_204321_add_foreign_service_variables.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignServiceVariables extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->integer('option_id', false, true)->change();\n            $table->foreign('option_id')->references('id')->on('service_options');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n            $table->dropIndex(['option_id']);\n\n            $table->mediumInteger('option_id', false, true)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_204454_add_foreign_subusers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignSubusers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('subusers', function (Blueprint $table) {\n            $table->foreign('user_id')->references('id')->on('users');\n            $table->foreign('server_id')->references('id')->on('servers');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('subusers', function (Blueprint $table) {\n            $table->dropForeign(['user_id']);\n            $table->dropIndex(['user_id']);\n\n            $table->dropForeign(['server_id']);\n            $table->dropIndex(['server_id']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_10_23_204610_add_foreign_tasks.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignTasks extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('tasks', function (Blueprint $table) {\n            $table->foreign('server')->references('id')->on('servers');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('tasks', function (Blueprint $table) {\n            $table->dropForeign(['server']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_11_04_000949_add_ark_service_option_fixed.php",
    "content": "<?php\n\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddArkServiceOptionFixed extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::transaction(function () {\n            $service = DB::table('services')->select('id')->where('author', 'ptrdctyl-v040-11e6-8b77-86f30ca893d3')->where('name', 'Source Engine')->first();\n\n            // No SRCDS Service, Skipping\n            if (!$service) {\n                return;\n            }\n\n            // Already have this service option installed.\n            if (DB::table('service_options')->select('id')->where('name', 'Ark: Survival Evolved')->where('parent_service', $service->id)->first()) {\n                return;\n            }\n\n            $oid = DB::table('service_options')->insertGetId([\n                'parent_service' => $service->id,\n                'name' => 'Ark: Survival Evolved',\n                'description' => 'As a man or woman stranded, naked, freezing, and starving on the unforgiving shores of a mysterious island called ARK, use your skill and cunning to kill or tame and ride the plethora of leviathan dinosaurs and other primeval creatures roaming the land. Hunt, harvest resources, craft items, grow crops, research technologies, and build shelters to withstand the elements and store valuables, all while teaming up with (or preying upon) hundreds of other players to survive, dominate... and escape! — Gamepedia: ARK',\n                'tag' => 'ark',\n                'docker_image' => 'quay.io/pterodactyl/srcds:ark',\n                'executable' => './ShooterGameServer',\n                'startup' => 'TheIsland?listen?ServerPassword={{ARK_PASSWORD}}?ServerAdminPassword={{ARK_ADMIN_PASSWORD}}?Port={{SERVER_PORT}}?MaxPlayers={{SERVER_MAX_PLAYERS}}',\n            ]);\n\n            DB::table('service_variables')->insert([\n                'option_id' => $oid,\n                'name' => 'Server Password',\n                'description' => 'If specified, players must provide this password to join the server.',\n                'env_variable' => 'ARK_PASSWORD',\n                'default_value' => '',\n                'user_viewable' => 1,\n                'user_editable' => 1,\n                'required' => 0,\n                'regex' => '/^(\\w\\.*)$/',\n            ]);\n\n            DB::table('service_variables')->insert([\n                'option_id' => $oid,\n                'name' => 'Admin Password',\n                'description' => 'If specified, players must provide this password (via the in-game console) to gain access to administrator commands on the server.',\n                'env_variable' => 'ARK_ADMIN_PASSWORD',\n                'default_value' => '',\n                'user_viewable' => 1,\n                'user_editable' => 1,\n                'required' => 0,\n                'regex' => '/^(\\w\\.*)$/',\n            ]);\n\n            DB::table('service_variables')->insert([\n                'option_id' => $oid,\n                'name' => 'Maximum Players',\n                'description' => 'Specifies the maximum number of players that can play on the server simultaneously.',\n                'env_variable' => 'SERVER_MAX_PLAYERS',\n                'default_value' => 20,\n                'user_viewable' => 1,\n                'user_editable' => 1,\n                'required' => 1,\n                'regex' => '/^(\\d{1,4})$/',\n            ]);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        DB::transaction(function () {\n            $service = DB::table('services')->select('id')->where('author', 'ptrdctyl-v040-11e6-8b77-86f30ca893d3')->where('name', 'Source Engine')->first();\n\n            if ($service) {\n                $option = DB::table('service_options')->where('parent_service', $service->id)->where('tag', 'ark')->first();\n\n                if ($option) {\n                    $variables = DB::table('service_variables')->where('option_id', $option->id)->delete();\n                }\n            }\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_11_11_220649_add_pack_support.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddPackSupport extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('service_packs', function (Blueprint $table) {\n            $table->increments('id');\n            $table->unsignedInteger('option');\n            $table->char('uuid', 36)->unique();\n            $table->string('name');\n            $table->string('version');\n            $table->text('description')->nullable();\n            $table->boolean('selectable')->default(true);\n            $table->boolean('visible')->default(true);\n            $table->timestamps();\n\n            $table->foreign('option')->references('id')->on('service_options');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::drop('service_packs');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_11_11_231731_set_service_name_unique.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass SetServiceNameUnique extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->unique('name');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->dropUnique('services_name_unique');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_11_27_142519_add_pack_column.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddPackColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->unsignedInteger('pack')->nullable()->after('option');\n\n            $table->foreign('pack')->references('id')->on('service_packs');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['pack']);\n            $table->dropColumn('pack');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_12_01_173018_add_configurable_upload_limit.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddConfigurableUploadLimit extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->unsignedInteger('upload_size')->after('disk_overallocate')->default(100);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->dropColumn('upload_size');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2016_12_02_185206_correct_service_variables.php",
    "content": "<?php\n\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CorrectServiceVariables extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::transaction(function () {\n            // Modify Default Spigot Startup Line\n            DB::table('service_options')->where([\n                ['name', 'Spigot'],\n                ['tag', 'spigot'],\n                ['startup', '-Xms128M -Xmx{{SERVER_MEMORY}}M -Djline.terminal=jline.UnsupportedTerminal -jar {{SERVER_JARFILE}}'],\n            ])->update([\n                'startup' => null,\n            ]);\n\n            // Correct Spigot Version Checking\n            DB::table('service_variables')->where([\n                ['name', 'Spigot Version'],\n                ['env_variable', 'DL_VERSION'],\n                ['default_value', 'latest'],\n                ['regex', '/^(latest|[a-zA-Z0-9_\\.-]{5,6})$/'],\n            ])->update([\n                'regex' => '/^(latest|[a-zA-Z0-9_\\.-]{3,7})$/',\n            ]);\n\n            // Correct Vanilla Version Checking (as well as naming)\n            DB::table('service_variables')->where([\n                ['name', 'Server Jar File'],\n                ['env_variable', 'VANILLA_VERSION'],\n                ['default_value', 'latest'],\n                ['regex', '/^(latest|[a-zA-Z0-9_\\.-]{5,6})$/'],\n            ])->update([\n                'name' => 'Server Version',\n                'regex' => '/^(latest|[a-zA-Z0-9_\\.-]{3,7})$/',\n            ]);\n\n            // Update Sponge Version Checking and Update Default Version\n            DB::table('service_variables')->where([\n                ['name', 'Sponge Version'],\n                ['env_variable', 'SPONGE_VERSION'],\n                ['default_value', '1.8.9-4.2.0-BETA-351'],\n                ['regex', '/^(.*)$/'],\n            ])->update([\n                'default_value' => '1.10.2-5.1.0-BETA-359',\n                'regex' => '/^([a-zA-Z0-9.\\-_]+)$/',\n            ]);\n\n            // Update Bungeecord Version Checking\n            DB::table('service_variables')->where([\n                ['name', 'Bungeecord Version'],\n                ['env_variable', 'BUNGEE_VERSION'],\n                ['default_value', 'latest'],\n                ['regex', '/^(latest|[\\d]{3,5})$/'],\n            ])->update([\n                'regex' => '/^(latest|[\\d]{1,6})$/',\n            ]);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        // do nothing\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_01_03_150436_fix_misnamed_option_tag.php",
    "content": "<?php\n\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass FixMisnamedOptionTag extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::transaction(function () {\n            DB::table('service_options')->where([\n                ['name', 'Sponge (SpongeVanilla)'],\n                ['tag', 'spigot'],\n                ['docker_image', 'quay.io/pterodactyl/minecraft:sponge'],\n            ])->update([\n                'tag' => 'sponge',\n            ]);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        DB::table('service_options')->where([\n            ['name', 'Sponge (SpongeVanilla)'],\n            ['tag', 'sponge'],\n            ['docker_image', 'quay.io/pterodactyl/minecraft:sponge'],\n        ])->update([\n            'tag' => 'spigot',\n        ]);\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_01_07_154228_create_node_configuration_tokens_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateNodeConfigurationTokensTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('node_configuration_tokens', function (Blueprint $table) {\n            $table->increments('id');\n            $table->char('token', 32);\n            $table->timestamp('expires_at');\n            $table->integer('node')->unsigned();\n            $table->foreign('node')->references('id')->on('nodes');\n            $table->timestamps();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('node_configuration_tokens');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_01_12_135449_add_more_user_data.php",
    "content": "<?php\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddMoreUserData extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->string('name_first')->after('email')->nullable();\n            $table->string('name_last')->after('name_first')->nullable();\n            $table->string('username')->after('uuid');\n            $table->boolean('gravatar')->after('totp_secret')->default(true);\n        });\n\n        DB::transaction(function () {\n            foreach (User::all() as &$user) {\n                $user->username = $user->email;\n                $user->save();\n            }\n        });\n\n        Schema::table('users', function (Blueprint $table) {\n            $table->string('username')->unique()->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->dropColumn('name_first');\n            $table->dropColumn('name_last');\n            $table->dropColumn('username');\n            $table->dropColumn('gravatar');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_02_02_175548_UpdateColumnNames.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateColumnNames extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['node']);\n            $table->dropForeign(['owner']);\n            $table->dropForeign(['allocation']);\n            $table->dropForeign(['service']);\n            $table->dropForeign(['option']);\n            $table->dropForeign(['pack']);\n\n            $table->renameColumn('node', 'node_id');\n            $table->renameColumn('owner', 'owner_id');\n            $table->renameColumn('allocation', 'allocation_id');\n            $table->renameColumn('service', 'service_id');\n            $table->renameColumn('option', 'option_id');\n            $table->renameColumn('pack', 'pack_id');\n\n            $table->foreign('node_id')->references('id')->on('nodes');\n            $table->foreign('owner_id')->references('id')->on('users');\n            $table->foreign('allocation_id')->references('id')->on('allocations');\n            $table->foreign('service_id')->references('id')->on('services');\n            $table->foreign('option_id')->references('id')->on('service_options');\n\n            // Pack ID was forgotten until multiple releases later, therefore it is\n            // contained in '2017_03_18_204953_AddForeignKeyToPacks'\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['node_id', 'owner_id', 'allocation_id', 'service_id', 'option_id']);\n\n            $table->renameColumn('node_id', 'node');\n            $table->renameColumn('owner_id', 'owner');\n            $table->renameColumn('allocation_id', 'allocation');\n            $table->renameColumn('service_id', 'service');\n            $table->renameColumn('option_id', 'option');\n            $table->renameColumn('pack_id', 'pack');\n\n            $table->foreign('node')->references('id')->on('nodes');\n            $table->foreign('owner')->references('id')->on('users');\n            $table->foreign('allocation')->references('id')->on('allocations');\n            $table->foreign('service')->references('id')->on('services');\n            $table->foreign('option')->references('id')->on('service_options');\n            $table->foreign('pack')->references('id')->on('service_packs');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_02_03_140948_UpdateNodesTable.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateNodesTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->dropForeign(['location']);\n\n            $table->renameColumn('location', 'location_id');\n            $table->foreign('location_id')->references('id')->on('locations');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->dropForeign(['location_id']);\n\n            $table->renameColumn('location_id', 'location');\n            $table->foreign('location')->references('id')->on('locations');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_02_03_155554_RenameColumns.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RenameColumns extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->dropForeign(['node']);\n            $table->dropForeign(['assigned_to']);\n\n            $table->renameColumn('node', 'node_id');\n            $table->renameColumn('assigned_to', 'server_id');\n            $table->foreign('node_id')->references('id')->on('nodes');\n            $table->foreign('server_id')->references('id')->on('servers');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->dropForeign(['node_id']);\n            $table->dropForeign(['server_id']);\n            $table->dropIndex(['node_id']);\n            $table->dropIndex(['server_id']);\n\n            $table->renameColumn('node_id', 'node');\n            $table->renameColumn('server_id', 'assigned_to');\n            $table->foreign('node')->references('id')->on('nodes');\n            $table->foreign('assigned_to')->references('id')->on('servers');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_02_05_164123_AdjustColumnNames.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AdjustColumnNames extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropForeign(['parent_service']);\n\n            $table->renameColumn('parent_service', 'service_id');\n            $table->foreign('service_id')->references('id')->on('services');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropForeign(['service_id']);\n            $table->dropIndex(['service_id']);\n\n            $table->renameColumn('service_id', 'parent_service');\n            $table->foreign('parent_service')->references('id')->on('services');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_02_05_164516_AdjustColumnNamesForServicePacks.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AdjustColumnNamesForServicePacks extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_packs', function (Blueprint $table) {\n            $table->dropForeign(['option']);\n\n            $table->renameColumn('option', 'option_id');\n            $table->foreign('option_id')->references('id')->on('service_options');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_packs', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n            $table->dropIndex(['option_id']);\n\n            $table->renameColumn('option_id', 'option');\n            $table->foreign('option')->references('id')->on('service_options');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_02_09_174834_SetupPermissionsPivotTable.php",
    "content": "<?php\n\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass SetupPermissionsPivotTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('permissions', function (Blueprint $table) {\n            $table->unsignedInteger('subuser_id')->after('id');\n        });\n\n        DB::transaction(function () {\n            foreach (Subuser::all() as &$subuser) {\n                Permission::query()->where('user_id', $subuser->user_id)->where('server_id', $subuser->server_id)->update([\n                    'subuser_id' => $subuser->id,\n                ]);\n            }\n        });\n\n        Schema::table('permissions', function (Blueprint $table) {\n            $table->dropForeign(['server_id']);\n            $table->dropForeign(['user_id']);\n\n            $table->dropColumn('server_id');\n            $table->dropColumn('user_id');\n            $table->dropColumn('created_at');\n            $table->dropColumn('updated_at');\n            $table->foreign('subuser_id')->references('id')->on('subusers');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('permissions', function (Blueprint $table) {\n            $table->unsignedInteger('server_id')->after('subuser_id');\n            $table->unsignedInteger('user_id')->after('server_id');\n            $table->timestamps();\n        });\n\n        DB::transaction(function () {\n            foreach (Subuser::all() as &$subuser) {\n                Permission::query()->where('subuser_id', $subuser->id)->update([\n                    'user_id' => $subuser->user_id,\n                    'server_id' => $subuser->server_id,\n                ]);\n            }\n        });\n\n        Schema::table('permissions', function (Blueprint $table) {\n            $table->dropForeign(['subuser_id']);\n            $table->dropIndex(['subuser_id']);\n            $table->dropColumn('subuser_id');\n\n            $table->foreign('server_id')->references('id')->on('servers');\n            $table->foreign('user_id')->references('id')->on('users');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_02_10_171858_UpdateAPIKeyColumnNames.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateAPIKeyColumnNames extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropForeign(['user']);\n\n            $table->renameColumn('user', 'user_id');\n            $table->foreign('user_id')->references('id')->on('users');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropForeign(['user_id']);\n\n            $table->renameColumn('user_id', 'user');\n            $table->foreign('user')->references('id')->on('users');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_03_224254_UpdateNodeConfigTokensColumns.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateNodeConfigTokensColumns extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('node_configuration_tokens', function (Blueprint $table) {\n            $table->dropForeign(['node']);\n            $table->dropColumn('expires_at');\n            $table->renameColumn('node', 'node_id');\n\n            $table->foreign('node_id')->references('id')->on('nodes');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('node_configuration_tokens', function (Blueprint $table) {\n            $table->dropForeign(['node_id']);\n            $table->renameColumn('node_id', 'node');\n            $table->timestamp('expires_at')->after('token');\n\n            $table->foreign('node')->references('id')->on('nodes');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_05_212803_DeleteServiceExecutableOption.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DeleteServiceExecutableOption extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->renameColumn('file', 'folder');\n            $table->dropColumn('executable');\n            $table->text('description')->nullable()->change();\n            $table->text('startup')->nullable()->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->string('executable')->after('folder');\n            $table->renameColumn('folder', 'file');\n            $table->text('description')->nullable(false)->change();\n            $table->text('startup')->nullable(false)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_10_162934_AddNewServiceOptionsColumns.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddNewServiceOptionsColumns extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropColumn('executable');\n\n            $table->unsignedInteger('config_from')->nullable()->after('docker_image');\n            $table->string('config_stop')->nullable()->after('docker_image');\n            $table->text('config_logs')->nullable()->after('docker_image');\n            $table->text('config_startup')->nullable()->after('docker_image');\n            $table->text('config_files')->nullable()->after('docker_image');\n\n            $table->foreign('config_from')->references('id')->on('service_options');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropForeign(['config_from']);\n\n            $table->dropColumn('config_from');\n            $table->dropColumn('config_stop');\n            $table->dropColumn('config_logs');\n            $table->dropColumn('config_startup');\n            $table->dropColumn('config_files');\n\n            $table->string('executable')->after('docker_image')->nullable();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_10_173607_MigrateToNewServiceSystem.php",
    "content": "<?php\n\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass MigrateToNewServiceSystem extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::transaction(function () {\n            $service = DB::table('services')->where('author', config('pterodactyl.service.core'))->where('folder', 'srcds')->first();\n            if (!$service) {\n                return;\n            }\n\n            $options = DB::table('service_options')->where('service_id', $service->id)->get();\n            $options->each(function ($item) {\n                if ($item->tag === 'srcds' && $item->name === 'Insurgency') {\n                    $item->tag = 'insurgency';\n                } elseif ($item->tag === 'srcds' && $item->name === 'Team Fortress 2') {\n                    $item->tag = 'tf2';\n                } elseif ($item->tag === 'srcds' && $item->name === 'Custom Source Engine Game') {\n                    $item->tag = 'source';\n                }\n                $item->save();\n            });\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        // Not doing reversals right now...\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_11_215455_ChangeServiceVariablesValidationRules.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ChangeServiceVariablesValidationRules extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->renameColumn('regex', 'rules');\n        });\n\n        DB::transaction(function () {\n            foreach (DB::table('service_variables')->get() as $variable) {\n                $variable->rules = ($variable->required) ? 'required|regex:' . $variable->rules : 'regex:' . $variable->rules;\n                $variable->save();\n            }\n        });\n\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->dropColumn('required');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->renameColumn('rules', 'regex');\n            $table->boolean('required')->default(true)->before('regex');\n        });\n\n        DB::transaction(function () {\n            foreach (DB::table('service_variables')->get() as $variable) {\n                $variable->regex = str_replace(['required|regex:', 'regex:'], '', $variable->regex);\n                $variable->save();\n            }\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_12_150648_MoveFunctionsFromFileToDatabase.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass MoveFunctionsFromFileToDatabase extends Migration\n{\n    private $default = <<<'EOF'\n'use strict';\n\n/**\n * Pterodactyl - Daemon\n * Copyright (c) 2015 - 2017 Dane Everitt <dane@daneeveritt.com>\n *\n * Permission is hereby granted, free of charge, to any person obtaining a copy\n * of this software and associated documentation files (the \"Software\"), to deal\n * in the Software without restriction, including without limitation the rights\n * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n * copies of the Software, and to permit persons to whom the Software is\n * furnished to do so, subject to the following conditions:\n *\n * The above copyright notice and this permission notice shall be included in all\n * copies or substantial portions of the Software.\n *\n * THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n * SOFTWARE.\n */\nconst rfr = require('rfr');\nconst _ = require('lodash');\n\nconst Core = rfr('src/services/index.js');\n\nclass Service extends Core {}\n\nmodule.exports = Service;\nEOF;\n\n    private $default_mc = <<<'EOF'\n'use strict';\n\n/**\n * Pterodactyl - Daemon\n * Copyright (c) 2015 - 2017 Dane Everitt <dane@daneeveritt.com>\n *\n * Permission is hereby granted, free of charge, to any person obtaining a copy\n * of this software and associated documentation files (the \"Software\"), to deal\n * in the Software without restriction, including without limitation the rights\n * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n * copies of the Software, and to permit persons to whom the Software is\n * furnished to do so, subject to the following conditions:\n *\n * The above copyright notice and this permission notice shall be included in all\n * copies or substantial portions of the Software.\n *\n * THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n * SOFTWARE.\n */\nconst rfr = require('rfr');\nconst _ = require('lodash');\n\nconst Core = rfr('src/services/index.js');\n\nclass Service extends Core {\n    onConsole(data) {\n        // Hide the output spam from Bungeecord getting pinged.\n        if (_.endsWith(data, '<-> InitialHandler has connected')) return;\n        return super.onConsole(data);\n    }\n}\n\nmodule.exports = Service;\nEOF;\n\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->text('index_file')->after('startup');\n        });\n\n        DB::transaction(function () {\n            DB::table('services')->where('author', 'ptrdctyl-v040-11e6-8b77-86f30ca893d3')->where('folder', '!=', 'minecraft')->update([\n                'index_file' => $this->default,\n            ]);\n\n            DB::table('services')->where('author', 'ptrdctyl-v040-11e6-8b77-86f30ca893d3')->where('folder', 'minecraft')->update([\n                'index_file' => $this->default_mc,\n            ]);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->dropColumn('index_file');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_14_175631_RenameServicePacksToSingluarPacks.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RenameServicePacksToSingluarPacks extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_packs', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n        });\n\n        Schema::rename('service_packs', 'packs');\n\n        Schema::table('packs', function (Blueprint $table) {\n            $table->foreign('option_id')->references('id')->on('service_options');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('packs', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n        });\n\n        Schema::rename('packs', 'service_packs');\n\n        Schema::table('service_packs', function (Blueprint $table) {\n            $table->foreign('option_id')->references('id')->on('service_options');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_14_200326_AddLockedStatusToTable.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddLockedStatusToTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('packs', function (Blueprint $table) {\n            $table->boolean('locked')->default(false)->after('visible');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('packs', function (Blueprint $table) {\n            $table->dropColumn('locked');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_16_181109_ReOrganizeDatabaseServersToDatabaseHost.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ReOrganizeDatabaseServersToDatabaseHost extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('database_servers', function (Blueprint $table) {\n            $table->dropForeign(['linked_node']);\n        });\n\n        Schema::rename('database_servers', 'database_hosts');\n\n        Schema::table('database_hosts', function (Blueprint $table) {\n            $table->renameColumn('linked_node', 'node_id');\n\n            $table->foreign('node_id')->references('id')->on('nodes');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('database_hosts', function (Blueprint $table) {\n            $table->dropForeign(['node_id']);\n        });\n\n        Schema::rename('database_hosts', 'database_servers');\n\n        Schema::table('database_servers', function (Blueprint $table) {\n            $table->renameColumn('node_id', 'linked_node');\n\n            $table->foreign('linked_node')->references('id')->on('nodes');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_16_181515_CleanupDatabasesDatabase.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CleanupDatabasesDatabase extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->dropForeign(['db_server']);\n\n            $table->renameColumn('db_server', 'database_host_id');\n\n            $table->foreign('database_host_id')->references('id')->on('database_hosts');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->dropForeign(['database_host_id']);\n\n            $table->renameColumn('database_host_id', 'db_server');\n\n            $table->foreign('db_server')->references('id')->on('database_hosts');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_18_204953_AddForeignKeyToPacks.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignKeyToPacks extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->foreign('pack_id')->references('id')->on('packs');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['pack_id']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_03_31_221948_AddServerDescriptionColumn.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddServerDescriptionColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->text('description')->after('name');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('description');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_04_02_163232_DropDeletedAtColumnFromServers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DropDeletedAtColumnFromServers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('deleted_at');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->timestamp('deleted_at')->nullable();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_04_15_125021_UpgradeTaskSystem.php",
    "content": "<?php\n\nuse Pterodactyl\\Models\\Task;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpgradeTaskSystem extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('tasks', function (Blueprint $table) {\n            $table->dropForeign(['server']);\n\n            $table->renameColumn('server', 'server_id');\n            $table->unsignedInteger('user_id')->nullable()->after('id');\n\n            $table->foreign('server_id')->references('id')->on('servers');\n            $table->foreign('user_id')->references('id')->on('users');\n        });\n\n        DB::transaction(function () {\n            foreach (Task::all() as $task) {\n                $task->user_id = $task->server->owner_id;\n                $task->save();\n            }\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('tasks', function (Blueprint $table) {\n            //            $table->dropForeign(['server_id']);\n            //            $table->dropForeign(['user_id']);\n\n            $table->renameColumn('server_id', 'server');\n            $table->dropColumn('user_id');\n\n            $table->foreign('server')->references('id')->on('servers');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_04_20_171943_AddScriptsToServiceOptions.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddScriptsToServiceOptions extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->text('script_install')->after('startup')->nullable();\n            $table->boolean('script_is_privileged')->default(true)->after('startup');\n            $table->string('script_entry')->default('ash')->after('startup');\n            $table->string('script_container')->default('alpine:3.4')->after('startup');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropColumn('script_install');\n            $table->dropColumn('script_is_privileged');\n            $table->dropColumn('script_entry');\n            $table->dropColumn('script_container');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_04_21_151432_AddServiceScriptTrackingToServers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddServiceScriptTrackingToServers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->boolean('skip_scripts')->default(false)->after('description');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('skip_scripts');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_04_27_145300_AddCopyScriptFromColumn.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddCopyScriptFromColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->unsignedInteger('copy_script_from')->nullable()->after('script_container');\n\n            $table->foreign('copy_script_from')->references('id')->on('service_options');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropForeign(['copy_script_from']);\n            $table->dropColumn('copy_script_from');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_04_27_223629_AddAbilityToDefineConnectionOverSSLWithDaemonBehindProxy.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddAbilityToDefineConnectionOverSSLWithDaemonBehindProxy extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->boolean('behind_proxy')->after('scheme')->default(false);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->dropColumn('behind_proxy');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_05_01_141528_DeleteDownloadTable.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DeleteDownloadTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::dropIfExists('downloads');\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::create('downloads', function (Blueprint $table) {\n            $table->increments('id');\n            $table->char('token', 36)->unique();\n            $table->char('server', 36);\n            $table->text('path');\n            $table->timestamps();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_05_01_141559_DeleteNodeConfigurationTable.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DeleteNodeConfigurationTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::dropIfExists('node_configuration_tokens');\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::create('node_configuration_tokens', function (Blueprint $table) {\n            $table->increments('id');\n            $table->char('token', 32);\n            $table->unsignedInteger('node_id');\n            $table->timestamps();\n        });\n\n        Schema::table('node_configuration_tokens', function (Blueprint $table) {\n            $table->foreign('node_id')->references('id')->on('nodes');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_06_10_152951_add_external_id_to_users.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddExternalIdToUsers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->unsignedInteger('external_id')->after('id')->nullable()->unique();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->dropColumn('external_id');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_06_25_133923_ChangeForeignKeyToBeOnCascadeDelete.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ChangeForeignKeyToBeOnCascadeDelete extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('api_permissions', function (Blueprint $table) {\n            $table->dropForeign(['key_id']);\n\n            $table->foreign('key_id')->references('id')->on('api_keys')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('api_permissions', function (Blueprint $table) {\n            $table->dropForeign(['key_id']);\n\n            $table->foreign('key_id')->references('id')->on('api_keys');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_07_08_152806_ChangeUserPermissionsToDeleteOnUserDeletion.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ChangeUserPermissionsToDeleteOnUserDeletion extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('permissions', function (Blueprint $table) {\n            $table->dropForeign(['subuser_id']);\n\n            $table->foreign('subuser_id')->references('id')->on('subusers')->onDelete('cascade');\n        });\n\n        Schema::table('subusers', function (Blueprint $table) {\n            $table->dropForeign(['user_id']);\n            $table->dropForeign(['server_id']);\n\n            $table->foreign('user_id')->references('id')->on('users')->onDelete('cascade');\n            $table->foreign('server_id')->references('id')->on('servers')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('subusers', function (Blueprint $table) {\n            $table->dropForeign(['user_id']);\n            $table->dropForeign(['server_id']);\n\n            $table->foreign('user_id')->references('id')->on('users');\n            $table->foreign('server_id')->references('id')->on('servers');\n        });\n\n        Schema::table('permissions', function (Blueprint $table) {\n            $table->dropForeign(['subuser_id']);\n\n            $table->foreign('subuser_id')->references('id')->on('subusers');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_07_08_154416_SetAllocationToReferenceNullOnServerDelete.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass SetAllocationToReferenceNullOnServerDelete extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->dropForeign(['server_id']);\n\n            $table->foreign('server_id')->references('id')->on('servers')->onDelete('set null');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->dropForeign(['server_id']);\n\n            $table->foreign('server_id')->references('id')->on('servers');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_07_08_154650_CascadeDeletionWhenAServerOrVariableIsDeleted.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CascadeDeletionWhenAServerOrVariableIsDeleted extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('server_variables', function (Blueprint $table) {\n            $table->dropForeign(['server_id']);\n            $table->dropForeign(['variable_id']);\n\n            $table->foreign('server_id')->references('id')->on('servers')->onDelete('cascade');\n            $table->foreign('variable_id')->references('id')->on('service_variables')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('server_variables', function (Blueprint $table) {\n            $table->dropForeign(['server_id']);\n            $table->dropForeign(['variable_id']);\n\n            $table->foreign('server_id')->references('id')->on('servers');\n            $table->foreign('variable_id')->references('id')->on('service_variables');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_07_24_194433_DeleteTaskWhenParentServerIsDeleted.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DeleteTaskWhenParentServerIsDeleted extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('tasks', function (Blueprint $table) {\n            $table->dropForeign(['server_id']);\n\n            $table->foreign('server_id')->references('id')->on('servers')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_08_05_115800_CascadeNullValuesForDatabaseHostWhenNodeIsDeleted.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CascadeNullValuesForDatabaseHostWhenNodeIsDeleted extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('database_hosts', function (Blueprint $table) {\n            $table->dropForeign(['node_id']);\n            $table->foreign('node_id')->references('id')->on('nodes')->onDelete('set null');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('database_hosts', function (Blueprint $table) {\n            $table->dropForeign(['node_id']);\n            $table->foreign('node_id')->references('id')->on('nodes');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_08_05_144104_AllowNegativeValuesForOverallocation.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AllowNegativeValuesForOverallocation extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->integer('disk_overallocate')->default(0)->nullable(false)->change();\n            $table->integer('memory_overallocate')->default(0)->nullable(false)->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            DB::statement('ALTER TABLE nodes MODIFY disk_overallocate MEDIUMINT UNSIGNED NULL,\n                                             MODIFY memory_overallocate MEDIUMINT UNSIGNED NULL');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_08_05_174811_SetAllocationUnqiueUsingMultipleFields.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass SetAllocationUnqiueUsingMultipleFields extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->unique(['node_id', 'ip', 'port']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->dropForeign(['node_id']);\n            $table->dropUnique(['node_id', 'ip', 'port']);\n            $table->foreign('node_id')->references('id')->on('nodes');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_08_15_214555_CascadeDeletionWhenAParentServiceIsDeleted.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CascadeDeletionWhenAParentServiceIsDeleted extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropForeign(['service_id']);\n\n            $table->foreign('service_id')->references('id')->on('services')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropForeign(['service_id']);\n\n            $table->foreign('service_id')->references('id')->on('services');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_08_18_215428_RemovePackWhenParentServiceOptionIsDeleted.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RemovePackWhenParentServiceOptionIsDeleted extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('packs', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n\n            $table->foreign('option_id')->references('id')->on('service_options')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('packs', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n\n            $table->foreign('option_id')->references('id')->on('service_options');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_09_10_225749_RenameTasksTableForStructureRefactor.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RenameTasksTableForStructureRefactor extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::rename('tasks', 'tasks_old');\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::rename('tasks_old', 'tasks');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_09_10_225941_CreateSchedulesTable.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateSchedulesTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('schedules', function (Blueprint $table) {\n            $table->increments('id');\n            $table->unsignedInteger('server_id');\n            $table->string('name')->nullable();\n            $table->string('cron_day_of_week');\n            $table->string('cron_day_of_month');\n            $table->string('cron_hour');\n            $table->string('cron_minute');\n            $table->boolean('is_active');\n            $table->boolean('is_processing');\n            $table->timestamp('last_run_at')->nullable();\n            $table->timestamp('next_run_at')->nullable();\n            $table->timestamps();\n\n            $table->foreign('server_id')->references('id')->on('servers')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('schedules');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_09_10_230309_CreateNewTasksTableForSchedules.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateNewTasksTableForSchedules extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('tasks', function (Blueprint $table) {\n            $table->increments('id');\n            $table->unsignedInteger('schedule_id');\n            $table->unsignedInteger('sequence_id');\n            $table->string('action');\n            $table->text('payload');\n            $table->unsignedInteger('time_offset');\n            $table->boolean('is_queued');\n            $table->timestamps();\n\n            $table->index(['schedule_id', 'sequence_id']);\n            $table->foreign('schedule_id')->references('id')->on('schedules')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('tasks');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_09_11_002938_TransferOldTasksToNewScheduler.php",
    "content": "<?php\n\nuse Carbon\\Carbon;\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass TransferOldTasksToNewScheduler extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::transaction(function () {\n            $tasks = DB::table('tasks_old')->get();\n\n            $tasks->each(function ($task) {\n                $schedule = DB::table('schedules')->insertGetId([\n                    'server_id' => $task->server_id,\n                    'name' => null,\n                    'cron_day_of_week' => $task->day_of_week,\n                    'cron_day_of_month' => $task->day_of_month,\n                    'cron_hour' => $task->hour,\n                    'cron_minute' => $task->minute,\n                    'is_active' => (bool) $task->active,\n                    'is_processing' => false,\n                    'last_run_at' => $task->last_run,\n                    'next_run_at' => $task->next_run,\n                    'created_at' => $task->created_at,\n                    'updated_at' => Carbon::now()->toDateTimeString(),\n                ]);\n\n                DB::table('tasks')->insert([\n                    'schedule_id' => $schedule,\n                    'sequence_id' => 1,\n                    'action' => $task->action,\n                    'payload' => $task->data,\n                    'time_offset' => 0,\n                    'is_queued' => false,\n                    'updated_at' => Carbon::now()->toDateTimeString(),\n                    'created_at' => Carbon::now()->toDateTimeString(),\n                ]);\n\n                DB::table('tasks_old')->delete($task->id);\n            });\n        });\n\n        Schema::dropIfExists('tasks_old');\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::create('tasks_old', function (Blueprint $table) {\n            $table->increments('id');\n            $table->unsignedInteger('user_id')->nullable();\n            $table->unsignedInteger('server_id');\n            $table->tinyInteger('active')->default(1);\n            $table->string('action');\n            $table->text('data');\n            $table->unsignedTinyInteger('queued')->default(0);\n            $table->string('year')->default('*');\n            $table->string('month')->default('*');\n            $table->string('day_of_week')->default('*');\n            $table->string('day_of_month')->default('*');\n            $table->string('minute')->default('*');\n            $table->timestamp('last_run')->nullable();\n            $table->timestamp('next_run');\n            $table->timestamps();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_09_13_211810_UpdateOldPermissionsToPointToNewScheduleSystem.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateOldPermissionsToPointToNewScheduleSystem extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        $permissions = DB::table('permissions')->where('permission', 'like', '%-task%')->get();\n        foreach ($permissions as $record) {\n            $parts = explode('-', $record->permission);\n            if (!in_array(array_get($parts, 1), ['tasks', 'task']) || count($parts) !== 2) {\n                continue;\n            }\n\n            $newPermission = $parts[0] . '-' . str_replace('task', 'schedule', $parts[1]);\n\n            DB::table('permissions')->where('id', '=', $record->id)->update(['permission' => $newPermission]);\n        }\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        $permissions = DB::table('permissions')->where('permission', 'like', '%-schedule%')->get();\n        foreach ($permissions as $record) {\n            $parts = explode('-', $record->permission);\n            if (!in_array(array_get($parts, 1), ['schedules', 'schedule']) || count($parts) !== 2) {\n                continue;\n            }\n\n            $newPermission = $parts[0] . '-' . str_replace('schedule', 'task', $parts[1]);\n\n            DB::table('permissions')->where('id', '=', $record->id)->update(['permission' => $newPermission]);\n        }\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_09_23_170933_CreateDaemonKeysTable.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateDaemonKeysTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('daemon_keys', function (Blueprint $table) {\n            $table->increments('id');\n            $table->unsignedInteger('server_id');\n            $table->unsignedInteger('user_id');\n            $table->string('secret')->unique();\n            $table->timestamp('expires_at');\n            $table->timestamps();\n\n            $table->index(['server_id', 'user_id']);\n            $table->foreign('server_id')->references('id')->on('servers')->onDelete('cascade');\n            $table->foreign('user_id')->references('id')->on('users')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('daemon_keys');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_09_23_173628_RemoveDaemonSecretFromServersTable.php",
    "content": "<?php\n\nuse Carbon\\Carbon;\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\nuse Pterodactyl\\Contracts\\Repository\\DaemonKeyRepositoryInterface;\n\nclass RemoveDaemonSecretFromServersTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        $inserts = [];\n\n        $servers = DB::table('servers')->select('id', 'owner_id')->get();\n        $servers->each(function ($server) use (&$inserts) {\n            $inserts[] = [\n                'user_id' => $server->owner_id,\n                'server_id' => $server->id,\n                'secret' => DaemonKeyRepositoryInterface::INTERNAL_KEY_IDENTIFIER . str_random(40),\n                'expires_at' => Carbon::now()->addMinutes(config('pterodactyl.api.key_expire_time', 720))->toDateTimeString(),\n                'created_at' => Carbon::now()->toDateTimeString(),\n                'updated_at' => Carbon::now()->toDateTimeString(),\n            ];\n        });\n\n        DB::transaction(function () use ($inserts) {\n            DB::table('daemon_keys')->insert($inserts);\n        });\n\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropUnique(['daemonSecret']);\n            $table->dropColumn('daemonSecret');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->char('daemonSecret', 36)->after('startup')->unique();\n        });\n\n        DB::table('daemon_keys')->truncate();\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_09_23_185022_RemoveDaemonSecretFromSubusersTable.php",
    "content": "<?php\n\nuse Carbon\\Carbon;\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\nuse Pterodactyl\\Contracts\\Repository\\DaemonKeyRepositoryInterface;\n\nclass RemoveDaemonSecretFromSubusersTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        $inserts = [];\n        $subusers = DB::table('subusers')->get();\n        $subusers->each(function ($subuser) use (&$inserts) {\n            $inserts[] = [\n                'user_id' => $subuser->user_id,\n                'server_id' => $subuser->server_id,\n                'secret' => DaemonKeyRepositoryInterface::INTERNAL_KEY_IDENTIFIER . str_random(40),\n                'expires_at' => Carbon::now()->addMinutes(config('pterodactyl.api.key_expire_time', 720))->toDateTimeString(),\n                'created_at' => Carbon::now()->toDateTimeString(),\n                'updated_at' => Carbon::now()->toDateTimeString(),\n            ];\n        });\n\n        DB::transaction(function () use ($inserts) {\n            DB::table('daemon_keys')->insert($inserts);\n        });\n\n        Schema::table('subusers', function (Blueprint $table) {\n            $table->dropUnique(['daemonSecret']);\n            $table->dropColumn('daemonSecret');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('subusers', function (Blueprint $table) {\n            $table->char('daemonSecret', 36)->after('server_id');\n        });\n\n        $subusers = DB::table('subusers')->get();\n        $subusers->each(function ($subuser) {\n            DB::table('daemon_keys')->where('user_id', $subuser->user_id)->where('server_id', $subuser->server_id)->delete();\n        });\n\n        Schema::table('subusers', function (Blueprint $table) {\n            $table->unique('daemonSecret');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_10_02_202000_ChangeServicesToUseAMoreUniqueIdentifier.php",
    "content": "<?php\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ChangeServicesToUseAMoreUniqueIdentifier extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->dropUnique(['name']);\n            $table->dropUnique(['file']);\n\n            $table->string('author')->change();\n            $table->char('uuid', 36)->after('id');\n            $table->dropColumn('folder');\n            $table->dropColumn('startup');\n            $table->dropColumn('index_file');\n        });\n\n        DB::table('services')->get(['id', 'author', 'uuid'])->each(function ($service) {\n            DB::table('services')->where('id', $service->id)->update([\n                'author' => ($service->author === 'ptrdctyl-v040-11e6-8b77-86f30ca893d3') ? 'support@pterodactyl.io' : 'unknown@unknown-author.com',\n                'uuid' => Uuid::uuid4()->toString(),\n            ]);\n        });\n\n        Schema::table('services', function (Blueprint $table) {\n            $table->unique('uuid');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('services', function (Blueprint $table) {\n            $table->dropColumn('uuid');\n            $table->string('folder')->nullable();\n            $table->text('startup')->nullable();\n            $table->text('index_file');\n            $table->string('author', 36)->change();\n\n            $table->unique('name');\n            $table->unique('folder', 'services_file_unique');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_10_02_202007_ChangeToABetterUniqueServiceConfiguration.php",
    "content": "<?php\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ChangeToABetterUniqueServiceConfiguration extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->char('uuid', 36)->after('id');\n            $table->string('author')->after('service_id');\n            $table->dropColumn('tag');\n        });\n\n        DB::transaction(function () {\n            DB::table('service_options')->select([\n                'service_options.id',\n                'service_options.uuid',\n                'services.author AS service_author',\n            ])->join('services', 'services.id', '=', 'service_options.service_id')->get()->each(function ($option) {\n                DB::table('service_options')->where('id', $option->id)->update([\n                    'author' => $option->service_author,\n                    'uuid' => Uuid::uuid4()->toString(),\n                ]);\n            });\n        });\n\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->unique('uuid');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropColumn('uuid');\n            $table->dropColumn('author');\n            $table->string('tag');\n        });\n\n        DB::transaction(function () {\n            DB::table('service_options')->select(['id', 'tag'])->get()->each(function ($option) {\n                DB::table('service_options')->where('id', $option->id)->update([\n                    'tag' => str_random(10),\n                ]);\n            });\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_10_03_233202_CascadeDeletionWhenServiceOptionIsDeleted.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CascadeDeletionWhenServiceOptionIsDeleted extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n\n            $table->foreign('option_id')->references('id')->on('service_options')->onDelete('CASCADE');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n\n            $table->foreign('option_id')->references('id')->on('service_options');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_10_06_214026_ServicesToNestsConversion.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ServicesToNestsConversion extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::disableForeignKeyConstraints();\n\n        Schema::rename('services', 'nests');\n\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['service_id']);\n            $table->renameColumn('service_id', 'nest_id');\n\n            $table->foreign('nest_id')->references('id')->on('nests');\n        });\n\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropForeign(['service_id']);\n            $table->renameColumn('service_id', 'nest_id');\n\n            $table->foreign('nest_id')->references('id')->on('nests')->onDelete('CASCADE');\n        });\n\n        Schema::enableForeignKeyConstraints();\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::disableForeignKeyConstraints();\n\n        Schema::rename('nests', 'services');\n\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['nest_id']);\n            $table->renameColumn('nest_id', 'service_id');\n\n            $table->foreign('service_id')->references('id')->on('services');\n        });\n\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropForeign(['nest_id']);\n            $table->renameColumn('nest_id', 'service_id');\n\n            $table->foreign('service_id')->references('id')->on('services')->onDelete('CASCADE');\n        });\n\n        Schema::enableForeignKeyConstraints();\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_10_06_214053_ServiceOptionsToEggsConversion.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ServiceOptionsToEggsConversion extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::disableForeignKeyConstraints();\n\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->dropForeign(['config_from']);\n            $table->dropForeign(['copy_script_from']);\n        });\n\n        Schema::rename('service_options', 'eggs');\n\n        Schema::table('packs', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n            $table->renameColumn('option_id', 'egg_id');\n\n            $table->foreign('egg_id')->references('id')->on('eggs')->onDelete('CASCADE');\n        });\n\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n            $table->renameColumn('option_id', 'egg_id');\n\n            $table->foreign('egg_id')->references('id')->on('eggs');\n        });\n\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->foreign('config_from')->references('id')->on('eggs')->onDelete('SET NULL');\n            $table->foreign('copy_script_from')->references('id')->on('eggs')->onDelete('SET NULL');\n        });\n\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->dropForeign(['option_id']);\n            $table->renameColumn('option_id', 'egg_id');\n\n            $table->foreign('egg_id')->references('id')->on('eggs')->onDelete('CASCADE');\n        });\n\n        Schema::enableForeignKeyConstraints();\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::disableForeignKeyConstraints();\n\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->dropForeign(['config_from']);\n            $table->dropForeign(['copy_script_from']);\n        });\n\n        Schema::rename('eggs', 'service_options');\n\n        Schema::table('packs', function (Blueprint $table) {\n            $table->dropForeign(['egg_id']);\n            $table->renameColumn('egg_id', 'option_id');\n\n            $table->foreign('option_id')->references('id')->on('service_options')->onDelete('CASCADE');\n        });\n\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['egg_id']);\n            $table->renameColumn('egg_id', 'option_id');\n\n            $table->foreign('option_id')->references('id')->on('service_options');\n        });\n\n        Schema::table('service_options', function (Blueprint $table) {\n            $table->foreign('config_from')->references('id')->on('service_options')->onDelete('SET NULL');\n            $table->foreign('copy_script_from')->references('id')->on('service_options')->onDelete('SET NULL');\n        });\n\n        Schema::table('service_variables', function (Blueprint $table) {\n            $table->dropForeign(['egg_id']);\n            $table->renameColumn('egg_id', 'option_id');\n\n            $table->foreign('option_id')->references('id')->on('options')->onDelete('CASCADE');\n        });\n\n        Schema::enableForeignKeyConstraints();\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_10_06_215741_ServiceVariablesToEggVariablesConversion.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ServiceVariablesToEggVariablesConversion extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::disableForeignKeyConstraints();\n\n        Schema::rename('service_variables', 'egg_variables');\n\n        Schema::table('server_variables', function (Blueprint $table) {\n            $table->dropForeign(['variable_id']);\n\n            $table->foreign('variable_id')->references('id')->on('egg_variables')->onDelete('CASCADE');\n        });\n\n        Schema::enableForeignKeyConstraints();\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::disableForeignKeyConstraints();\n\n        Schema::rename('egg_variables', 'service_variables');\n\n        Schema::table('server_variables', function (Blueprint $table) {\n            $table->dropForeign(['variable_id']);\n\n            $table->foreign('variable_id')->references('id')->on('service_variables')->onDelete('CASCADE');\n        });\n\n        Schema::enableForeignKeyConstraints();\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_10_24_222238_RemoveLegacySFTPInformation.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RemoveLegacySFTPInformation extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropUnique(['username']);\n\n            $table->dropColumn('username');\n            $table->dropColumn('sftp_password');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->string('username')->nullable()->after('image')->unique();\n            $table->text('sftp_password')->after('image');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_11_11_161922_Add2FaLastAuthorizationTimeColumn.php",
    "content": "<?php\n\nuse Carbon\\Carbon;\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Crypt;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass Add2FaLastAuthorizationTimeColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->text('totp_secret')->nullable()->change();\n            $table->timestampTz('totp_authenticated_at')->after('totp_secret')->nullable();\n        });\n\n        DB::transaction(function () {\n            DB::table('users')->get()->each(function ($user) {\n                if (is_null($user->totp_secret)) {\n                    return;\n                }\n\n                DB::table('users')->where('id', $user->id)->update([\n                    'totp_secret' => Crypt::encrypt($user->totp_secret),\n                    'updated_at' => Carbon::now()->toAtomString(),\n                ]);\n            });\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        DB::transaction(function () {\n            DB::table('users')->get()->each(function ($user) {\n                if (is_null($user->totp_secret)) {\n                    return;\n                }\n\n                DB::table('users')->where('id', $user->id)->update([\n                    'totp_secret' => Crypt::decrypt($user->totp_secret),\n                    'updated_at' => Carbon::now()->toAtomString(),\n                ]);\n            });\n        });\n\n        DB::statement('ALTER TABLE users MODIFY totp_secret CHAR(16) DEFAULT NULL');\n\n        Schema::table('users', function (Blueprint $table) {\n            $table->dropColumn('totp_authenticated_at');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_11_19_122708_MigratePubPrivFormatToSingleKey.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Str;\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Crypt;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\nuse Illuminate\\Contracts\\Encryption\\DecryptException;\n\nclass MigratePubPrivFormatToSingleKey extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::transaction(function () {\n            DB::table('api_keys')->get()->each(function ($item) {\n                try {\n                    $decrypted = Crypt::decrypt($item->secret);\n                } catch (DecryptException) {\n                    $decrypted = str_random(32);\n                } finally {\n                    DB::table('api_keys')->where('id', $item->id)->update([\n                        'secret' => $decrypted,\n                    ]);\n                }\n            });\n        });\n\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropColumn('public');\n            $table->renameColumn('secret', 'token');\n        });\n\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->char('token', 32)->change();\n            $table->unique('token');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropUnique(['token']);\n            $table->renameColumn('token', 'secret');\n        });\n\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropUnique('token');\n            $table->text('token')->change();\n        });\n\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->renameColumn('token', 'secret');\n\n            $table->text('secret')->nullable()->change();\n            $table->char('public', 16)->after('user_id');\n        });\n\n        DB::transaction(function () {\n            DB::table('api_keys')->get()->each(function ($item) {\n                DB::table('api_keys')->where('id', $item->id)->update([\n                    'public' => Str::random(16),\n                    'secret' => Crypt::encrypt($item->secret),\n                ]);\n            });\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_12_04_184012_DropAllocationsWhenNodeIsDeleted.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DropAllocationsWhenNodeIsDeleted extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->dropForeign(['node_id']);\n\n            $table->foreign('node_id')->references('id')->on('nodes')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->dropForeign(['node_id']);\n\n            $table->foreign('node_id')->references('id')->on('nodes');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2017_12_12_220426_MigrateSettingsTableToNewFormat.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass MigrateSettingsTableToNewFormat extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::table('settings')->truncate();\n        Schema::table('settings', function (Blueprint $table) {\n            $table->increments('id')->first();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('settings', function (Blueprint $table) {\n            $table->dropColumn('id');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_01_01_122821_AllowNegativeValuesForServerSwap.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AllowNegativeValuesForServerSwap extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->integer('swap')->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->unsignedInteger('swap')->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_01_11_213943_AddApiKeyPermissionColumns.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddApiKeyPermissionColumns extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::dropIfExists('api_permissions');\n\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->unsignedTinyInteger('r_servers')->default(0);\n            $table->unsignedTinyInteger('r_nodes')->default(0);\n            $table->unsignedTinyInteger('r_allocations')->default(0);\n            $table->unsignedTinyInteger('r_users')->default(0);\n            $table->unsignedTinyInteger('r_locations')->default(0);\n            $table->unsignedTinyInteger('r_nests')->default(0);\n            $table->unsignedTinyInteger('r_eggs')->default(0);\n            $table->unsignedTinyInteger('r_database_hosts')->default(0);\n            $table->unsignedTinyInteger('r_server_databases')->default(0);\n            $table->unsignedTinyInteger('r_packs')->default(0);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::create('api_permissions', function (Blueprint $table) {\n            $table->increments('id');\n            $table->unsignedInteger('key_id');\n            $table->string('permission');\n\n            $table->foreign('key_id')->references('id')->on('api_keys')->onDelete('cascade');\n        });\n\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropColumn([\n                'r_servers',\n                'r_nodes',\n                'r_allocations',\n                'r_users',\n                'r_locations',\n                'r_nests',\n                'r_eggs',\n                'r_database_hosts',\n                'r_server_databases',\n                'r_packs',\n            ]);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_01_13_142012_SetupTableForKeyEncryption.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass SetupTableForKeyEncryption extends Migration\n{\n    /**\n     * Run the migrations.\n     *\n     * @throws Exception\n     * @throws Throwable\n     */\n    public function up(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->char('identifier', 16)->nullable()->unique()->after('user_id');\n            $table->dropUnique(['token']);\n        });\n\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->text('token')->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     *\n     * @throws Exception\n     * @throws Throwable\n     */\n    public function down(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropColumn('identifier');\n            $table->string('token', 32)->unique()->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_01_13_145209_AddLastUsedAtColumn.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddLastUsedAtColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->unsignedTinyInteger('key_type')->after('user_id')->default(0);\n            $table->timestamp('last_used_at')->after('memo')->nullable();\n            $table->dropColumn('expires_at');\n\n            $table->dropForeign(['user_id']);\n        });\n\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->foreign('user_id')->references('id')->on('users')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->timestamp('expires_at')->after('memo')->nullable();\n            $table->dropColumn('last_used_at', 'key_type');\n            $table->dropForeign(['user_id']);\n        });\n\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->foreign('user_id')->references('id')->on('users');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_02_04_145617_AllowTextInUserExternalId.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AllowTextInUserExternalId extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->string('external_id')->nullable()->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->unsignedInteger('external_id')->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_02_10_151150_remove_unique_index_on_external_id_column.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RemoveUniqueIndexOnExternalIdColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->dropUnique(['external_id']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->unique(['external_id']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_02_17_134254_ensure_unique_allocation_id_on_servers_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass EnsureUniqueAllocationIdOnServersTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->unique(['allocation_id']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['allocation_id']);\n            $table->dropUnique(['allocation_id']);\n\n            $table->foreign('allocation_id')->references('id')->on('allocations');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_02_24_112356_add_external_id_column_to_servers_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddExternalIdColumnToServersTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->string('external_id')->after('id')->nullable()->unique();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('external_id');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_02_25_160152_remove_default_null_value_on_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RemoveDefaultNullValueOnTable extends Migration\n{\n    /**\n     * Run the migrations.\n     *\n     * @throws Exception\n     * @throws Throwable\n     */\n    public function up(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->string('external_id')->default(null)->change();\n        });\n\n        DB::transaction(function () {\n            DB::table('users')->where('external_id', '=', 'NULL')->update([\n                'external_id' => null,\n            ]);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        // This should not be rolled back.\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_02_25_160604_define_unique_index_on_users_external_id.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DefineUniqueIndexOnUsersExternalId extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->index(['external_id']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('users', function (Blueprint $table) {\n            $table->dropIndex(['external_id']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_03_01_192831_add_database_and_port_limit_columns_to_servers_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddDatabaseAndPortLimitColumnsToServersTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->unsignedInteger('database_limit')->after('installed')->nullable()->default(0);\n            $table->unsignedInteger('allocation_limit')->after('installed')->nullable()->default(0);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn(['database_limit', 'allocation_limit']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_03_15_124536_add_description_to_nodes.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddDescriptionToNodes extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->text('description')->after('name');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->dropColumn('description');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_05_04_123826_add_maintenance_to_nodes.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddMaintenanceToNodes extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->boolean('maintenance_mode')->after('behind_proxy')->default(false);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->dropColumn('maintenance_mode');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_09_03_143756_allow_egg_variables_to_have_longer_values.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AllowEggVariablesToHaveLongerValues extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('egg_variables', function (Blueprint $table) {\n            $table->text('default_value')->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('egg_variables', function (Blueprint $table) {\n            $table->string('default_value')->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2018_09_03_144005_allow_server_variables_to_have_longer_values.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AllowServerVariablesToHaveLongerValues extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('server_variables', function (Blueprint $table) {\n            $table->text('variable_value')->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('server_variables', function (Blueprint $table) {\n            $table->string('variable_value')->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2019_03_02_142328_set_allocation_limit_default_null.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass SetAllocationLimitDefaultNull extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->unsignedInteger('allocation_limit')->nullable()->default(null)->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->unsignedInteger('allocation_limit')->nullable()->default(0)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2019_03_02_151321_fix_unique_index_to_account_for_host.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass FixUniqueIndexToAccountForHost extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->dropUnique(['database']);\n            $table->dropUnique(['username']);\n\n            $table->unique(['database_host_id', 'database']);\n            $table->unique(['database_host_id', 'username']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->dropForeign(['database_host_id']);\n\n            $table->dropUnique(['database_host_id', 'database']);\n            $table->dropUnique(['database_host_id', 'username']);\n\n            $table->unique(['database']);\n            $table->unique(['username']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_03_22_163911_merge_permissions_table_into_subusers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Support\\Facades\\DB;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Pterodactyl\\Models\\Permission as P;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass MergePermissionsTableIntoSubusers extends Migration\n{\n    /**\n     * A list of all pre-1.0 permissions available to a user and their associated\n     * casting for the new permissions system.\n     *\n     * @var array\n     */\n    protected static $permissionsMap = [\n        'power-start' => P::ACTION_CONTROL_START,\n        'power-stop' => P::ACTION_CONTROL_STOP,\n        'power-restart' => P::ACTION_CONTROL_RESTART,\n        'power-kill' => P::ACTION_CONTROL_STOP,\n        'send-command' => P::ACTION_CONTROL_CONSOLE,\n        'list-subusers' => P::ACTION_USER_READ,\n        'view-subuser' => P::ACTION_USER_READ,\n        'edit-subuser' => P::ACTION_USER_UPDATE,\n        'create-subuser' => P::ACTION_USER_CREATE,\n        'delete-subuser' => P::ACTION_USER_DELETE,\n        'view-allocations' => P::ACTION_ALLOCATION_READ,\n        'edit-allocation' => P::ACTION_ALLOCATION_UPDATE,\n        'view-startup' => P::ACTION_STARTUP_READ,\n        'edit-startup' => P::ACTION_STARTUP_UPDATE,\n        'view-databases' => P::ACTION_DATABASE_READ,\n        // Better to just break this flow a bit than accidentally grant a dangerous permission.\n        'reset-db-password' => P::ACTION_DATABASE_UPDATE,\n        'delete-database' => P::ACTION_DATABASE_DELETE,\n        'create-database' => P::ACTION_DATABASE_CREATE,\n        'access-sftp' => P::ACTION_FILE_SFTP,\n        'list-files' => P::ACTION_FILE_READ,\n        'edit-files' => P::ACTION_FILE_READ_CONTENT,\n        'save-files' => P::ACTION_FILE_UPDATE,\n        'create-files' => P::ACTION_FILE_CREATE,\n        'delete-files' => P::ACTION_FILE_DELETE,\n        'compress-files' => P::ACTION_FILE_ARCHIVE,\n        'list-schedules' => P::ACTION_SCHEDULE_READ,\n        'view-schedule' => P::ACTION_SCHEDULE_READ,\n        'edit-schedule' => P::ACTION_SCHEDULE_UPDATE,\n        'create-schedule' => P::ACTION_SCHEDULE_CREATE,\n        'delete-schedule' => P::ACTION_SCHEDULE_DELETE,\n        // Skipping these permissions as they are granted if you have more specific read/write permissions.\n        'move-files' => null,\n        'copy-files' => null,\n        'decompress-files' => null,\n        'upload-files' => null,\n        'download-files' => null,\n        // These permissions do not exist in 1.0\n        'toggle-schedule' => null,\n        'queue-schedule' => null,\n    ];\n\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('subusers', function (Blueprint $table) {\n            $table->json('permissions')->nullable()->after('server_id');\n        });\n\n        $cursor = DB::table('permissions')\n            ->select(['subuser_id'])\n            ->when(DB::getPdo()->getAttribute(PDO::ATTR_DRIVER_NAME) === 'mysql', function ($query) {\n                $query->selectRaw('group_concat(permission) as permissions');\n            })\n            ->when(DB::getPdo()->getAttribute(PDO::ATTR_DRIVER_NAME) === 'pgsql', function ($query) {\n                $query->selectRaw(\"string_agg(permission, ',') as permissions\");\n            })\n            ->from('permissions')\n            ->groupBy(['subuser_id'])\n            ->cursor();\n\n        DB::transaction(function () use (&$cursor) {\n            $cursor->each(function ($datum) {\n                $updated = Collection::make(explode(',', $datum->permissions))\n                    ->map(function ($value) {\n                        return self::$permissionsMap[$value] ?? null;\n                    })->filter(function ($value) {\n                        return !is_null($value) && $value !== Permission::ACTION_WEBSOCKET_CONNECT;\n                    })\n                    // All subusers get this permission, so make sure it gets pushed into the array.\n                    ->merge([Permission::ACTION_WEBSOCKET_CONNECT])\n                    ->unique()\n                    ->values()\n                    ->toJson();\n\n                DB::update('UPDATE subusers SET permissions = ? WHERE id = ?', [$updated, $datum->subuser_id]);\n            });\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        $flipped = array_flip(array_filter(self::$permissionsMap));\n\n        foreach (DB::select('SELECT id, permissions FROM subusers') as $datum) {\n            $values = [];\n            foreach (json_decode($datum->permissions, true) as $permission) {\n                $v = $flipped[$permission] ?? null;\n                if (!empty($v)) {\n                    $values[] = $datum->id;\n                    $values[] = $v;\n                }\n            }\n\n            if (!empty($values)) {\n                $string = 'VALUES ' . implode(', ', array_fill(0, count($values) / 2, '(?, ?)'));\n\n                DB::insert('INSERT INTO permissions(`subuser_id`, `permission`) ' . $string, $values);\n            }\n        }\n\n        Schema::table('subusers', function (Blueprint $table) {\n            $table->dropColumn('permissions');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_03_22_164814_drop_permissions_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DropPermissionsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::dropIfExists('permissions');\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::create('permissions', function (Blueprint $table) {\n            $table->increments('id');\n            $table->unsignedInteger('subuser_id');\n            $table->string('permission');\n\n            $table->foreign('subuser_id')->references('id')->on('subusers')->onDelete('cascade');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_04_03_203624_add_threads_column_to_servers_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddThreadsColumnToServersTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->string('threads')->nullable()->after('cpu');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('threads');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_04_03_230614_create_backups_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateBackupsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        $db = config('database.default');\n        // There exists a backups plugin for the 0.7 version of the Panel. However, it didn't properly\n        // namespace itself so now we have to deal with these tables being in the way of tables we're trying\n        // to use. For now, just rename them to maintain the data.\n        $results = DB::select('SELECT TABLE_NAME FROM information_schema.tables WHERE table_schema = ? AND table_name LIKE ? AND table_name NOT LIKE \\'%_plugin_bak\\'', [\n            config(\"database.connections.{$db}.database\"),\n            'backup%',\n        ]);\n\n        // Take any of the results, most likely \"backups\" and \"backup_logs\" and rename them to have a\n        // suffix so data isn't completely lost, but they're no longer in the way of this migration...\n        foreach ($results as $result) {\n            Schema::rename($result->TABLE_NAME, $result->TABLE_NAME . '_plugin_bak');\n        }\n\n        Schema::create('backups', function (Blueprint $table) {\n            $table->bigIncrements('id');\n            $table->unsignedInteger('server_id');\n            $table->char('uuid', 36);\n            $table->string('name');\n            $table->text('ignored_files');\n            $table->string('disk');\n            $table->string('sha256_hash')->nullable();\n            $table->integer('bytes')->default(0);\n            $table->timestamp('completed_at')->nullable();\n            $table->timestamps();\n            $table->softDeletes();\n\n            $table->unique('uuid');\n            $table->foreign('server_id')->references('id')->on('servers')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('backups');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_04_04_131016_add_table_server_transfers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddTableServerTransfers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        // Nuclear approach to whatever plugins are out there and not properly namespacing their own tables\n        // leading to constant support requests from people...\n        Schema::dropIfExists('server_transfers');\n\n        Schema::create('server_transfers', function (Blueprint $table) {\n            $table->increments('id');\n            $table->integer('server_id')->unsigned();\n            $table->boolean('successful')->unsigned()->default(0);\n            $table->integer('old_node')->unsigned();\n            $table->integer('new_node')->unsigned();\n            $table->integer('old_allocation')->unsigned();\n            $table->integer('new_allocation')->unsigned();\n            $table->json('old_additional_allocations')->nullable();\n            $table->json('new_additional_allocations')->nullable();\n            $table->timestamps();\n\n            $table->foreign('server_id')->references('id')->on('servers')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('server_transfers');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_04_10_141024_store_node_tokens_as_encrypted_value.php",
    "content": "<?php\n\nuse Ramsey\\Uuid\\Uuid;\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Container\\Container;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\n\nclass StoreNodeTokensAsEncryptedValue extends Migration\n{\n    /**\n     * Run the migrations.\n     *\n     * @throws Exception\n     */\n    public function up(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->dropUnique(['daemonSecret']);\n        });\n\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->char('uuid', 36)->after('id');\n            $table->char('daemon_token_id', 16)->after('upload_size');\n\n            $table->renameColumn('`daemonSecret`', 'daemon_token');\n        });\n\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->text('daemon_token')->change();\n        });\n\n        /** @var Encrypter $encrypter */\n        $encrypter = Container::getInstance()->make(Encrypter::class);\n\n        foreach (DB::select('SELECT id, daemon_token FROM nodes') as $datum) {\n            DB::update('UPDATE nodes SET uuid = ?, daemon_token_id = ?, daemon_token = ? WHERE id = ?', [\n                Uuid::uuid4()->toString(),\n                substr($datum->daemon_token, 0, 16),\n                $encrypter->encrypt(substr($datum->daemon_token, 16)),\n                $datum->id,\n            ]);\n        }\n\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->unique(['uuid']);\n            $table->unique(['daemon_token_id']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        DB::transaction(function () {\n            /** @var Encrypter $encrypter */\n            $encrypter = Container::getInstance()->make(Encrypter::class);\n\n            foreach (DB::select('SELECT id, daemon_token_id, daemon_token FROM nodes') as $datum) {\n                DB::update('UPDATE nodes SET daemon_token = ? WHERE id = ?', [\n                    $datum->daemon_token_id . $encrypter->decrypt($datum->daemon_token),\n                    $datum->id,\n                ]);\n            }\n        });\n\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->dropUnique(['uuid']);\n            $table->dropUnique(['daemon_token_id']);\n        });\n\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->dropColumn(['uuid', 'daemon_token_id']);\n            $table->renameColumn('daemon_token', 'daemonSecret');\n        });\n\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->string('daemonSecret', 36)->change();\n            $table->unique(['daemonSecret']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_04_17_203438_allow_nullable_descriptions.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AllowNullableDescriptions extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->text('description')->nullable()->change();\n        });\n\n        Schema::table('nests', function (Blueprint $table) {\n            $table->text('description')->nullable()->change();\n        });\n\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->text('description')->nullable()->change();\n        });\n\n        Schema::table('locations', function (Blueprint $table) {\n            $table->text('long')->nullable()->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->text('description')->nullable(false)->change();\n        });\n\n        Schema::table('nests', function (Blueprint $table) {\n            $table->text('description')->nullable(false)->change();\n        });\n\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->text('description')->nullable(false)->change();\n        });\n\n        Schema::table('locations', function (Blueprint $table) {\n            $table->text('long')->nullable(false)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_04_22_055500_add_max_connections_column.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddMaxConnectionsColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->integer('max_connections')->nullable()->default(0)->after('password');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->dropColumn('max_connections');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_04_26_111208_add_backup_limit_to_servers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddBackupLimitToServers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        $db = config('database.default');\n        // Same as in the backups migration, we need to handle that plugin messing with the data structure\n        // here. If we find a result we'll actually keep the column around since we can maintain that backup\n        // limit, but we need to correct the column definition a bit.\n        $results = DB::select('SELECT * FROM information_schema.COLUMNS WHERE TABLE_SCHEMA = ? AND TABLE_NAME = \\'servers\\' AND COLUMN_NAME = \\'backup_limit\\'', [\n            config(\"database.connections.{$db}.database\"),\n        ]);\n\n        if (count($results) === 1) {\n            Schema::table('servers', function (Blueprint $table) {\n                $table->unsignedInteger('backup_limit')->default(0)->change();\n            });\n        } else {\n            Schema::table('servers', function (Blueprint $table) {\n                $table->unsignedInteger('backup_limit')->default(0)->after('database_limit');\n            });\n        }\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('backup_limit');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_05_20_234655_add_mounts_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddMountsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('mounts', function (Blueprint $table) {\n            $table->increments('id')->unique();\n            $table->char('uuid', 36)->unique();\n            $table->string('name')->unique();\n            $table->text('description')->nullable();\n            $table->string('source');\n            $table->string('target');\n            $table->tinyInteger('read_only')->unsigned();\n            $table->tinyInteger('user_mountable')->unsigned();\n        });\n\n        Schema::create('egg_mount', function (Blueprint $table) {\n            $table->integer('egg_id');\n            $table->integer('mount_id');\n\n            $table->unique(['egg_id', 'mount_id']);\n        });\n\n        Schema::create('mount_node', function (Blueprint $table) {\n            $table->integer('node_id');\n            $table->integer('mount_id');\n\n            $table->unique(['node_id', 'mount_id']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('mount_node');\n        Schema::dropIfExists('egg_mount');\n        Schema::dropIfExists('mounts');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_05_21_192756_add_mount_server_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddMountServerTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('mount_server', function (Blueprint $table) {\n            $table->integer('server_id');\n            $table->integer('mount_id');\n\n            $table->unique(['server_id', 'mount_id']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('mount_server');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_07_02_213612_create_user_recovery_tokens_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateUserRecoveryTokensTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('recovery_tokens', function (Blueprint $table) {\n            $table->id();\n            $table->unsignedInteger('user_id');\n            $table->string('token');\n            $table->timestamp('created_at')->nullable();\n\n            $table->foreign('user_id')->references('id')->on('users')->cascadeOnDelete();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('recovery_tokens');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_07_09_201845_add_notes_column_for_allocations.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddNotesColumnForAllocations extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->string('notes')->nullable()->after('server_id');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('allocations', function (Blueprint $table) {\n            $table->dropColumn('notes');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_08_20_205533_add_backup_state_column_to_backups.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddBackupStateColumnToBackups extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->boolean('is_successful')->after('uuid')->default(true);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->dropColumn('is_successful');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_08_22_132500_update_bytes_to_unsigned_bigint.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateBytesToUnsignedBigint extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->unsignedBigInteger('bytes')->default(0)->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->integer('bytes')->default(0)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_08_23_175331_modify_checksums_column_for_backups.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ModifyChecksumsColumnForBackups extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->renameColumn('sha256_hash', 'checksum');\n        });\n\n        Schema::table('backups', function (Blueprint $table) {\n            DB::update('UPDATE backups SET checksum = CONCAT(\\'sha256:\\', checksum)');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->renameColumn('checksum', 'sha256_hash');\n        });\n\n        Schema::table('backups', function (Blueprint $table) {\n            DB::update('UPDATE backups SET sha256_hash = SUBSTRING(sha256_hash, 8)');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_09_13_110007_drop_packs_from_servers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DropPacksFromServers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropForeign(['pack_id']);\n            $table->dropColumn('pack_id');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->unsignedInteger('pack_id')->after('egg_id')->nullable();\n            $table->foreign('pack_id')->references('id')->on('packs');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_09_13_110021_drop_packs_from_api_key_permissions.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DropPacksFromApiKeyPermissions extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropColumn('r_packs');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->unsignedTinyInteger('r_packs')->default(0);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_09_13_110047_drop_packs_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DropPacksTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::dropIfExists('packs');\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::create('packs', function (Blueprint $table) {\n            $table->increments('id');\n            $table->unsignedInteger('egg_id');\n            $table->char('uuid', 36)->unique();\n            $table->string('name');\n            $table->string('version');\n            $table->text('description')->nullable();\n            $table->tinyInteger('selectable')->default(1);\n            $table->tinyInteger('visible')->default(1);\n            $table->tinyInteger('locked')->default(0);\n            $table->timestamps();\n        });\n\n        Schema::table('packs', function (Blueprint $table) {\n            $table->foreign('egg_id')->references('id')->on('eggs')->cascadeOnDelete();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_09_13_113503_drop_daemon_key_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DropDaemonKeyTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::dropIfExists('daemon_keys');\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::create('daemon_keys', function (Blueprint $table) {\n            $table->increments('id');\n            $table->unsignedInteger('server_id');\n            $table->unsignedInteger('user_id');\n            $table->string('secret')->unique();\n            $table->timestamp('expires_at');\n            $table->timestamps();\n        });\n\n        Schema::table('daemon_keys', function (Blueprint $table) {\n            $table->foreign('server_id')->references('id')->on('servers')->cascadeOnDelete();\n            $table->foreign('user_id')->references('id')->on('users')->cascadeOnDelete();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_10_10_165437_change_unique_database_name_to_account_for_server.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ChangeUniqueDatabaseNameToAccountForServer extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->dropUnique(['database_host_id', 'database']);\n        });\n\n        Schema::table('databases', function (Blueprint $table) {\n            $table->unique(['database_host_id', 'server_id', 'database']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('databases', function (Blueprint $table) {\n            $table->dropUnique(['database_host_id', 'server_id', 'database']);\n        });\n\n        Schema::table('databases', function (Blueprint $table) {\n            $table->unique(['database_host_id', 'database']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_10_26_194904_remove_nullable_from_schedule_name_field.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RemoveNullableFromScheduleNameField extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::update(\"UPDATE schedules SET name = 'Schedule' WHERE name IS NULL OR name = ''\");\n\n        Schema::table('schedules', function (Blueprint $table) {\n            $table->string('name')->nullable(false)->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('schedules', function (Blueprint $table) {\n            $table->string('name')->nullable()->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_11_02_201014_add_features_column_to_eggs.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddFeaturesColumnToEggs extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->json('features')->after('description')->nullable();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->dropColumn('features');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_12_12_102435_support_multiple_docker_images_and_updates.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass SupportMultipleDockerImagesAndUpdates extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->json('docker_images')->after('docker_image')->nullable();\n            $table->text('update_url')->after('docker_images')->nullable();\n        });\n\n        switch (DB::getPdo()->getAttribute(PDO::ATTR_DRIVER_NAME)) {\n            case 'mysql':\n                DB::table('eggs')->update(['docker_images' => DB::raw('JSON_ARRAY(docker_image)')]);\n                break;\n            case 'pgsql':\n                DB::table('eggs')->update(['docker_images' => DB::raw('jsonb_build_array(docker_image)')]);\n                break;\n        }\n\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->dropColumn('docker_image');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->text('docker_image')->after('docker_images');\n        });\n\n        switch (DB::getPdo()->getAttribute(PDO::ATTR_DRIVER_NAME)) {\n            case 'mysql':\n                DB::table('eggs')->update(['docker_images' => DB::raw('JSON_UNQUOTE(JSON_EXTRACT(docker_images, \"$[0]\")')]);\n                break;\n            case 'pgsql':\n                DB::table('eggs')->update(['docker_images' => DB::raw('JSON_UNQUOTE(JSON_EXTRACT(docker_images, \"$[0]\")')]);\n                DB::table('eggs')->update(['docker_images' => DB::raw('docker_images->>0')]);\n                break;\n        }\n\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->dropColumn('docker_images');\n            $table->dropColumn('update_url');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_12_14_013707_make_successful_nullable_in_server_transfers.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass MakeSuccessfulNullableInServerTransfers extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('server_transfers', function (Blueprint $table) {\n            $table->boolean('successful')->nullable()->default(null)->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('server_transfers', function (Blueprint $table) {\n            $table->boolean('successful')->default(0)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_12_17_014330_add_archived_field_to_server_transfers_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddArchivedFieldToServerTransfersTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('server_transfers', function (Blueprint $table) {\n            $table->boolean('archived')->default(0)->after('new_additional_allocations');\n        });\n\n        // Update archived to all be true on existing transfers.\n        DB::table('server_transfers')->where('successful', true)->update(['archived' => 1]);\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('server_transfers', function (Blueprint $table) {\n            $table->dropColumn('archived');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_12_24_092449_make_allocation_fields_json.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass MakeAllocationFieldsJson extends Migration\n{\n    /**\n     * Run the migrations.\n     *\n     * @return void\n     */\n    public function up()\n    {\n        Schema::table('server_transfers', function (Blueprint $table) {\n            $table->json('old_additional_allocations')->nullable()->change();\n            $table->json('new_additional_allocations')->nullable()->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     *\n     * @return void\n     */\n    public function down()\n    {\n        Schema::table('server_transfers', function (Blueprint $table) {\n            $table->string('old_additional_allocations')->nullable()->change();\n            $table->string('new_additional_allocations')->nullable()->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2020_12_26_184914_add_upload_id_column_to_backups_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddUploadIdColumnToBackupsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->text('upload_id')->nullable()->after('uuid');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->dropColumn('upload_id');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_01_10_153937_add_file_denylist_to_egg_configs.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddFileDenylistToEggConfigs extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->text('file_denylist')->after('docker_images');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->dropColumn('file_denylist');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_01_13_013420_add_cron_month.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddCronMonth extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('schedules', function (Blueprint $table) {\n            $table->string('cron_month')->after('cron_day_of_week');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('schedules', function (Blueprint $table) {\n            $table->dropColumn('cron_month');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_01_17_102401_create_audit_logs_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateAuditLogsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('audit_logs', function (Blueprint $table) {\n            $table->id();\n            $table->char('uuid', 36);\n            $table->boolean('is_system')->default(false);\n            $table->unsignedInteger('user_id')->nullable();\n            $table->unsignedInteger('server_id')->nullable();\n            $table->string('action');\n            $table->string('subaction')->nullable();\n            $table->json('device');\n            $table->json('metadata');\n            $table->timestamp('created_at', 0);\n\n            $table->foreign('user_id')->references('id')->on('users')->onDelete('set null');\n            $table->foreign('server_id')->references('id')->on('servers')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('audit_logs');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_01_17_152623_add_generic_server_status_column.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddGenericServerStatusColumn extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->string('status')->nullable()->after('description');\n        });\n\n        DB::table('servers')->where('suspended', 1)->update(['status' => 'suspended']);\n        DB::table('servers')->where('installed', 1)->update(['status' => 'installing']);\n        DB::table('servers')->where('installed', 1)->update(['status' => 'install_failed']);\n\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('suspended');\n            $table->dropColumn('installed');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->unsignedTinyInteger('suspended')->default(0);\n            $table->unsignedTinyInteger('installed')->default(0);\n        });\n\n        DB::table('servers')->where('status', 'suspended')->update(['suspended' => 1]);\n        DB::table('servers')->whereNull('status')->update(['installed' => 1]);\n        DB::table('servers')->where('status', 'install_failed')->update(['installed' => 2]);\n\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('status');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_01_26_210502_update_file_denylist_to_json.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass UpdateFileDenylistToJson extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->dropColumn('file_denylist');\n        });\n\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->json('file_denylist')->nullable()->after('docker_images');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->dropColumn('file_denylist');\n        });\n\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->text('file_denylist')->after('docker_images');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_02_23_205021_add_index_for_server_and_action.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddIndexForServerAndAction extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('audit_logs', function (Blueprint $table) {\n            // Doing the index in this order lets me use the action alone without the server\n            // or I can later include the server to also filter down at an even more specific\n            // level.\n            //\n            // Ordering the other way around would require a second index for only \"action\" in\n            // order to query a specific action type for any server. Remeber, indexes run left\n            // to right in MySQL.\n            $table->index(['action', 'server_id']);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('audit_logs', function (Blueprint $table) {\n            $table->dropIndex(['action', 'server_id']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_02_23_212657_make_sftp_port_unsigned_int.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass MakeSftpPortUnsignedInt extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->unsignedSmallInteger('daemonSFTP')->default(2022)->change();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('nodes', function (Blueprint $table) {\n            $table->smallInteger('daemonSFTP')->default(2022)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_03_21_104718_force_cron_month_field_to_have_value_if_missing.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ForceCronMonthFieldToHaveValueIfMissing extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::table('schedules')->where('cron_month', '')->update(['cron_month' => '*']);\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        // No down function.\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_05_01_092457_add_continue_on_failure_option_to_tasks.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddContinueOnFailureOptionToTasks extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('tasks', function (Blueprint $table) {\n            $table->unsignedTinyInteger('continue_on_failure')->after('is_queued')->default(0);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('tasks', function (Blueprint $table) {\n            $table->dropColumn('continue_on_failure');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_05_01_092523_add_only_run_when_server_online_option_to_schedules.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddOnlyRunWhenServerOnlineOptionToSchedules extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('schedules', function (Blueprint $table) {\n            $table->unsignedTinyInteger('only_when_online')->after('is_processing')->default(0);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('schedules', function (Blueprint $table) {\n            $table->dropColumn('only_when_online');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_05_03_201016_add_support_for_locking_a_backup.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddSupportForLockingABackup extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->unsignedTinyInteger('is_locked')->after('is_successful')->default(0);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->dropColumn('is_locked');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_07_12_013420_remove_userinteraction.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass RemoveUserInteraction extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        // Remove User Interaction from startup config\n        switch (DB::getPdo()->getAttribute(PDO::ATTR_DRIVER_NAME)) {\n            case 'mysql':\n                DB::table('eggs')->update([\n                    'config_startup' => DB::raw('JSON_REMOVE(config_startup, \\'$.userInteraction\\')'),\n                ]);\n                break;\n            case 'pgsql':\n                DB::table('eggs')->update([\n                    'config_startup' => DB::raw('config_startup::jsonb - \\'userInteraction\\''),\n                ]);\n                break;\n        }\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        // Add blank User Interaction array back to startup config\n        switch (DB::getPdo()->getAttribute(PDO::ATTR_DRIVER_NAME)) {\n            case 'mysql':\n                DB::table('eggs')->update([\n                    'config_startup' => DB::raw('JSON_SET(config_startup, \\'$.userInteraction\\', JSON_ARRAY())'),\n                ]);\n                break;\n            case 'pgsql':\n                DB::table('eggs')->update([\n                    'config_startup' => DB::raw('jsonb_set(config_startup::jsonb, \\'$.userInteraction\\', jsonb_build_array())'),\n                ]);\n                break;\n        }\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_07_17_211512_create_user_ssh_keys_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateUserSshKeysTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('user_ssh_keys', function (Blueprint $table) {\n            $table->increments('id');\n            $table->unsignedInteger('user_id');\n            $table->string('name');\n            $table->string('fingerprint');\n            $table->text('public_key');\n            $table->timestamps();\n            $table->softDeletes();\n\n            $table->foreign('user_id')->references('id')->on('users')->onDelete('cascade');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('user_ssh_keys');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_08_03_210600_change_successful_field_to_default_to_false_on_backups_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass ChangeSuccessfulFieldToDefaultToFalseOnBackupsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->boolean('is_successful')->after('uuid')->default(false)->change();\n        });\n\n        // Convert currently processing backups to the new format so things don't break.\n        DB::table('backups')->select('id')->where('is_successful', 1)->whereNull('completed_at')->update([\n            'is_successful' => 0,\n        ]);\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('backups', function (Blueprint $table) {\n            $table->boolean('is_successful')->after('uuid')->default(true)->change();\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_08_21_175111_add_foreign_keys_to_mount_node_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignKeysToMountNodeTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        // Fix the columns having a different type than their relations.\n        Schema::table('mount_node', function (Blueprint $table) {\n            $table->unsignedInteger('node_id')->change();\n            $table->unsignedInteger('mount_id')->change();\n        });\n\n        // Fetch an array of node and mount ids to check relations against.\n        $nodes = DB::table('nodes')->select('id')->pluck('id')->toArray();\n        $mounts = DB::table('mounts')->select('id')->pluck('id')->toArray();\n\n        // Drop any relations that are missing a node or mount.\n        DB::table('mount_node')\n            ->select('node_id', 'mount_id')\n            ->whereNotIn('node_id', $nodes)\n            ->orWhereNotIn('mount_id', $mounts)\n            ->delete();\n\n        Schema::table('mount_node', function (Blueprint $table) {\n            $table->foreign('node_id')\n                ->references('id')\n                ->on('nodes')\n                ->cascadeOnDelete()\n                ->cascadeOnUpdate();\n            $table->foreign('mount_id')->references('id')\n                ->on('mounts')\n                ->cascadeOnDelete()\n                ->cascadeOnUpdate();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('mount_node', function (Blueprint $table) {\n            $table->dropForeign(['node_id']);\n            $table->dropForeign(['mount_id']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_08_21_175118_add_foreign_keys_to_mount_server_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignKeysToMountServerTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        // Fix the columns having a different type than their relations.\n        Schema::table('mount_server', function (Blueprint $table) {\n            $table->unsignedInteger('server_id')->change();\n            $table->unsignedInteger('mount_id')->change();\n        });\n\n        // Fetch an array of node and mount ids to check relations against.\n        $servers = DB::table('servers')->select('id')->pluck('id')->toArray();\n        $mounts = DB::table('mounts')->select('id')->pluck('id')->toArray();\n\n        // Drop any relations that are missing a server or mount.\n        DB::table('mount_server')\n            ->select('server_id', 'mount_id')\n            ->whereNotIn('server_id', $servers)\n            ->orWhereNotIn('mount_id', $mounts)\n            ->delete();\n\n        Schema::table('mount_server', function (Blueprint $table) {\n            $table->foreign('server_id')\n                ->references('id')\n                ->on('servers')\n                ->cascadeOnDelete()\n                ->cascadeOnUpdate();\n            $table->foreign('mount_id')->references('id')\n                ->on('mounts')\n                ->cascadeOnDelete()\n                ->cascadeOnUpdate();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('mount_server', function (Blueprint $table) {\n            $table->dropForeign(['server_id']);\n            $table->dropForeign(['mount_id']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2021_08_21_180921_add_foreign_keys_to_egg_mount_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForeignKeysToEggMountTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        // Fix the columns having a different type than their relations.\n        Schema::table('egg_mount', function (Blueprint $table) {\n            $table->unsignedInteger('egg_id')->change();\n            $table->unsignedInteger('mount_id')->change();\n        });\n\n        // Fetch an array of node and mount ids to check relations against.\n        $eggs = DB::table('eggs')->select('id')->pluck('id')->toArray();\n        $mounts = DB::table('mounts')->select('id')->pluck('id')->toArray();\n\n        // Drop any relations that are missing an egg or mount.\n        DB::table('egg_mount')\n            ->select('egg_id', 'mount_id')\n            ->whereNotIn('egg_id', $eggs)\n            ->orWhereNotIn('mount_id', $mounts)\n            ->delete();\n\n        Schema::table('egg_mount', function (Blueprint $table) {\n            $table->foreign('egg_id')\n                ->references('id')\n                ->on('eggs')\n                ->cascadeOnDelete()\n                ->cascadeOnUpdate();\n            $table->foreign('mount_id')->references('id')\n                ->on('mounts')\n                ->cascadeOnDelete()\n                ->cascadeOnUpdate();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('egg_mount', function (Blueprint $table) {\n            $table->dropForeign(['egg_id']);\n            $table->dropForeign(['mount_id']);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2022_01_25_030847_drop_google_analytics.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass DropGoogleAnalytics extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        DB::table('settings')->where('key', 'settings::app:analytics')->delete();\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        DB::table('settings')->insert([\n            'key' => 'settings::app:analytics',\n        ]);\n    }\n}\n"
  },
  {
    "path": "database/migrations/2022_05_07_165334_migrate_egg_images_array_to_new_format.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass MigrateEggImagesArrayToNewFormat extends Migration\n{\n    /**\n     * Run the migrations. This will loop over every egg on the system and update the\n     * images array to both exist, and have key => value pairings to support naming the\n     * images provided.\n     */\n    public function up(): void\n    {\n        DB::table('eggs')->select(['id', 'docker_images'])->cursor()->each(function ($egg) {\n            $images = is_null($egg->docker_images) ? [] : json_decode($egg->docker_images, true, 512, JSON_THROW_ON_ERROR);\n\n            $results = [];\n            foreach ($images as $key => $value) {\n                $results[is_int($key) ? $value : $key] = $value;\n            }\n\n            DB::table('eggs')->where('id', $egg->id)->update(['docker_images' => $results]);\n        });\n    }\n\n    /**\n     * Reverse the migrations. This just keeps the values from the docker images array.\n     */\n    public function down(): void\n    {\n        DB::table('eggs')->select(['id', 'docker_images'])->cursor()->each(function ($egg) {\n            DB::table('eggs')->where('id', $egg->id)->update([\n                'docker_images' => array_values(json_decode($egg->docker_images, true, 512, JSON_THROW_ON_ERROR)),\n            ]);\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2022_05_28_135717_create_activity_logs_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateActivityLogsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('activity_logs', function (Blueprint $table) {\n            $table->id();\n            $table->uuid('batch')->nullable();\n            $table->string('event')->index();\n            $table->string('ip');\n            $table->text('description')->nullable();\n            $table->nullableNumericMorphs('actor');\n            $table->json('properties');\n            $table->timestamp('timestamp')->useCurrent()->onUpdate(null);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('activity_logs');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2022_05_29_140349_create_activity_log_actors_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass CreateActivityLogActorsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::create('activity_log_subjects', function (Blueprint $table) {\n            $table->id();\n            $table->foreignId('activity_log_id')->references('id')->on('activity_logs')->cascadeOnDelete();\n            $table->numericMorphs('subject');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::dropIfExists('activity_log_subjects');\n    }\n}\n"
  },
  {
    "path": "database/migrations/2022_06_18_112822_track_api_key_usage_for_activity_events.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nreturn new class () extends Migration {\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('activity_logs', function (Blueprint $table) {\n            $table->unsignedInteger('api_key_id')->nullable()->after('actor_id');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('activity_logs', function (Blueprint $table) {\n            $table->dropColumn('api_key_id');\n        });\n    }\n};\n"
  },
  {
    "path": "database/migrations/2022_08_16_214400_add_force_outgoing_ip_column_to_eggs_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddForceOutgoingIpColumnToEggsTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->boolean('force_outgoing_ip')->default(false);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('eggs', function (Blueprint $table) {\n            $table->dropColumn('force_outgoing_ip');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2022_08_16_230204_add_installed_at_column_to_servers_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nclass AddInstalledAtColumnToServersTable extends Migration\n{\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->timestamp('installed_at')->nullable();\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('servers', function (Blueprint $table) {\n            $table->dropColumn('installed_at');\n        });\n    }\n}\n"
  },
  {
    "path": "database/migrations/2022_12_12_213937_update_mail_settings_to_new_format.php",
    "content": "<?php\n\nuse Pterodactyl\\Models\\Setting;\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nreturn new class () extends Migration {\n    private array $keys = [\n        ['mail:host', 'mail:mailers:smtp:host'],\n        ['mail:port', 'mail:mailers:smtp:port'],\n        ['mail:encryption', 'mail:mailers:smtp:encryption'],\n        ['mail:username', 'mail:mailers:smtp:username'],\n        ['mail:password', 'mail:mailers:smtp:password'],\n    ];\n\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        $settings = Setting::all();\n\n        // Gets the first column in our key table and gets all matching settings.\n        $oldKeys = array_column($this->keys, 0);\n        $oldSettings = $settings->filter(fn (Setting $setting) => in_array($setting->key, $oldKeys));\n\n        // Gets the second column in our key table and gets all matching settings.\n        $newKeys = array_column($this->keys, 1);\n        $newSettings = $settings->filter(fn (Setting $setting) => in_array($setting->key, $newKeys));\n\n        // Map all the old settings to their new key.\n        $oldSettings->map(function (Setting $setting) use ($oldKeys) {\n            $row = array_search($setting->key, $oldKeys, true);\n            $setting->key = $this->keys[$row][1];\n\n            return $setting;\n            // Check if any settings with the new key already exist.\n        })->filter(function (Setting $setting) use ($newSettings) {\n            if ($newSettings->contains('key', $setting->key)) {\n                return false;\n            }\n\n            return true;\n            // Update the settings to use their new keys if they don't already exist.\n        })->each(fn (Setting $setting) => $setting->save());\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        DB::transaction(function () {\n            $settings = Setting::all();\n\n            // Gets the second column in our key table and gets all matching settings.\n            $newKeys = array_column($this->keys, 0);\n            $newSettings = $settings->filter(fn (Setting $setting) => in_array($setting->key, $newKeys));\n\n            // Delete all settings that already have the new key.\n            $newSettings->each(fn (Setting $setting) => $setting->delete());\n\n            // Gets the first column in our key table and gets all matching settings.\n            $oldKeys = array_column($this->keys, 1);\n            $oldSettings = $settings->filter(fn (Setting $setting) => in_array($setting->key, $oldKeys));\n\n            // Map all the old settings to their new key.\n            $oldSettings->map(function (Setting $setting) use ($oldKeys) {\n                $row = array_search($setting->key, $oldKeys, true);\n                $setting->key = $this->keys[$row][0];\n\n                return $setting;\n                // Update the settings to use their new keys if they don't already exist.\n            })->each(fn (Setting $setting) => $setting->save());\n        });\n    }\n};\n"
  },
  {
    "path": "database/migrations/2023_01_24_210051_add_uuid_column_to_failed_jobs_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nreturn new class () extends Migration {\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('failed_jobs', function (Blueprint $table) {\n            $table->string('uuid')->after('id')->nullable()->unique();\n        });\n\n        DB::table('failed_jobs')->whereNull('uuid')->cursor()->each(function ($job) {\n            DB::table('failed_jobs')\n                ->where('id', $job->id)\n                ->update(['uuid' => (string) Illuminate\\Support\\Str::uuid()]);\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('failed_jobs', function (Blueprint $table) {\n            $table->dropColumn('uuid');\n        });\n    }\n};\n"
  },
  {
    "path": "database/migrations/2023_02_23_191004_add_expires_at_column_to_api_keys_table.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Schema;\nuse Illuminate\\Database\\Schema\\Blueprint;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nreturn new class () extends Migration {\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->timestamp('expires_at')->nullable()->after('last_used_at');\n        });\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        Schema::table('api_keys', function (Blueprint $table) {\n            $table->dropColumn('expires_at');\n        });\n    }\n};\n"
  },
  {
    "path": "database/migrations/2024_07_13_091852_clear_unused_allocation_notes.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\DB;\nuse Illuminate\\Database\\Migrations\\Migration;\n\nreturn new class () extends Migration {\n    /**\n     * Run the migrations.\n     */\n    public function up(): void\n    {\n\n        DB::table('allocations')\n            ->whereNull('server_id')\n            ->update(['notes' => null]);\n\n    }\n\n    /**\n     * Reverse the migrations.\n     */\n    public function down(): void\n    {\n        // Reverse not needed\n    }\n};\n"
  },
  {
    "path": "database/schema/mysql-schema.sql",
    "content": "/*!40103 SET @OLD_TIME_ZONE=@@TIME_ZONE */;\n/*!40103 SET TIME_ZONE='+00:00' */;\n/*!40014 SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0 */;\n/*!40014 SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0 */;\n/*!40101 SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='NO_AUTO_VALUE_ON_ZERO' */;\n/*!40111 SET @OLD_SQL_NOTES=@@SQL_NOTES, SQL_NOTES=0 */;\nDROP TABLE IF EXISTS `activity_log_subjects`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `activity_log_subjects` (\n  `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,\n  `activity_log_id` bigint(20) unsigned NOT NULL,\n  `subject_type` varchar(191) NOT NULL,\n  `subject_id` bigint(20) unsigned NOT NULL,\n  PRIMARY KEY (`id`),\n  KEY `activity_log_subjects_activity_log_id_foreign` (`activity_log_id`),\n  KEY `activity_log_subjects_subject_type_subject_id_index` (`subject_type`,`subject_id`),\n  CONSTRAINT `activity_log_subjects_activity_log_id_foreign` FOREIGN KEY (`activity_log_id`) REFERENCES `activity_logs` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `activity_logs`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `activity_logs` (\n  `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,\n  `batch` char(36) DEFAULT NULL,\n  `event` varchar(191) NOT NULL,\n  `ip` varchar(191) NOT NULL,\n  `description` text DEFAULT NULL,\n  `actor_type` varchar(191) DEFAULT NULL,\n  `actor_id` bigint(20) unsigned DEFAULT NULL,\n  `api_key_id` int(10) unsigned DEFAULT NULL,\n  `properties` longtext CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NOT NULL CHECK (json_valid(`properties`)),\n  `timestamp` timestamp NOT NULL DEFAULT current_timestamp(),\n  PRIMARY KEY (`id`),\n  KEY `activity_logs_actor_type_actor_id_index` (`actor_type`,`actor_id`),\n  KEY `activity_logs_event_index` (`event`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `allocations`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `allocations` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `node_id` int(10) unsigned NOT NULL,\n  `ip` varchar(191) NOT NULL,\n  `ip_alias` text DEFAULT NULL,\n  `port` mediumint(8) unsigned NOT NULL,\n  `server_id` int(10) unsigned DEFAULT NULL,\n  `notes` varchar(191) DEFAULT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `allocations_node_id_ip_port_unique` (`node_id`,`ip`,`port`),\n  KEY `allocations_server_id_foreign` (`server_id`),\n  CONSTRAINT `allocations_node_id_foreign` FOREIGN KEY (`node_id`) REFERENCES `nodes` (`id`) ON DELETE CASCADE,\n  CONSTRAINT `allocations_server_id_foreign` FOREIGN KEY (`server_id`) REFERENCES `servers` (`id`) ON DELETE SET NULL\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `api_keys`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `api_keys` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `user_id` int(10) unsigned NOT NULL,\n  `key_type` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `identifier` char(16) DEFAULT NULL,\n  `token` text NOT NULL,\n  `allowed_ips` text DEFAULT NULL,\n  `memo` text DEFAULT NULL,\n  `last_used_at` timestamp NULL DEFAULT NULL,\n  `expires_at` timestamp NULL DEFAULT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  `r_servers` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `r_nodes` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `r_allocations` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `r_users` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `r_locations` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `r_nests` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `r_eggs` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `r_database_hosts` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `r_server_databases` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `api_keys_identifier_unique` (`identifier`),\n  KEY `api_keys_user_id_foreign` (`user_id`),\n  CONSTRAINT `api_keys_user_id_foreign` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `api_logs`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `api_logs` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `authorized` tinyint(1) NOT NULL,\n  `error` text DEFAULT NULL,\n  `key` char(16) DEFAULT NULL,\n  `method` char(6) NOT NULL,\n  `route` text NOT NULL,\n  `content` text DEFAULT NULL,\n  `user_agent` text NOT NULL,\n  `request_ip` varchar(45) NOT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `audit_logs`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `audit_logs` (\n  `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,\n  `uuid` char(36) NOT NULL,\n  `is_system` tinyint(1) NOT NULL DEFAULT 0,\n  `user_id` int(10) unsigned DEFAULT NULL,\n  `server_id` int(10) unsigned DEFAULT NULL,\n  `action` varchar(191) NOT NULL,\n  `subaction` varchar(191) DEFAULT NULL,\n  `device` longtext CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NOT NULL CHECK (json_valid(`device`)),\n  `metadata` longtext CHARACTER SET utf8mb4 COLLATE utf8mb4_bin NOT NULL CHECK (json_valid(`metadata`)),\n  `created_at` timestamp NOT NULL,\n  PRIMARY KEY (`id`),\n  KEY `audit_logs_user_id_foreign` (`user_id`),\n  KEY `audit_logs_server_id_foreign` (`server_id`),\n  KEY `audit_logs_action_server_id_index` (`action`,`server_id`),\n  CONSTRAINT `audit_logs_server_id_foreign` FOREIGN KEY (`server_id`) REFERENCES `servers` (`id`) ON DELETE CASCADE,\n  CONSTRAINT `audit_logs_user_id_foreign` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`) ON DELETE SET NULL\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `backups`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `backups` (\n  `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,\n  `server_id` int(10) unsigned NOT NULL,\n  `uuid` char(36) NOT NULL,\n  `upload_id` text DEFAULT NULL,\n  `is_successful` tinyint(1) NOT NULL DEFAULT 0,\n  `is_locked` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `name` varchar(191) NOT NULL,\n  `ignored_files` text NOT NULL,\n  `disk` varchar(191) NOT NULL,\n  `checksum` varchar(191) DEFAULT NULL,\n  `bytes` bigint(20) unsigned NOT NULL DEFAULT 0,\n  `completed_at` timestamp NULL DEFAULT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  `deleted_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `backups_uuid_unique` (`uuid`),\n  KEY `backups_server_id_foreign` (`server_id`),\n  CONSTRAINT `backups_server_id_foreign` FOREIGN KEY (`server_id`) REFERENCES `servers` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `database_hosts`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `database_hosts` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `name` varchar(191) NOT NULL,\n  `host` varchar(191) NOT NULL,\n  `port` int(10) unsigned NOT NULL,\n  `username` varchar(191) NOT NULL,\n  `password` text NOT NULL,\n  `max_databases` int(10) unsigned DEFAULT NULL,\n  `node_id` int(10) unsigned DEFAULT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  KEY `database_hosts_node_id_foreign` (`node_id`),\n  CONSTRAINT `database_hosts_node_id_foreign` FOREIGN KEY (`node_id`) REFERENCES `nodes` (`id`) ON DELETE SET NULL\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `databases`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `databases` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `server_id` int(10) unsigned NOT NULL,\n  `database_host_id` int(10) unsigned NOT NULL,\n  `database` varchar(191) NOT NULL,\n  `username` varchar(191) NOT NULL,\n  `remote` varchar(191) NOT NULL DEFAULT '%',\n  `password` text NOT NULL,\n  `max_connections` int(11) DEFAULT 0,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `databases_database_host_id_username_unique` (`database_host_id`,`username`),\n  UNIQUE KEY `databases_database_host_id_server_id_database_unique` (`database_host_id`,`server_id`,`database`),\n  KEY `databases_server_id_foreign` (`server_id`),\n  CONSTRAINT `databases_database_host_id_foreign` FOREIGN KEY (`database_host_id`) REFERENCES `database_hosts` (`id`),\n  CONSTRAINT `databases_server_id_foreign` FOREIGN KEY (`server_id`) REFERENCES `servers` (`id`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `egg_mount`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `egg_mount` (\n  `egg_id` int(10) unsigned NOT NULL,\n  `mount_id` int(10) unsigned NOT NULL,\n  UNIQUE KEY `egg_mount_egg_id_mount_id_unique` (`egg_id`,`mount_id`),\n  KEY `egg_mount_mount_id_foreign` (`mount_id`),\n  CONSTRAINT `egg_mount_egg_id_foreign` FOREIGN KEY (`egg_id`) REFERENCES `eggs` (`id`) ON DELETE CASCADE ON UPDATE CASCADE,\n  CONSTRAINT `egg_mount_mount_id_foreign` FOREIGN KEY (`mount_id`) REFERENCES `mounts` (`id`) ON DELETE CASCADE ON UPDATE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `egg_variables`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `egg_variables` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `egg_id` int(10) unsigned NOT NULL,\n  `name` varchar(191) NOT NULL,\n  `description` text NOT NULL,\n  `env_variable` varchar(191) NOT NULL,\n  `default_value` text NOT NULL,\n  `user_viewable` tinyint(3) unsigned NOT NULL,\n  `user_editable` tinyint(3) unsigned NOT NULL,\n  `rules` text DEFAULT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  KEY `service_variables_egg_id_foreign` (`egg_id`),\n  CONSTRAINT `service_variables_egg_id_foreign` FOREIGN KEY (`egg_id`) REFERENCES `eggs` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `eggs`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `eggs` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `uuid` char(36) NOT NULL,\n  `nest_id` int(10) unsigned NOT NULL,\n  `author` varchar(191) NOT NULL,\n  `name` varchar(191) NOT NULL,\n  `description` text DEFAULT NULL,\n  `features` longtext CHARACTER SET utf8mb4 COLLATE utf8mb4_bin DEFAULT NULL CHECK (json_valid(`features`)),\n  `docker_images` longtext CHARACTER SET utf8mb4 COLLATE utf8mb4_bin DEFAULT NULL CHECK (json_valid(`docker_images`)),\n  `file_denylist` longtext CHARACTER SET utf8mb4 COLLATE utf8mb4_bin DEFAULT NULL CHECK (json_valid(`file_denylist`)),\n  `update_url` text DEFAULT NULL,\n  `config_files` text DEFAULT NULL,\n  `config_startup` text DEFAULT NULL,\n  `config_logs` text DEFAULT NULL,\n  `config_stop` varchar(191) DEFAULT NULL,\n  `config_from` int(10) unsigned DEFAULT NULL,\n  `startup` text DEFAULT NULL,\n  `script_container` varchar(191) NOT NULL DEFAULT 'alpine:3.4',\n  `copy_script_from` int(10) unsigned DEFAULT NULL,\n  `script_entry` varchar(191) NOT NULL DEFAULT 'ash',\n  `script_is_privileged` tinyint(1) NOT NULL DEFAULT 1,\n  `script_install` text DEFAULT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  `force_outgoing_ip` tinyint(1) NOT NULL DEFAULT 0,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `service_options_uuid_unique` (`uuid`),\n  KEY `service_options_nest_id_foreign` (`nest_id`),\n  KEY `eggs_config_from_foreign` (`config_from`),\n  KEY `eggs_copy_script_from_foreign` (`copy_script_from`),\n  CONSTRAINT `eggs_config_from_foreign` FOREIGN KEY (`config_from`) REFERENCES `eggs` (`id`) ON DELETE SET NULL,\n  CONSTRAINT `eggs_copy_script_from_foreign` FOREIGN KEY (`copy_script_from`) REFERENCES `eggs` (`id`) ON DELETE SET NULL,\n  CONSTRAINT `service_options_nest_id_foreign` FOREIGN KEY (`nest_id`) REFERENCES `nests` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `failed_jobs`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `failed_jobs` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `uuid` varchar(191) DEFAULT NULL,\n  `connection` text NOT NULL,\n  `queue` text NOT NULL,\n  `payload` longtext NOT NULL,\n  `failed_at` timestamp NOT NULL,\n  `exception` text NOT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `failed_jobs_uuid_unique` (`uuid`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `jobs`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `jobs` (\n  `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,\n  `queue` varchar(191) NOT NULL,\n  `payload` longtext NOT NULL,\n  `attempts` tinyint(3) unsigned NOT NULL,\n  `reserved_at` int(10) unsigned DEFAULT NULL,\n  `available_at` int(10) unsigned NOT NULL,\n  `created_at` int(10) unsigned NOT NULL,\n  PRIMARY KEY (`id`),\n  KEY `jobs_queue_reserved_at_index` (`queue`,`reserved_at`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `locations`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `locations` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `short` varchar(191) NOT NULL,\n  `long` text DEFAULT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `locations_short_unique` (`short`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `migrations`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `migrations` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `migration` varchar(191) NOT NULL,\n  `batch` int(11) NOT NULL,\n  PRIMARY KEY (`id`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `mount_node`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `mount_node` (\n  `node_id` int(10) unsigned NOT NULL,\n  `mount_id` int(10) unsigned NOT NULL,\n  UNIQUE KEY `mount_node_node_id_mount_id_unique` (`node_id`,`mount_id`),\n  KEY `mount_node_mount_id_foreign` (`mount_id`),\n  CONSTRAINT `mount_node_mount_id_foreign` FOREIGN KEY (`mount_id`) REFERENCES `mounts` (`id`) ON DELETE CASCADE ON UPDATE CASCADE,\n  CONSTRAINT `mount_node_node_id_foreign` FOREIGN KEY (`node_id`) REFERENCES `nodes` (`id`) ON DELETE CASCADE ON UPDATE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `mount_server`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `mount_server` (\n  `server_id` int(10) unsigned NOT NULL,\n  `mount_id` int(10) unsigned NOT NULL,\n  UNIQUE KEY `mount_server_server_id_mount_id_unique` (`server_id`,`mount_id`),\n  KEY `mount_server_mount_id_foreign` (`mount_id`),\n  CONSTRAINT `mount_server_mount_id_foreign` FOREIGN KEY (`mount_id`) REFERENCES `mounts` (`id`) ON DELETE CASCADE ON UPDATE CASCADE,\n  CONSTRAINT `mount_server_server_id_foreign` FOREIGN KEY (`server_id`) REFERENCES `servers` (`id`) ON DELETE CASCADE ON UPDATE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `mounts`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `mounts` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `uuid` char(36) NOT NULL,\n  `name` varchar(191) NOT NULL,\n  `description` text DEFAULT NULL,\n  `source` varchar(191) NOT NULL,\n  `target` varchar(191) NOT NULL,\n  `read_only` tinyint(3) unsigned NOT NULL,\n  `user_mountable` tinyint(3) unsigned NOT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `mounts_id_unique` (`id`),\n  UNIQUE KEY `mounts_uuid_unique` (`uuid`),\n  UNIQUE KEY `mounts_name_unique` (`name`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `nests`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `nests` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `uuid` char(36) NOT NULL,\n  `author` char(191) NOT NULL,\n  `name` varchar(191) NOT NULL,\n  `description` text DEFAULT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `services_uuid_unique` (`uuid`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `nodes`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `nodes` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `uuid` char(36) NOT NULL,\n  `public` smallint(5) unsigned NOT NULL,\n  `name` varchar(191) NOT NULL,\n  `description` text DEFAULT NULL,\n  `location_id` int(10) unsigned NOT NULL,\n  `fqdn` varchar(191) NOT NULL,\n  `scheme` varchar(191) NOT NULL DEFAULT 'https',\n  `behind_proxy` tinyint(1) NOT NULL DEFAULT 0,\n  `maintenance_mode` tinyint(1) NOT NULL DEFAULT 0,\n  `memory` int(10) unsigned NOT NULL,\n  `memory_overallocate` int(11) NOT NULL DEFAULT 0,\n  `disk` int(10) unsigned NOT NULL,\n  `disk_overallocate` int(11) NOT NULL DEFAULT 0,\n  `upload_size` int(10) unsigned NOT NULL DEFAULT 100,\n  `daemon_token_id` char(16) NOT NULL,\n  `daemon_token` text NOT NULL,\n  `daemonListen` smallint(5) unsigned NOT NULL DEFAULT 8080,\n  `daemonSFTP` smallint(5) unsigned NOT NULL DEFAULT 2022,\n  `daemonBase` varchar(191) NOT NULL DEFAULT '/home/daemon-files',\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `nodes_uuid_unique` (`uuid`),\n  UNIQUE KEY `nodes_daemon_token_id_unique` (`daemon_token_id`),\n  KEY `nodes_location_id_foreign` (`location_id`),\n  CONSTRAINT `nodes_location_id_foreign` FOREIGN KEY (`location_id`) REFERENCES `locations` (`id`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `notifications`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `notifications` (\n  `id` varchar(191) NOT NULL,\n  `type` varchar(191) NOT NULL,\n  `notifiable_type` varchar(191) NOT NULL,\n  `notifiable_id` bigint(20) unsigned NOT NULL,\n  `data` text NOT NULL,\n  `read_at` timestamp NULL DEFAULT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  KEY `notifications_notifiable_type_notifiable_id_index` (`notifiable_type`,`notifiable_id`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `password_resets`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `password_resets` (\n  `email` varchar(191) NOT NULL,\n  `token` varchar(191) NOT NULL,\n  `created_at` timestamp NOT NULL,\n  KEY `password_resets_email_index` (`email`),\n  KEY `password_resets_token_index` (`token`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `recovery_tokens`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `recovery_tokens` (\n  `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,\n  `user_id` int(10) unsigned NOT NULL,\n  `token` varchar(191) NOT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  KEY `recovery_tokens_user_id_foreign` (`user_id`),\n  CONSTRAINT `recovery_tokens_user_id_foreign` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `schedules`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `schedules` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `server_id` int(10) unsigned NOT NULL,\n  `name` varchar(191) NOT NULL,\n  `cron_day_of_week` varchar(191) NOT NULL,\n  `cron_month` varchar(191) NOT NULL,\n  `cron_day_of_month` varchar(191) NOT NULL,\n  `cron_hour` varchar(191) NOT NULL,\n  `cron_minute` varchar(191) NOT NULL,\n  `is_active` tinyint(1) NOT NULL,\n  `is_processing` tinyint(1) NOT NULL,\n  `only_when_online` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `last_run_at` timestamp NULL DEFAULT NULL,\n  `next_run_at` timestamp NULL DEFAULT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  KEY `schedules_server_id_foreign` (`server_id`),\n  CONSTRAINT `schedules_server_id_foreign` FOREIGN KEY (`server_id`) REFERENCES `servers` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `server_transfers`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `server_transfers` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `server_id` int(10) unsigned NOT NULL,\n  `successful` tinyint(1) DEFAULT NULL,\n  `old_node` int(10) unsigned NOT NULL,\n  `new_node` int(10) unsigned NOT NULL,\n  `old_allocation` int(10) unsigned NOT NULL,\n  `new_allocation` int(10) unsigned NOT NULL,\n  `old_additional_allocations` longtext DEFAULT NULL COMMENT '(DC2Type:json)',\n  `new_additional_allocations` longtext DEFAULT NULL COMMENT '(DC2Type:json)',\n  `archived` tinyint(1) NOT NULL DEFAULT 0,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  KEY `server_transfers_server_id_foreign` (`server_id`),\n  CONSTRAINT `server_transfers_server_id_foreign` FOREIGN KEY (`server_id`) REFERENCES `servers` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `server_variables`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `server_variables` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `server_id` int(10) unsigned DEFAULT NULL,\n  `variable_id` int(10) unsigned NOT NULL,\n  `variable_value` text NOT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  KEY `server_variables_server_id_foreign` (`server_id`),\n  KEY `server_variables_variable_id_foreign` (`variable_id`),\n  CONSTRAINT `server_variables_server_id_foreign` FOREIGN KEY (`server_id`) REFERENCES `servers` (`id`) ON DELETE CASCADE,\n  CONSTRAINT `server_variables_variable_id_foreign` FOREIGN KEY (`variable_id`) REFERENCES `egg_variables` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `servers`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `servers` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `external_id` varchar(191) DEFAULT NULL,\n  `uuid` char(36) NOT NULL,\n  `uuidShort` char(8) NOT NULL,\n  `node_id` int(10) unsigned NOT NULL,\n  `name` varchar(191) NOT NULL,\n  `description` text NOT NULL,\n  `status` varchar(191) DEFAULT NULL,\n  `skip_scripts` tinyint(1) NOT NULL DEFAULT 0,\n  `owner_id` int(10) unsigned NOT NULL,\n  `memory` int(10) unsigned NOT NULL,\n  `swap` int(11) NOT NULL,\n  `disk` int(10) unsigned NOT NULL,\n  `io` int(10) unsigned NOT NULL,\n  `cpu` int(10) unsigned NOT NULL,\n  `threads` varchar(191) DEFAULT NULL,\n  `oom_disabled` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `allocation_id` int(10) unsigned NOT NULL,\n  `nest_id` int(10) unsigned NOT NULL,\n  `egg_id` int(10) unsigned NOT NULL,\n  `startup` text NOT NULL,\n  `image` varchar(191) NOT NULL,\n  `allocation_limit` int(10) unsigned DEFAULT NULL,\n  `database_limit` int(10) unsigned DEFAULT 0,\n  `backup_limit` int(10) unsigned NOT NULL DEFAULT 0,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  `installed_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `servers_uuid_unique` (`uuid`),\n  UNIQUE KEY `servers_uuidshort_unique` (`uuidShort`),\n  UNIQUE KEY `servers_allocation_id_unique` (`allocation_id`),\n  UNIQUE KEY `servers_external_id_unique` (`external_id`),\n  KEY `servers_node_id_foreign` (`node_id`),\n  KEY `servers_owner_id_foreign` (`owner_id`),\n  KEY `servers_nest_id_foreign` (`nest_id`),\n  KEY `servers_egg_id_foreign` (`egg_id`),\n  CONSTRAINT `servers_allocation_id_foreign` FOREIGN KEY (`allocation_id`) REFERENCES `allocations` (`id`),\n  CONSTRAINT `servers_egg_id_foreign` FOREIGN KEY (`egg_id`) REFERENCES `eggs` (`id`),\n  CONSTRAINT `servers_nest_id_foreign` FOREIGN KEY (`nest_id`) REFERENCES `nests` (`id`),\n  CONSTRAINT `servers_node_id_foreign` FOREIGN KEY (`node_id`) REFERENCES `nodes` (`id`),\n  CONSTRAINT `servers_owner_id_foreign` FOREIGN KEY (`owner_id`) REFERENCES `users` (`id`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `sessions`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `sessions` (\n  `id` varchar(191) NOT NULL,\n  `user_id` int(11) DEFAULT NULL,\n  `ip_address` varchar(45) DEFAULT NULL,\n  `user_agent` text DEFAULT NULL,\n  `payload` text NOT NULL,\n  `last_activity` int(11) NOT NULL,\n  UNIQUE KEY `sessions_id_unique` (`id`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `settings`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `settings` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `key` varchar(191) NOT NULL,\n  `value` text NOT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `settings_key_unique` (`key`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `subusers`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `subusers` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `user_id` int(10) unsigned NOT NULL,\n  `server_id` int(10) unsigned NOT NULL,\n  `permissions` longtext CHARACTER SET utf8mb4 COLLATE utf8mb4_bin DEFAULT NULL CHECK (json_valid(`permissions`)),\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  KEY `subusers_user_id_foreign` (`user_id`),\n  KEY `subusers_server_id_foreign` (`server_id`),\n  CONSTRAINT `subusers_server_id_foreign` FOREIGN KEY (`server_id`) REFERENCES `servers` (`id`) ON DELETE CASCADE,\n  CONSTRAINT `subusers_user_id_foreign` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `tasks`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `tasks` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `schedule_id` int(10) unsigned NOT NULL,\n  `sequence_id` int(10) unsigned NOT NULL,\n  `action` varchar(191) NOT NULL,\n  `payload` text NOT NULL,\n  `time_offset` int(10) unsigned NOT NULL,\n  `is_queued` tinyint(1) NOT NULL,\n  `continue_on_failure` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  KEY `tasks_schedule_id_sequence_id_index` (`schedule_id`,`sequence_id`),\n  CONSTRAINT `tasks_schedule_id_foreign` FOREIGN KEY (`schedule_id`) REFERENCES `schedules` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `tasks_log`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `tasks_log` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `task_id` int(10) unsigned NOT NULL,\n  `run_time` timestamp NOT NULL,\n  `run_status` int(10) unsigned NOT NULL,\n  `response` text NOT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `user_ssh_keys`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `user_ssh_keys` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `user_id` int(10) unsigned NOT NULL,\n  `name` varchar(191) NOT NULL,\n  `fingerprint` varchar(191) NOT NULL,\n  `public_key` text NOT NULL,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  `deleted_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  KEY `user_ssh_keys_user_id_foreign` (`user_id`),\n  CONSTRAINT `user_ssh_keys_user_id_foreign` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`) ON DELETE CASCADE\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\nDROP TABLE IF EXISTS `users`;\n/*!40101 SET @saved_cs_client     = @@character_set_client */;\n/*!40101 SET character_set_client = utf8 */;\nCREATE TABLE `users` (\n  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,\n  `external_id` varchar(191) DEFAULT NULL,\n  `uuid` char(36) NOT NULL,\n  `username` varchar(191) NOT NULL,\n  `email` varchar(191) NOT NULL,\n  `name_first` varchar(191) DEFAULT NULL,\n  `name_last` varchar(191) DEFAULT NULL,\n  `password` text NOT NULL,\n  `remember_token` varchar(191) DEFAULT NULL,\n  `language` char(5) NOT NULL DEFAULT 'en',\n  `root_admin` tinyint(3) unsigned NOT NULL DEFAULT 0,\n  `use_totp` tinyint(3) unsigned NOT NULL,\n  `totp_secret` text DEFAULT NULL,\n  `totp_authenticated_at` timestamp NULL DEFAULT NULL,\n  `gravatar` tinyint(1) NOT NULL DEFAULT 1,\n  `created_at` timestamp NULL DEFAULT NULL,\n  `updated_at` timestamp NULL DEFAULT NULL,\n  PRIMARY KEY (`id`),\n  UNIQUE KEY `users_uuid_unique` (`uuid`),\n  UNIQUE KEY `users_email_unique` (`email`),\n  UNIQUE KEY `users_username_unique` (`username`),\n  KEY `users_external_id_index` (`external_id`)\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;\n/*!40101 SET character_set_client = @saved_cs_client */;\n/*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */;\n\n/*!40101 SET SQL_MODE=@OLD_SQL_MODE */;\n/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */;\n/*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */;\n/*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */;\n\nINSERT INTO `migrations` VALUES (1,'2016_01_23_195641_add_allocations_table',1);\nINSERT INTO `migrations` VALUES (2,'2016_01_23_195851_add_api_keys',1);\nINSERT INTO `migrations` VALUES (3,'2016_01_23_200044_add_api_permissions',1);\nINSERT INTO `migrations` VALUES (4,'2016_01_23_200159_add_downloads',1);\nINSERT INTO `migrations` VALUES (5,'2016_01_23_200421_create_failed_jobs_table',1);\nINSERT INTO `migrations` VALUES (6,'2016_01_23_200440_create_jobs_table',1);\nINSERT INTO `migrations` VALUES (7,'2016_01_23_200528_add_locations',1);\nINSERT INTO `migrations` VALUES (8,'2016_01_23_200648_add_nodes',1);\nINSERT INTO `migrations` VALUES (9,'2016_01_23_201433_add_password_resets',1);\nINSERT INTO `migrations` VALUES (10,'2016_01_23_201531_add_permissions',1);\nINSERT INTO `migrations` VALUES (11,'2016_01_23_201649_add_server_variables',1);\nINSERT INTO `migrations` VALUES (12,'2016_01_23_201748_add_servers',1);\nINSERT INTO `migrations` VALUES (13,'2016_01_23_202544_add_service_options',1);\nINSERT INTO `migrations` VALUES (14,'2016_01_23_202731_add_service_varibles',1);\nINSERT INTO `migrations` VALUES (15,'2016_01_23_202943_add_services',1);\nINSERT INTO `migrations` VALUES (16,'2016_01_23_203119_create_settings_table',1);\nINSERT INTO `migrations` VALUES (17,'2016_01_23_203150_add_subusers',1);\nINSERT INTO `migrations` VALUES (18,'2016_01_23_203159_add_users',1);\nINSERT INTO `migrations` VALUES (19,'2016_01_23_203947_create_sessions_table',1);\nINSERT INTO `migrations` VALUES (20,'2016_01_25_234418_rename_permissions_column',1);\nINSERT INTO `migrations` VALUES (21,'2016_02_07_172148_add_databases_tables',1);\nINSERT INTO `migrations` VALUES (22,'2016_02_07_181319_add_database_servers_table',1);\nINSERT INTO `migrations` VALUES (23,'2016_02_13_154306_add_service_option_default_startup',1);\nINSERT INTO `migrations` VALUES (24,'2016_02_20_155318_add_unique_service_field',1);\nINSERT INTO `migrations` VALUES (25,'2016_02_27_163411_add_tasks_table',1);\nINSERT INTO `migrations` VALUES (26,'2016_02_27_163447_add_tasks_log_table',1);\nINSERT INTO `migrations` VALUES (27,'2016_03_18_155649_add_nullable_field_lastrun',1);\nINSERT INTO `migrations` VALUES (28,'2016_08_30_212718_add_ip_alias',1);\nINSERT INTO `migrations` VALUES (29,'2016_08_30_213301_modify_ip_storage_method',1);\nINSERT INTO `migrations` VALUES (30,'2016_09_01_193520_add_suspension_for_servers',1);\nINSERT INTO `migrations` VALUES (31,'2016_09_01_211924_remove_active_column',1);\nINSERT INTO `migrations` VALUES (32,'2016_09_02_190647_add_sftp_password_storage',1);\nINSERT INTO `migrations` VALUES (33,'2016_09_04_171338_update_jobs_tables',1);\nINSERT INTO `migrations` VALUES (34,'2016_09_04_172028_update_failed_jobs_table',1);\nINSERT INTO `migrations` VALUES (35,'2016_09_04_182835_create_notifications_table',1);\nINSERT INTO `migrations` VALUES (36,'2016_09_07_163017_add_unique_identifier',1);\nINSERT INTO `migrations` VALUES (37,'2016_09_14_145945_allow_longer_regex_field',1);\nINSERT INTO `migrations` VALUES (38,'2016_09_17_194246_add_docker_image_column',1);\nINSERT INTO `migrations` VALUES (39,'2016_09_21_165554_update_servers_column_name',1);\nINSERT INTO `migrations` VALUES (40,'2016_09_29_213518_rename_double_insurgency',1);\nINSERT INTO `migrations` VALUES (41,'2016_10_07_152117_build_api_log_table',1);\nINSERT INTO `migrations` VALUES (42,'2016_10_14_164802_update_api_keys',1);\nINSERT INTO `migrations` VALUES (43,'2016_10_23_181719_update_misnamed_bungee',1);\nINSERT INTO `migrations` VALUES (44,'2016_10_23_193810_add_foreign_keys_servers',1);\nINSERT INTO `migrations` VALUES (45,'2016_10_23_201624_add_foreign_allocations',1);\nINSERT INTO `migrations` VALUES (46,'2016_10_23_202222_add_foreign_api_keys',1);\nINSERT INTO `migrations` VALUES (47,'2016_10_23_202703_add_foreign_api_permissions',1);\nINSERT INTO `migrations` VALUES (48,'2016_10_23_202953_add_foreign_database_servers',1);\nINSERT INTO `migrations` VALUES (49,'2016_10_23_203105_add_foreign_databases',1);\nINSERT INTO `migrations` VALUES (50,'2016_10_23_203335_add_foreign_nodes',1);\nINSERT INTO `migrations` VALUES (51,'2016_10_23_203522_add_foreign_permissions',1);\nINSERT INTO `migrations` VALUES (52,'2016_10_23_203857_add_foreign_server_variables',1);\nINSERT INTO `migrations` VALUES (53,'2016_10_23_204157_add_foreign_service_options',1);\nINSERT INTO `migrations` VALUES (54,'2016_10_23_204321_add_foreign_service_variables',1);\nINSERT INTO `migrations` VALUES (55,'2016_10_23_204454_add_foreign_subusers',1);\nINSERT INTO `migrations` VALUES (56,'2016_10_23_204610_add_foreign_tasks',1);\nINSERT INTO `migrations` VALUES (57,'2016_11_04_000949_add_ark_service_option_fixed',1);\nINSERT INTO `migrations` VALUES (58,'2016_11_11_220649_add_pack_support',1);\nINSERT INTO `migrations` VALUES (59,'2016_11_11_231731_set_service_name_unique',1);\nINSERT INTO `migrations` VALUES (60,'2016_11_27_142519_add_pack_column',1);\nINSERT INTO `migrations` VALUES (61,'2016_12_01_173018_add_configurable_upload_limit',1);\nINSERT INTO `migrations` VALUES (62,'2016_12_02_185206_correct_service_variables',1);\nINSERT INTO `migrations` VALUES (63,'2017_01_03_150436_fix_misnamed_option_tag',1);\nINSERT INTO `migrations` VALUES (64,'2017_01_07_154228_create_node_configuration_tokens_table',1);\nINSERT INTO `migrations` VALUES (65,'2017_01_12_135449_add_more_user_data',1);\nINSERT INTO `migrations` VALUES (66,'2017_02_02_175548_UpdateColumnNames',1);\nINSERT INTO `migrations` VALUES (67,'2017_02_03_140948_UpdateNodesTable',1);\nINSERT INTO `migrations` VALUES (68,'2017_02_03_155554_RenameColumns',1);\nINSERT INTO `migrations` VALUES (69,'2017_02_05_164123_AdjustColumnNames',1);\nINSERT INTO `migrations` VALUES (70,'2017_02_05_164516_AdjustColumnNamesForServicePacks',1);\nINSERT INTO `migrations` VALUES (71,'2017_02_09_174834_SetupPermissionsPivotTable',1);\nINSERT INTO `migrations` VALUES (72,'2017_02_10_171858_UpdateAPIKeyColumnNames',1);\nINSERT INTO `migrations` VALUES (73,'2017_03_03_224254_UpdateNodeConfigTokensColumns',1);\nINSERT INTO `migrations` VALUES (74,'2017_03_05_212803_DeleteServiceExecutableOption',1);\nINSERT INTO `migrations` VALUES (75,'2017_03_10_162934_AddNewServiceOptionsColumns',1);\nINSERT INTO `migrations` VALUES (76,'2017_03_10_173607_MigrateToNewServiceSystem',1);\nINSERT INTO `migrations` VALUES (77,'2017_03_11_215455_ChangeServiceVariablesValidationRules',1);\nINSERT INTO `migrations` VALUES (78,'2017_03_12_150648_MoveFunctionsFromFileToDatabase',1);\nINSERT INTO `migrations` VALUES (79,'2017_03_14_175631_RenameServicePacksToSingluarPacks',1);\nINSERT INTO `migrations` VALUES (80,'2017_03_14_200326_AddLockedStatusToTable',1);\nINSERT INTO `migrations` VALUES (81,'2017_03_16_181109_ReOrganizeDatabaseServersToDatabaseHost',1);\nINSERT INTO `migrations` VALUES (82,'2017_03_16_181515_CleanupDatabasesDatabase',1);\nINSERT INTO `migrations` VALUES (83,'2017_03_18_204953_AddForeignKeyToPacks',1);\nINSERT INTO `migrations` VALUES (84,'2017_03_31_221948_AddServerDescriptionColumn',1);\nINSERT INTO `migrations` VALUES (85,'2017_04_02_163232_DropDeletedAtColumnFromServers',1);\nINSERT INTO `migrations` VALUES (86,'2017_04_15_125021_UpgradeTaskSystem',1);\nINSERT INTO `migrations` VALUES (87,'2017_04_20_171943_AddScriptsToServiceOptions',1);\nINSERT INTO `migrations` VALUES (88,'2017_04_21_151432_AddServiceScriptTrackingToServers',1);\nINSERT INTO `migrations` VALUES (89,'2017_04_27_145300_AddCopyScriptFromColumn',1);\nINSERT INTO `migrations` VALUES (90,'2017_04_27_223629_AddAbilityToDefineConnectionOverSSLWithDaemonBehindProxy',1);\nINSERT INTO `migrations` VALUES (91,'2017_05_01_141528_DeleteDownloadTable',1);\nINSERT INTO `migrations` VALUES (92,'2017_05_01_141559_DeleteNodeConfigurationTable',1);\nINSERT INTO `migrations` VALUES (93,'2017_06_10_152951_add_external_id_to_users',1);\nINSERT INTO `migrations` VALUES (94,'2017_06_25_133923_ChangeForeignKeyToBeOnCascadeDelete',1);\nINSERT INTO `migrations` VALUES (95,'2017_07_08_152806_ChangeUserPermissionsToDeleteOnUserDeletion',1);\nINSERT INTO `migrations` VALUES (96,'2017_07_08_154416_SetAllocationToReferenceNullOnServerDelete',1);\nINSERT INTO `migrations` VALUES (97,'2017_07_08_154650_CascadeDeletionWhenAServerOrVariableIsDeleted',1);\nINSERT INTO `migrations` VALUES (98,'2017_07_24_194433_DeleteTaskWhenParentServerIsDeleted',1);\nINSERT INTO `migrations` VALUES (99,'2017_08_05_115800_CascadeNullValuesForDatabaseHostWhenNodeIsDeleted',1);\nINSERT INTO `migrations` VALUES (100,'2017_08_05_144104_AllowNegativeValuesForOverallocation',1);\nINSERT INTO `migrations` VALUES (101,'2017_08_05_174811_SetAllocationUnqiueUsingMultipleFields',1);\nINSERT INTO `migrations` VALUES (102,'2017_08_15_214555_CascadeDeletionWhenAParentServiceIsDeleted',1);\nINSERT INTO `migrations` VALUES (103,'2017_08_18_215428_RemovePackWhenParentServiceOptionIsDeleted',1);\nINSERT INTO `migrations` VALUES (104,'2017_09_10_225749_RenameTasksTableForStructureRefactor',1);\nINSERT INTO `migrations` VALUES (105,'2017_09_10_225941_CreateSchedulesTable',1);\nINSERT INTO `migrations` VALUES (106,'2017_09_10_230309_CreateNewTasksTableForSchedules',1);\nINSERT INTO `migrations` VALUES (107,'2017_09_11_002938_TransferOldTasksToNewScheduler',1);\nINSERT INTO `migrations` VALUES (108,'2017_09_13_211810_UpdateOldPermissionsToPointToNewScheduleSystem',1);\nINSERT INTO `migrations` VALUES (109,'2017_09_23_170933_CreateDaemonKeysTable',1);\nINSERT INTO `migrations` VALUES (110,'2017_09_23_173628_RemoveDaemonSecretFromServersTable',1);\nINSERT INTO `migrations` VALUES (111,'2017_09_23_185022_RemoveDaemonSecretFromSubusersTable',1);\nINSERT INTO `migrations` VALUES (112,'2017_10_02_202000_ChangeServicesToUseAMoreUniqueIdentifier',1);\nINSERT INTO `migrations` VALUES (113,'2017_10_02_202007_ChangeToABetterUniqueServiceConfiguration',1);\nINSERT INTO `migrations` VALUES (114,'2017_10_03_233202_CascadeDeletionWhenServiceOptionIsDeleted',1);\nINSERT INTO `migrations` VALUES (115,'2017_10_06_214026_ServicesToNestsConversion',1);\nINSERT INTO `migrations` VALUES (116,'2017_10_06_214053_ServiceOptionsToEggsConversion',1);\nINSERT INTO `migrations` VALUES (117,'2017_10_06_215741_ServiceVariablesToEggVariablesConversion',1);\nINSERT INTO `migrations` VALUES (118,'2017_10_24_222238_RemoveLegacySFTPInformation',1);\nINSERT INTO `migrations` VALUES (119,'2017_11_11_161922_Add2FaLastAuthorizationTimeColumn',1);\nINSERT INTO `migrations` VALUES (120,'2017_11_19_122708_MigratePubPrivFormatToSingleKey',1);\nINSERT INTO `migrations` VALUES (121,'2017_12_04_184012_DropAllocationsWhenNodeIsDeleted',1);\nINSERT INTO `migrations` VALUES (122,'2017_12_12_220426_MigrateSettingsTableToNewFormat',1);\nINSERT INTO `migrations` VALUES (123,'2018_01_01_122821_AllowNegativeValuesForServerSwap',1);\nINSERT INTO `migrations` VALUES (124,'2018_01_11_213943_AddApiKeyPermissionColumns',1);\nINSERT INTO `migrations` VALUES (125,'2018_01_13_142012_SetupTableForKeyEncryption',1);\nINSERT INTO `migrations` VALUES (126,'2018_01_13_145209_AddLastUsedAtColumn',1);\nINSERT INTO `migrations` VALUES (127,'2018_02_04_145617_AllowTextInUserExternalId',1);\nINSERT INTO `migrations` VALUES (128,'2018_02_10_151150_remove_unique_index_on_external_id_column',1);\nINSERT INTO `migrations` VALUES (129,'2018_02_17_134254_ensure_unique_allocation_id_on_servers_table',1);\nINSERT INTO `migrations` VALUES (130,'2018_02_24_112356_add_external_id_column_to_servers_table',1);\nINSERT INTO `migrations` VALUES (131,'2018_02_25_160152_remove_default_null_value_on_table',1);\nINSERT INTO `migrations` VALUES (132,'2018_02_25_160604_define_unique_index_on_users_external_id',1);\nINSERT INTO `migrations` VALUES (133,'2018_03_01_192831_add_database_and_port_limit_columns_to_servers_table',1);\nINSERT INTO `migrations` VALUES (134,'2018_03_15_124536_add_description_to_nodes',1);\nINSERT INTO `migrations` VALUES (135,'2018_05_04_123826_add_maintenance_to_nodes',1);\nINSERT INTO `migrations` VALUES (136,'2018_09_03_143756_allow_egg_variables_to_have_longer_values',1);\nINSERT INTO `migrations` VALUES (137,'2018_09_03_144005_allow_server_variables_to_have_longer_values',1);\nINSERT INTO `migrations` VALUES (138,'2019_03_02_142328_set_allocation_limit_default_null',1);\nINSERT INTO `migrations` VALUES (139,'2019_03_02_151321_fix_unique_index_to_account_for_host',1);\nINSERT INTO `migrations` VALUES (140,'2020_03_22_163911_merge_permissions_table_into_subusers',1);\nINSERT INTO `migrations` VALUES (141,'2020_03_22_164814_drop_permissions_table',1);\nINSERT INTO `migrations` VALUES (142,'2020_04_03_203624_add_threads_column_to_servers_table',1);\nINSERT INTO `migrations` VALUES (143,'2020_04_03_230614_create_backups_table',1);\nINSERT INTO `migrations` VALUES (144,'2020_04_04_131016_add_table_server_transfers',1);\nINSERT INTO `migrations` VALUES (145,'2020_04_10_141024_store_node_tokens_as_encrypted_value',1);\nINSERT INTO `migrations` VALUES (146,'2020_04_17_203438_allow_nullable_descriptions',1);\nINSERT INTO `migrations` VALUES (147,'2020_04_22_055500_add_max_connections_column',1);\nINSERT INTO `migrations` VALUES (148,'2020_04_26_111208_add_backup_limit_to_servers',1);\nINSERT INTO `migrations` VALUES (149,'2020_05_20_234655_add_mounts_table',1);\nINSERT INTO `migrations` VALUES (150,'2020_05_21_192756_add_mount_server_table',1);\nINSERT INTO `migrations` VALUES (151,'2020_07_02_213612_create_user_recovery_tokens_table',1);\nINSERT INTO `migrations` VALUES (152,'2020_07_09_201845_add_notes_column_for_allocations',1);\nINSERT INTO `migrations` VALUES (153,'2020_08_20_205533_add_backup_state_column_to_backups',1);\nINSERT INTO `migrations` VALUES (154,'2020_08_22_132500_update_bytes_to_unsigned_bigint',1);\nINSERT INTO `migrations` VALUES (155,'2020_08_23_175331_modify_checksums_column_for_backups',1);\nINSERT INTO `migrations` VALUES (156,'2020_09_13_110007_drop_packs_from_servers',1);\nINSERT INTO `migrations` VALUES (157,'2020_09_13_110021_drop_packs_from_api_key_permissions',1);\nINSERT INTO `migrations` VALUES (158,'2020_09_13_110047_drop_packs_table',1);\nINSERT INTO `migrations` VALUES (159,'2020_09_13_113503_drop_daemon_key_table',1);\nINSERT INTO `migrations` VALUES (160,'2020_10_10_165437_change_unique_database_name_to_account_for_server',1);\nINSERT INTO `migrations` VALUES (161,'2020_10_26_194904_remove_nullable_from_schedule_name_field',1);\nINSERT INTO `migrations` VALUES (162,'2020_11_02_201014_add_features_column_to_eggs',1);\nINSERT INTO `migrations` VALUES (163,'2020_12_12_102435_support_multiple_docker_images_and_updates',1);\nINSERT INTO `migrations` VALUES (164,'2020_12_14_013707_make_successful_nullable_in_server_transfers',1);\nINSERT INTO `migrations` VALUES (165,'2020_12_17_014330_add_archived_field_to_server_transfers_table',1);\nINSERT INTO `migrations` VALUES (166,'2020_12_24_092449_make_allocation_fields_json',1);\nINSERT INTO `migrations` VALUES (167,'2020_12_26_184914_add_upload_id_column_to_backups_table',1);\nINSERT INTO `migrations` VALUES (168,'2021_01_10_153937_add_file_denylist_to_egg_configs',1);\nINSERT INTO `migrations` VALUES (169,'2021_01_13_013420_add_cron_month',1);\nINSERT INTO `migrations` VALUES (170,'2021_01_17_102401_create_audit_logs_table',1);\nINSERT INTO `migrations` VALUES (171,'2021_01_17_152623_add_generic_server_status_column',1);\nINSERT INTO `migrations` VALUES (172,'2021_01_26_210502_update_file_denylist_to_json',1);\nINSERT INTO `migrations` VALUES (173,'2021_02_23_205021_add_index_for_server_and_action',1);\nINSERT INTO `migrations` VALUES (174,'2021_02_23_212657_make_sftp_port_unsigned_int',1);\nINSERT INTO `migrations` VALUES (175,'2021_03_21_104718_force_cron_month_field_to_have_value_if_missing',1);\nINSERT INTO `migrations` VALUES (176,'2021_05_01_092457_add_continue_on_failure_option_to_tasks',1);\nINSERT INTO `migrations` VALUES (177,'2021_05_01_092523_add_only_run_when_server_online_option_to_schedules',1);\nINSERT INTO `migrations` VALUES (178,'2021_05_03_201016_add_support_for_locking_a_backup',1);\nINSERT INTO `migrations` VALUES (179,'2021_07_12_013420_remove_userinteraction',1);\nINSERT INTO `migrations` VALUES (180,'2021_07_17_211512_create_user_ssh_keys_table',1);\nINSERT INTO `migrations` VALUES (181,'2021_08_03_210600_change_successful_field_to_default_to_false_on_backups_table',1);\nINSERT INTO `migrations` VALUES (182,'2021_08_21_175111_add_foreign_keys_to_mount_node_table',1);\nINSERT INTO `migrations` VALUES (183,'2021_08_21_175118_add_foreign_keys_to_mount_server_table',1);\nINSERT INTO `migrations` VALUES (184,'2021_08_21_180921_add_foreign_keys_to_egg_mount_table',1);\nINSERT INTO `migrations` VALUES (185,'2022_01_25_030847_drop_google_analytics',1);\nINSERT INTO `migrations` VALUES (186,'2022_05_07_165334_migrate_egg_images_array_to_new_format',1);\nINSERT INTO `migrations` VALUES (187,'2022_05_28_135717_create_activity_logs_table',1);\nINSERT INTO `migrations` VALUES (188,'2022_05_29_140349_create_activity_log_actors_table',1);\nINSERT INTO `migrations` VALUES (189,'2022_06_18_112822_track_api_key_usage_for_activity_events',1);\nINSERT INTO `migrations` VALUES (190,'2022_08_16_214400_add_force_outgoing_ip_column_to_eggs_table',1);\nINSERT INTO `migrations` VALUES (191,'2022_08_16_230204_add_installed_at_column_to_servers_table',1);\nINSERT INTO `migrations` VALUES (192,'2022_12_12_213937_update_mail_settings_to_new_format',1);\nINSERT INTO `migrations` VALUES (193,'2023_01_24_210051_add_uuid_column_to_failed_jobs_table',1);\nINSERT INTO `migrations` VALUES (194,'2023_02_23_191004_add_expires_at_column_to_api_keys_table',1);\n"
  },
  {
    "path": "docker-compose.example.yml",
    "content": "x-common:\n  database:\n    &db-environment\n    # 不要将下面行尾 \"&db-password\" 删除，这对面板功能很重要。\n    MYSQL_PASSWORD: &db-password \"CHANGE_ME\"\n    MYSQL_ROOT_PASSWORD: \"CHANGE_ME_TOO\"\n  panel:\n    &panel-environment\n    APP_URL: \"http://example.com\"\n    # 可以在这里找到有效时区列表：http://php.net/manual/zh/timezones.php\n    APP_TIMEZONE: \"Asia/Shanghai\"\n    APP_SERVICE_AUTHOR: \"noreply@example.com\"\n    # 如果您想使用 Let's Encrypt 为面板生成 SSL 证书，请取消下面的注释行并写入配置\n    # LE_EMAIL: \"\"\n  mail:\n    &mail-environment\n    MAIL_FROM: \"noreply@example.com\"\n    MAIL_DRIVER: \"smtp\"\n    MAIL_HOST: \"mail\"\n    MAIL_PORT: \"1025\"\n    MAIL_USERNAME: \"\"\n    MAIL_PASSWORD: \"\"\n    MAIL_ENCRYPTION: \"true\"\n\n#\n# ------------------------------------------------------------------------------------------\n# 下面的危险区域\n#\n# 该文件的其余部分可能不需要更改。 请仅在您了解自己在做什么的情况下进行以下修改。\n#\nservices:\n  database:\n    image: mariadb:11\n    restart: always\n    command: --default-authentication-plugin=mysql_native_password\n    volumes:\n      - \"/srv/pterodactyl/database:/var/lib/mysql\"\n    environment:\n      <<: *db-environment\n      MYSQL_DATABASE: \"panel\"\n      MYSQL_USER: \"pterodactyl\"\n  cache:\n    image: redis:alpine\n    restart: always\n  panel:\n    image: pterodactylchina/panel:latest\n    restart: always\n    ports:\n      - \"80:80\"\n      - \"443:443\"\n    links:\n      - database\n      - cache\n    volumes:\n      - \"/srv/pterodactyl/var/:/app/var/\"\n      - \"/srv/pterodactyl/nginx/:/etc/nginx/http.d/\"\n      - \"/srv/pterodactyl/certs/:/etc/letsencrypt/\"\n      - \"/srv/pterodactyl/logs/:/app/storage/logs\"\n    environment:\n      <<: [*panel-environment, *mail-environment]\n      DB_PASSWORD: *db-password\n      APP_ENV: \"production\"\n      APP_ENVIRONMENT_ONLY: \"false\"\n      CACHE_DRIVER: \"redis\"\n      SESSION_DRIVER: \"redis\"\n      QUEUE_DRIVER: \"redis\"\n      REDIS_HOST: \"cache\"\n      DB_HOST: \"database\"\n      DB_PORT: \"3306\"\n      HASHIDS_LENGTH: 8\nnetworks:\n  default:\n    ipam:\n      config:\n        - subnet: 172.20.0.0/16\n"
  },
  {
    "path": "flake.nix",
    "content": "{\n  description = \"Pterodactyl Panel\";\n\n  inputs = {\n    flake-parts = {\n      url = \"github:hercules-ci/flake-parts\";\n      inputs.nixpkgs-lib.follows = \"nixpkgs\";\n    };\n\n    nixpkgs.url = \"github:NixOS/nixpkgs/nixos-unstable\";\n    systems.url = \"github:nix-systems/default\";\n  };\n\n  outputs = {self, ...} @ inputs:\n    inputs.flake-parts.lib.mkFlake {inherit inputs;} {\n      systems = import inputs.systems;\n\n      perSystem = {\n        pkgs,\n        system,\n        ...\n      }: let\n        php = pkgs.php; # PHP 8.2\n\n        phpWithExtensions = php.buildEnv {\n          extensions = {\n            enabled,\n            all,\n          }:\n            enabled\n            ++ (with all; [\n              redis\n              xdebug\n            ]);\n          extraConfig = ''\n            xdebug.mode=debug\n          '';\n        };\n\n        composer = php.packages.composer.override {php = phpWithExtensions;};\n      in {\n        # Initialize pkgs with our overlays\n        _module.args.pkgs = import inputs.nixpkgs {\n          inherit system;\n        };\n\n        devShells.default = pkgs.mkShellNoCC {\n          buildInputs = with pkgs; [\n            composer\n            nodejs_18\n            nodePackages.pnpm\n            nodePackages.yarn\n            phpWithExtensions\n          ];\n\n          shellHook = ''\n            PATH=\"$PATH:${pkgs.docker-compose}/libexec/docker/cli-plugins\"\n          '';\n        };\n\n        packages.development = pkgs.dockerTools.buildImage {\n          name = \"pterodactyl/development\";\n          tag = \"panel\";\n\n          copyToRoot = pkgs.buildEnv (let\n            caddyfile = pkgs.writeText \"Caddyfile\" ''\n              :80 {\n                root * /var/www/html/public/\n                file_server\n\n                header {\n                  -Server\n                  -X-Powered-By\n                  Referrer-Policy \"same-origin\"\n                  X-Frame-Options \"deny\"\n                  X-XSS-Protection \"1; mode=block\"\n                  X-Content-Type-Options \"nosniff\"\n                }\n\n                encode gzip zstd\n\n                php_fastcgi localhost:9000 {\n                  trusted_proxies private_ranges\n                }\n\n                try_files {path} {path}/ /index.php?{query}\n              }\n            '';\n\n            phpfpmConf = pkgs.writeText \"php-fpm.conf\" ''\n              [global]\n              error_log = /dev/stderr\n              daemonize = no\n\n              [www]\n              user  = nobody\n              group = nobody\n\n              listen = 0.0.0.0:9000\n\n              pm                      = dynamic\n              pm.start_servers        = 4\n              pm.min_spare_servers    = 4\n              pm.max_spare_servers    = 16\n              pm.max_children         = 64\n              pm.max_requests         = 256\n\n              clear_env = no\n              catch_workers_output = yes\n\n              decorate_workers_output = no\n            '';\n          in {\n            name = \"image-root\";\n            paths = with pkgs; [\n              (pkgs.runCommand \"configs\" {} ''\n                mkdir -p \"$out\"/etc/caddy\n                ln -s ${caddyfile} \"$out\"/etc/caddy/Caddyfile\n                ln -s ${phpfpmConf} \"$out\"/etc/php-fpm.conf\n              '')\n              bash\n              dockerTools.caCertificates\n              dockerTools.fakeNss\n              caddy\n              composer\n              coreutils\n              mysql80\n              nodejs_18\n              nodePackages.pnpm\n              nodePackages.yarn\n              phpWithExtensions\n            ];\n            pathsToLink = [\"/bin\" \"/etc\"];\n          });\n        };\n      };\n    };\n}\n"
  },
  {
    "path": "index.html",
    "content": "<!DOCTYPE html>\r\n<html lang=\"en\">\r\n<head>\r\n  <meta charset=\"UTF-8\">\r\n  <title>Error</title>\r\n  <style>\r\n    * {\r\n      margin: 0;\r\n      padding: 0;\r\n    }\r\n\r\n    main {\r\n      display: flex;\r\n      flex-direction: column;\r\n      justify-content: center;\r\n      align-items: center;\r\n      height: 100vh;\r\n      color: #333;\r\n      font-size: 20px;\r\n      font-family: -apple-system,BlinkMacSystemFont,Segoe UI,Helvetica,Arial,sans-serif;\r\n    }\r\n\r\n    .gap {\r\n      height: 2%;\r\n    }\r\n  </style>\r\n</head>\r\n<body>\r\n  <main>\r\n    <div>请将 Web 根目录设为当前目录下的 public 目录。</div>\r\n    <div class=\"gap\"></div>\r\n    <div>\r\n      Please define your web server root directory as the \"public\" directory under current directory.\r\n    </div>\r\n  </main>\r\n</body>\r\n</html>\r\n"
  },
  {
    "path": "jest.config.js",
    "content": "const { pathsToModuleNameMapper } = require('ts-jest');\nconst { compilerOptions } = require('./tsconfig');\n\n/** @type {import('ts-jest').InitialOptionsTsJest} */\nmodule.exports = {\n    preset: 'ts-jest',\n    globals: {\n        'ts-jest': {\n            isolatedModules: true,\n        },\n    },\n    moduleFileExtensions: ['js', 'ts', 'tsx', 'd.ts', 'json', 'node'],\n    moduleNameMapper: {\n        '\\\\.(jpe?g|png|gif|svg)$': '<rootDir>/resources/scripts/__mocks__/file.ts',\n        '\\\\.(s?css|less)$': 'identity-obj-proxy',\n        ...pathsToModuleNameMapper(compilerOptions.paths, {\n            prefix: '<rootDir>/',\n        }),\n    },\n    setupFilesAfterEnv: [\n        '<rootDir>/resources/scripts/setup-tests.ts',\n    ],\n    transform: {\n        '.*\\\\.[t|j]sx$': 'babel-jest',\n        '.*\\\\.ts$': 'ts-jest',\n    },\n    testPathIgnorePatterns: ['/node_modules/'],\n};\n"
  },
  {
    "path": "package.json",
    "content": "{\n    \"name\": \"pterodactyl-panel\",\n    \"engines\": {\n        \"node\": \">=22\"\n    },\n    \"dependencies\": {\n        \"@floating-ui/react-dom-interactions\": \"^0.6.6\",\n        \"@fortawesome/fontawesome-svg-core\": \"^1.2.32\",\n        \"@fortawesome/free-solid-svg-icons\": \"^5.15.1\",\n        \"@fortawesome/react-fontawesome\": \"^0.1.11\",\n        \"@headlessui/react\": \"^1.6.4\",\n        \"@heroicons/react\": \"^1.0.6\",\n        \"@hot-loader/react-dom\": \"^16.14.0\",\n        \"@preact/signals-react\": \"^1.2.1\",\n        \"@tailwindcss/forms\": \"^0.5.2\",\n        \"@tailwindcss/line-clamp\": \"^0.4.0\",\n        \"axios\": \"^1.13.2\",\n        \"boring-avatars\": \"^1.7.0\",\n        \"chart.js\": \"^3.8.0\",\n        \"classnames\": \"^2.3.1\",\n        \"codemirror\": \"^5.57.0\",\n        \"copy-to-clipboard\": \"^3.3.1\",\n        \"date-fns\": \"^2.28.0\",\n        \"debounce\": \"^1.2.0\",\n        \"deepmerge-ts\": \"^4.2.1\",\n        \"easy-peasy\": \"^4.0.1\",\n        \"events\": \"^3.0.0\",\n        \"formik\": \"^2.2.6\",\n        \"framer-motion\": \"^6.3.10\",\n        \"i18next\": \"^25.8.0\",\n        \"i18next-http-backend\": \"^3.0.2\",\n        \"i18next-multiload-backend-adapter\": \"^2.3.0\",\n        \"pathe\": \"^2.0.3\",\n        \"qrcode.react\": \"^1.0.1\",\n        \"react\": \"^16.14.0\",\n        \"react-chartjs-2\": \"^4.2.0\",\n        \"react-dom\": \"npm:@hot-loader/react-dom\",\n        \"react-fast-compare\": \"^3.2.0\",\n        \"react-hot-loader\": \"^4.12.21\",\n        \"react-i18next\": \"^16.5.4\",\n        \"react-router-dom\": \"^5.1.2\",\n        \"react-transition-group\": \"^4.4.1\",\n        \"reaptcha\": \"^1.7.2\",\n        \"sockette\": \"^2.0.6\",\n        \"styled-components\": \"^5.3.0\",\n        \"styled-components-breakpoint\": \"^3.0.0-preview.20\",\n        \"swr\": \"^0.2.3\",\n        \"tailwindcss\": \"^3.0.24\",\n        \"use-fit-text\": \"^2.4.0\",\n        \"uuid\": \"^13.0.0\",\n        \"xterm\": \"^4.19.0\",\n        \"xterm-addon-fit\": \"^0.5.0\",\n        \"xterm-addon-search\": \"^0.9.0\",\n        \"xterm-addon-search-bar\": \"^0.2.0\",\n        \"xterm-addon-unicode11\": \"^0.6.0\",\n        \"xterm-addon-web-links\": \"^0.6.0\",\n        \"yup\": \"^0.29.1\"\n    },\n    \"devDependencies\": {\n        \"@babel/core\": \"^7.12.1\",\n        \"@babel/plugin-proposal-class-properties\": \"^7.12.1\",\n        \"@babel/plugin-proposal-nullish-coalescing-operator\": \"^7.12.1\",\n        \"@babel/plugin-proposal-object-rest-spread\": \"^7.12.1\",\n        \"@babel/plugin-proposal-optional-chaining\": \"^7.12.1\",\n        \"@babel/plugin-syntax-dynamic-import\": \"^7.8.3\",\n        \"@babel/plugin-transform-modules-commonjs\": \"^7.18.2\",\n        \"@babel/plugin-transform-react-jsx\": \"^7.12.1\",\n        \"@babel/plugin-transform-runtime\": \"^7.12.1\",\n        \"@babel/preset-env\": \"^7.12.1\",\n        \"@babel/preset-react\": \"^7.12.1\",\n        \"@babel/preset-typescript\": \"^7.12.1\",\n        \"@babel/runtime\": \"^7.12.1\",\n        \"@fontsource-variable/ibm-plex-sans\": \"^5.2.8\",\n        \"@testing-library/dom\": \"^8.14.0\",\n        \"@testing-library/jest-dom\": \"^5.16.4\",\n        \"@testing-library/react\": \"12.1.5\",\n        \"@testing-library/user-event\": \"^14.2.1\",\n        \"@types/codemirror\": \"^0.0.98\",\n        \"@types/debounce\": \"^1.2.0\",\n        \"@types/events\": \"^3.0.0\",\n        \"@types/jest\": \"^28.1.3\",\n        \"@types/node\": \"^22.0.0\",\n        \"@types/path-browserify\": \"^1.0.3\",\n        \"@types/qrcode.react\": \"^1.0.1\",\n        \"@types/react\": \"^16.14.0\",\n        \"@types/react-copy-to-clipboard\": \"^4.3.0\",\n        \"@types/react-dom\": \"^16.9.16\",\n        \"@types/react-redux\": \"^7.1.1\",\n        \"@types/react-router\": \"^5.1.3\",\n        \"@types/react-router-dom\": \"^5.1.3\",\n        \"@types/react-transition-group\": \"^4.4.0\",\n        \"@types/styled-components\": \"5.1.7\",\n        \"@types/uuid\": \"^3.4.5\",\n        \"@types/webpack-env\": \"^1.18.8\",\n        \"@types/yup\": \"^0.29.3\",\n        \"@typescript-eslint/eslint-plugin\": \"^5\",\n        \"@typescript-eslint/parser\": \"^5\",\n        \"autoprefixer\": \"^10.4.7\",\n        \"babel-jest\": \"^28.1.1\",\n        \"babel-loader\": \"^10.0.0\",\n        \"babel-plugin-styled-components\": \"^2.0.7\",\n        \"cross-env\": \"^7.0.2\",\n        \"css-loader\": \"^7.1.2\",\n        \"eslint\": \"^8\",\n        \"eslint-config-prettier\": \"^8\",\n        \"eslint-plugin-jest-dom\": \"^4.0.2\",\n        \"eslint-plugin-prettier\": \"^4\",\n        \"eslint-plugin-react\": \"^7\",\n        \"eslint-plugin-react-hooks\": \"^4\",\n        \"identity-obj-proxy\": \"^3.0.0\",\n        \"jest\": \"^28.1.1\",\n        \"postcss\": \"^8.5.6\",\n        \"postcss-import\": \"^14.1.0\",\n        \"postcss-loader\": \"^8.2.0\",\n        \"postcss-nesting\": \"^13.0.2\",\n        \"postcss-preset-env\": \"^10.4.0\",\n        \"prettier\": \"^2.7.1\",\n        \"redux-devtools-extension\": \"^2.13.8\",\n        \"source-map-loader\": \"^5.0.0\",\n        \"style-loader\": \"^4.0.0\",\n        \"svg-url-loader\": \"^8.0.0\",\n        \"terser-webpack-plugin\": \"^5.3.14\",\n        \"ts-essentials\": \"^9.1.2\",\n        \"ts-jest\": \"^28.0.5\",\n        \"twin.macro\": \"^2.8.2\",\n        \"typescript\": \"~5.1.0\",\n        \"webpack\": \"^5.103.0\",\n        \"webpack-assets-manifest\": \"^6.4.0\",\n        \"webpack-cli\": \"^6.0.1\",\n        \"webpack-dev-server\": \"^5.2.2\"\n    },\n    \"scripts\": {\n        \"clean\": \"cd public/assets && find . \\\\( -name \\\"*.js\\\" -o -name \\\"*.map\\\" \\\\) -type f -delete\",\n        \"test\": \"jest\",\n        \"tsc\": \"tsc --noEmit\",\n        \"lint\": \"eslint ./resources/scripts/**/*.{ts,tsx} --ext .ts,.tsx\",\n        \"watch\": \"cross-env NODE_ENV=development ./node_modules/.bin/webpack --watch --progress\",\n        \"build\": \"cross-env NODE_ENV=development ./node_modules/.bin/webpack --progress\",\n        \"build:production\": \"yarn run clean && cross-env NODE_ENV=production ./node_modules/.bin/webpack --mode production\",\n        \"serve\": \"yarn run clean && cross-env NODE_ENV=development USE_LOCAL_CERTS=true WEBPACK_PUBLIC_PATH=https://pterodactyl.test:5173/ webpack serve --progress --hot --server-type https\"\n    },\n    \"browserslist\": [\n        \"> 0.5%\",\n        \"last 2 versions\",\n        \"firefox esr\",\n        \"not dead\"\n    ],\n    \"babelMacros\": {\n        \"twin\": {\n            \"preset\": \"styled-components\"\n        },\n        \"styledComponents\": {\n            \"pure\": true,\n            \"displayName\": true,\n            \"fileName\": true\n        }\n    }\n}\n"
  },
  {
    "path": "phpstan.neon",
    "content": "includes:\n    - ./vendor/larastan/larastan/extension.neon\n    - ./vendor/phpstan/phpstan-webmozart-assert/extension.neon\n\nrules:\n    - PHPStan\\Rules\\DeadCode\\UnreachableStatementRule\n    - PHPStan\\Rules\\DeadCode\\UnusedPrivateConstantRule\n    - PHPStan\\Rules\\DeadCode\\UnusedPrivateMethodRule\n\nparameters:\n    level: 4\n    paths:\n        - app\n    ignoreErrors:\n        - '#Call to an undefined method Illuminate\\\\Database\\\\Eloquent\\\\Builder::allowed(\\w+)\\(\\)#'\n        - '#Call to an undefined method Prologue\\\\Alerts\\\\AlertsMessageBag::(success|warning|danger|info)\\(\\)#'\n    excludePaths:\n        - app/Repositories\n        - app/Extensions/Spatie/Fractalistic/Fractal.php\n"
  },
  {
    "path": "phpunit.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<phpunit xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xsi:noNamespaceSchemaLocation=\"https://schema.phpunit.de/10.5/phpunit.xsd\" bootstrap=\"bootstrap/tests.php\" colors=\"true\">\n  <testsuites>\n    <testsuite name=\"Integration\">\n      <directory>./tests/Integration</directory>\n    </testsuite>\n    <testsuite name=\"Unit\">\n      <directory>./tests/Unit</directory>\n    </testsuite>\n  </testsuites>\n  <php>\n    <env name=\"APP_ENV\" value=\"testing\"/>\n  </php>\n  <source>\n    <include>\n      <directory suffix=\".php\">./app</directory>\n    </include>\n  </source>\n</phpunit>\n"
  },
  {
    "path": "postcss.config.js",
    "content": "module.exports = {\n    plugins: [\n        require('postcss-import'),\n        // We want to make use of nesting following the CSS Nesting spec, and not the\n        // SASS style nesting.\n        //\n        // @see https://github.com/csstools/postcss-plugins/tree/main/plugins/postcss-nesting\n        require('tailwindcss/nesting')(require('postcss-nesting')),\n        require('tailwindcss'),\n        require('autoprefixer'),\n        require('postcss-preset-env')({\n            features: {\n                'nesting-rules': false,\n            },\n        }),\n    ],\n};\n"
  },
  {
    "path": "public/.gitignore",
    "content": "assets\nassets/*\n!assets/svgs\n!assets/svgs/*.svg\n"
  },
  {
    "path": "public/.htaccess",
    "content": "<IfModule mod_rewrite.c>\n    <IfModule mod_negotiation.c>\n        Options -MultiViews -Indexes\n    </IfModule>\n\n    RewriteEngine On\n\n    # Handle Authorization Header\n    RewriteCond %{HTTP:Authorization} .\n    RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]\n\n    # Redirect Trailing Slashes If Not A Folder...\n    RewriteCond %{REQUEST_FILENAME} !-d\n    RewriteCond %{REQUEST_URI} (.+)/$\n    RewriteRule ^ %1 [L,R=301]\n\n    # Handle Front Controller...\n    RewriteCond %{REQUEST_FILENAME} !-d\n    RewriteCond %{REQUEST_FILENAME} !-f\n    RewriteRule ^ index.php [L]\n</IfModule>\n"
  },
  {
    "path": "public/favicons/browserconfig.xml",
    "content": "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<browserconfig><msapplication><tile><square70x70logo src=\"/ms-icon-70x70.png\"/><square150x150logo src=\"/ms-icon-150x150.png\"/><square310x310logo src=\"/ms-icon-310x310.png\"/><TileColor>#ffffff</TileColor></tile></msapplication></browserconfig>"
  },
  {
    "path": "public/favicons/manifest.json",
    "content": "{\n \"name\": \"App\",\n \"icons\": [\n  {\n   \"src\": \"\\/android-icon-36x36.png\",\n   \"sizes\": \"36x36\",\n   \"type\": \"image\\/png\",\n   \"density\": \"0.75\"\n  },\n  {\n   \"src\": \"\\/android-icon-48x48.png\",\n   \"sizes\": \"48x48\",\n   \"type\": \"image\\/png\",\n   \"density\": \"1.0\"\n  },\n  {\n   \"src\": \"\\/android-icon-72x72.png\",\n   \"sizes\": \"72x72\",\n   \"type\": \"image\\/png\",\n   \"density\": \"1.5\"\n  },\n  {\n   \"src\": \"\\/android-icon-96x96.png\",\n   \"sizes\": \"96x96\",\n   \"type\": \"image\\/png\",\n   \"density\": \"2.0\"\n  },\n  {\n   \"src\": \"\\/android-icon-144x144.png\",\n   \"sizes\": \"144x144\",\n   \"type\": \"image\\/png\",\n   \"density\": \"3.0\"\n  },\n  {\n   \"src\": \"\\/android-icon-192x192.png\",\n   \"sizes\": \"192x192\",\n   \"type\": \"image\\/png\",\n   \"density\": \"4.0\"\n  }\n ]\n}"
  },
  {
    "path": "public/index.php",
    "content": "<?php\n\n/**\n * Laravel - A PHP Framework For Web Artisans.\n *\n * @author   Taylor Otwell <taylor@laravel.com>\n */\ndefine('LARAVEL_START', microtime(true));\n\n/*\n|--------------------------------------------------------------------------\n| Check If Application Is Under Maintenance\n|--------------------------------------------------------------------------\n|\n| If the application is maintenance / demo mode via the \"down\" command we\n| will require this file so that any pre-rendered template can be shown\n| instead of starting the framework, which could cause an exception.\n|\n*/\n\nif (file_exists(__DIR__ . '/../storage/framework/maintenance.php')) {\n    require __DIR__ . '/../storage/framework/maintenance.php';\n}\n\n/*\n|--------------------------------------------------------------------------\n| Register The Auto Loader\n|--------------------------------------------------------------------------\n|\n| Composer provides a convenient, automatically generated class loader for\n| our application. We just need to utilize it! We'll simply require it\n| into the script here so that we don't have to worry about manual\n| loading any of our classes later on. It feels great to relax.\n|\n*/\n\nrequire __DIR__ . '/../vendor/autoload.php';\n\n/*\n|--------------------------------------------------------------------------\n| Turn On The Lights\n|--------------------------------------------------------------------------\n|\n| We need to illuminate PHP development, so let us turn on the lights.\n| This bootstraps the framework and gets it ready for use, then it\n| will load up this application so that we can run it and send\n| the responses back to the browser and delight our users.\n|\n*/\n\n$app = require_once __DIR__ . '/../bootstrap/app.php';\n\n/*\n|--------------------------------------------------------------------------\n| Run The Application\n|--------------------------------------------------------------------------\n|\n| Once we have the application, we can handle the incoming request\n| through the kernel, and send the associated response back to\n| the client's browser allowing them to enjoy the creative\n| and wonderful application we have prepared for them.\n|\n*/\n\n$kernel = $app->make(Illuminate\\Contracts\\Http\\Kernel::class);\n\n$response = $kernel->handle(\n    $request = Illuminate\\Http\\Request::capture()\n);\n\n$response->send();\n\n$kernel->terminate($request, $response);\n"
  },
  {
    "path": "public/js/autocomplete.js",
    "content": "// Hacky fix for browsers ignoring autocomplete=\"off\"\n$(document).ready(function() {\n    $('.form-autocomplete-stop').on('click', function () {\n        $(this).removeAttr('readonly').blur().focus();\n    });\n});\n"
  },
  {
    "path": "public/js/keyboard.polyfill.js",
    "content": "/* global define, KeyboardEvent, module */\n\n(function () {\n\n  var keyboardeventKeyPolyfill = {\n    polyfill: polyfill,\n    keys: {\n      3: 'Cancel',\n      6: 'Help',\n      8: 'Backspace',\n      9: 'Tab',\n      12: 'Clear',\n      13: 'Enter',\n      16: 'Shift',\n      17: 'Control',\n      18: 'Alt',\n      19: 'Pause',\n      20: 'CapsLock',\n      27: 'Escape',\n      28: 'Convert',\n      29: 'NonConvert',\n      30: 'Accept',\n      31: 'ModeChange',\n      32: ' ',\n      33: 'PageUp',\n      34: 'PageDown',\n      35: 'End',\n      36: 'Home',\n      37: 'ArrowLeft',\n      38: 'ArrowUp',\n      39: 'ArrowRight',\n      40: 'ArrowDown',\n      41: 'Select',\n      42: 'Print',\n      43: 'Execute',\n      44: 'PrintScreen',\n      45: 'Insert',\n      46: 'Delete',\n      48: ['0', ')'],\n      49: ['1', '!'],\n      50: ['2', '@'],\n      51: ['3', '#'],\n      52: ['4', '$'],\n      53: ['5', '%'],\n      54: ['6', '^'],\n      55: ['7', '&'],\n      56: ['8', '*'],\n      57: ['9', '('],\n      91: 'OS',\n      93: 'ContextMenu',\n      144: 'NumLock',\n      145: 'ScrollLock',\n      181: 'VolumeMute',\n      182: 'VolumeDown',\n      183: 'VolumeUp',\n      186: [';', ':'],\n      187: ['=', '+'],\n      188: [',', '<'],\n      189: ['-', '_'],\n      190: ['.', '>'],\n      191: ['/', '?'],\n      192: ['`', '~'],\n      219: ['[', '{'],\n      220: ['\\\\', '|'],\n      221: [']', '}'],\n      222: [\"'\", '\"'],\n      224: 'Meta',\n      225: 'AltGraph',\n      246: 'Attn',\n      247: 'CrSel',\n      248: 'ExSel',\n      249: 'EraseEof',\n      250: 'Play',\n      251: 'ZoomOut'\n    }\n  };\n\n  // Function keys (F1-24).\n  var i;\n  for (i = 1; i < 25; i++) {\n    keyboardeventKeyPolyfill.keys[111 + i] = 'F' + i;\n  }\n\n  // Printable ASCII characters.\n  var letter = '';\n  for (i = 65; i < 91; i++) {\n    letter = String.fromCharCode(i);\n    keyboardeventKeyPolyfill.keys[i] = [letter.toLowerCase(), letter.toUpperCase()];\n  }\n\n  function polyfill () {\n    if (!('KeyboardEvent' in window) ||\n        'key' in KeyboardEvent.prototype) {\n      return false;\n    }\n\n    // Polyfill `key` on `KeyboardEvent`.\n    var proto = {\n      get: function (x) {\n        var key = keyboardeventKeyPolyfill.keys[this.which || this.keyCode];\n\n        if (Array.isArray(key)) {\n          key = key[+this.shiftKey];\n        }\n\n        return key;\n      }\n    };\n    Object.defineProperty(KeyboardEvent.prototype, 'key', proto);\n    return proto;\n  }\n\n  if (typeof define === 'function' && define.amd) {\n    define('keyboardevent-key-polyfill', keyboardeventKeyPolyfill);\n  } else if (typeof exports !== 'undefined' && typeof module !== 'undefined') {\n    module.exports = keyboardeventKeyPolyfill;\n  } else if (window) {\n    window.keyboardeventKeyPolyfill = keyboardeventKeyPolyfill;\n  }\n\n})();\n"
  },
  {
    "path": "public/js/laroute.js",
    "content": "(function () {\n\n    var laroute = (function () {\n\n        var routes = {\n\n            absolute: false,\n            rootUrl: 'http://pterodactyl.local',\n            routes : [{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"_debugbar\\/open\",\"name\":\"debugbar.openhandler\",\"action\":\"Barryvdh\\Debugbar\\Controllers\\OpenHandlerController@handle\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"_debugbar\\/clockwork\\/{id}\",\"name\":\"debugbar.clockwork\",\"action\":\"Barryvdh\\Debugbar\\Controllers\\OpenHandlerController@clockwork\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"_debugbar\\/assets\\/stylesheets\",\"name\":\"debugbar.assets.css\",\"action\":\"Barryvdh\\Debugbar\\Controllers\\AssetController@css\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"_debugbar\\/assets\\/javascript\",\"name\":\"debugbar.assets.js\",\"action\":\"Barryvdh\\Debugbar\\Controllers\\AssetController@js\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"_debugbar\\/cache\\/{key}\\/{tags?}\",\"name\":\"debugbar.cache.delete\",\"action\":\"Barryvdh\\Debugbar\\Controllers\\CacheController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"\\/\",\"name\":\"index\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\IndexController@getIndex\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"status\\/{server}\",\"name\":\"index.status\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\IndexController@status\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"account\",\"name\":\"account\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\AccountController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"account\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\AccountController@update\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"account\\/api\",\"name\":\"account.api\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\ClientApiController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"account\\/api\\/new\",\"name\":\"account.api.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\ClientApiController@create\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"account\\/api\\/new\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\ClientApiController@store\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"account\\/api\\/revoke\\/{identifier}\",\"name\":\"account.api.revoke\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\ClientApiController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"account\\/security\",\"name\":\"account.security\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\SecurityController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"account\\/security\\/revoke\\/{id}\",\"name\":\"account.security.revoke\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\SecurityController@revoke\"},{\"host\":null,\"methods\":[\"PUT\"],\"uri\":\"account\\/security\\/totp\",\"name\":\"account.security.totp\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\SecurityController@generateTotp\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"account\\/security\\/totp\",\"name\":\"account.security.totp.set\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\SecurityController@setTotp\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"account\\/security\\/totp\",\"name\":\"account.security.totp.disable\",\"action\":\"Pterodactyl\\Http\\Controllers\\Base\\SecurityController@disableTotp\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\",\"name\":\"admin.index\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\BaseController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/statistics\",\"name\":\"admin.statistics\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\StatisticsController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/api\",\"name\":\"admin.api.index\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ApiController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/api\\/new\",\"name\":\"admin.api.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ApiController@create\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/api\\/new\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ApiController@store\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/api\\/revoke\\/{identifier}\",\"name\":\"admin.api.delete\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ApiController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/locations\",\"name\":\"admin.locations\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\LocationController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/locations\\/view\\/{location}\",\"name\":\"admin.locations.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\LocationController@view\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/locations\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\LocationController@create\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/locations\\/view\\/{location}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\LocationController@update\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/databases\",\"name\":\"admin.databases\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\DatabaseController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/databases\\/view\\/{host}\",\"name\":\"admin.databases.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\DatabaseController@view\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/databases\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\DatabaseController@create\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/databases\\/view\\/{host}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\DatabaseController@update\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/databases\\/view\\/{host}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\DatabaseController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/settings\",\"name\":\"admin.settings\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Settings\\IndexController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/settings\\/mail\",\"name\":\"admin.settings.mail\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Settings\\MailController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/settings\\/mail\\/test\",\"name\":\"admin.settings.mail.test\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Settings\\MailController@test\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/settings\\/advanced\",\"name\":\"admin.settings.advanced\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Settings\\AdvancedController@index\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/settings\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Settings\\IndexController@update\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/settings\\/mail\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Settings\\MailController@update\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/settings\\/advanced\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Settings\\AdvancedController@update\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/users\",\"name\":\"admin.users\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\UserController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/users\\/accounts.json\",\"name\":\"admin.users.json\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\UserController@json\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/users\\/new\",\"name\":\"admin.users.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\UserController@create\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/users\\/view\\/{user}\",\"name\":\"admin.users.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\UserController@view\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/users\\/new\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\UserController@store\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/users\\/view\\/{user}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\UserController@update\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/users\\/view\\/{user}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\UserController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/servers\",\"name\":\"admin.servers\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/servers\\/new\",\"name\":\"admin.servers.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@create\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/servers\\/view\\/{server}\",\"name\":\"admin.servers.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@viewIndex\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/details\",\"name\":\"admin.servers.view.details\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@viewDetails\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/build\",\"name\":\"admin.servers.view.build\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@viewBuild\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/startup\",\"name\":\"admin.servers.view.startup\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@viewStartup\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/database\",\"name\":\"admin.servers.view.database\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@viewDatabase\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/manage\",\"name\":\"admin.servers.view.manage\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@viewManage\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/delete\",\"name\":\"admin.servers.view.delete\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@viewDelete\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/servers\\/new\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@store\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/build\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@updateBuild\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/startup\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@saveStartup\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/database\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@newDatabase\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/manage\\/toggle\",\"name\":\"admin.servers.view.manage.toggle\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@toggleInstall\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/manage\\/rebuild\",\"name\":\"admin.servers.view.manage.rebuild\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@rebuildContainer\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/manage\\/suspension\",\"name\":\"admin.servers.view.manage.suspension\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@manageSuspension\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/manage\\/reinstall\",\"name\":\"admin.servers.view.manage.reinstall\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@reinstallServer\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/delete\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@delete\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/details\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@setDetails\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/database\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@resetDatabasePassword\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/servers\\/view\\/{server}\\/database\\/{database}\\/delete\",\"name\":\"admin.servers.view.database.delete\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\ServersController@deleteDatabase\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nodes\",\"name\":\"admin.nodes\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nodes\\/new\",\"name\":\"admin.nodes.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@create\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\",\"name\":\"admin.nodes.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@viewIndex\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/settings\",\"name\":\"admin.nodes.view.settings\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@viewSettings\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/configuration\",\"name\":\"admin.nodes.view.configuration\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@viewConfiguration\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/allocation\",\"name\":\"admin.nodes.view.allocation\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@viewAllocation\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/servers\",\"name\":\"admin.nodes.view.servers\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@viewServers\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/settings\\/token\",\"name\":\"admin.nodes.view.configuration.token\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@setToken\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/nodes\\/new\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@store\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/allocation\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@createAllocation\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/allocation\\/remove\",\"name\":\"admin.nodes.view.allocation.removeBlock\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@allocationRemoveBlock\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/allocation\\/alias\",\"name\":\"admin.nodes.view.allocation.setAlias\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@allocationSetAlias\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/settings\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@updateSettings\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/delete\",\"name\":\"admin.nodes.view.delete\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@delete\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/allocation\\/remove\\/{allocation}\",\"name\":\"admin.nodes.view.allocation.removeSingle\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@allocationRemoveSingle\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/nodes\\/view\\/{node}\\/allocations\",\"name\":\"admin.nodes.view.allocation.removeMultiple\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\NodesController@allocationRemoveMultiple\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nests\",\"name\":\"admin.nests\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\NestController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nests\\/new\",\"name\":\"admin.nests.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\NestController@create\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nests\\/view\\/{nest}\",\"name\":\"admin.nests.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\NestController@view\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nests\\/egg\\/new\",\"name\":\"admin.nests.egg.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggController@create\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\",\"name\":\"admin.nests.egg.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggController@view\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\\/export\",\"name\":\"admin.nests.egg.export\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggShareController@export\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\\/variables\",\"name\":\"admin.nests.egg.variables\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggVariableController@view\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\\/scripts\",\"name\":\"admin.nests.egg.scripts\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggScriptController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/nests\\/new\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\NestController@store\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/nests\\/import\",\"name\":\"admin.nests.egg.import\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggShareController@import\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/nests\\/egg\\/new\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggController@store\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\\/variables\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggVariableController@store\"},{\"host\":null,\"methods\":[\"PUT\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggShareController@update\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/nests\\/view\\/{nest}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\NestController@update\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggController@update\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\\/scripts\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggScriptController@update\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\\/variables\\/{variable}\",\"name\":\"admin.nests.egg.variables.edit\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggVariableController@update\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/nests\\/view\\/{nest}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\NestController@destroy\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggController@destroy\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/nests\\/egg\\/{egg}\\/variables\\/{variable}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\Nests\\EggVariableController@destroy\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/packs\",\"name\":\"admin.packs\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\PackController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/packs\\/new\",\"name\":\"admin.packs.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\PackController@create\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/packs\\/new\\/template\",\"name\":\"admin.packs.new.template\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\PackController@newTemplate\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"admin\\/packs\\/view\\/{pack}\",\"name\":\"admin.packs.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\PackController@view\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/packs\\/new\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\PackController@store\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"admin\\/packs\\/view\\/{pack}\\/export\\/{files?}\",\"name\":\"admin.packs.view.export\",\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\PackController@export\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"admin\\/packs\\/view\\/{pack}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\PackController@update\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"admin\\/packs\\/view\\/{pack}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Admin\\PackController@destroy\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"auth\\/login\",\"name\":\"auth.login\",\"action\":\"Pterodactyl\\Http\\Controllers\\Auth\\LoginController@showLoginForm\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"auth\\/login\\/totp\",\"name\":\"auth.totp\",\"action\":\"Pterodactyl\\Http\\Controllers\\Auth\\LoginController@totp\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"auth\\/password\",\"name\":\"auth.password\",\"action\":\"Pterodactyl\\Http\\Controllers\\Auth\\ForgotPasswordController@showLinkRequestForm\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"auth\\/password\\/reset\\/{token}\",\"name\":\"auth.reset\",\"action\":\"Pterodactyl\\Http\\Controllers\\Auth\\ResetPasswordController@showResetForm\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"auth\\/login\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Auth\\LoginController@login\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"auth\\/login\\/totp\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Auth\\LoginController@loginUsingTotp\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"auth\\/password\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Auth\\ForgotPasswordController@sendResetLinkEmail\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"auth\\/password\\/reset\",\"name\":\"auth.reset.post\",\"action\":\"Pterodactyl\\Http\\Controllers\\Auth\\ResetPasswordController@reset\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"auth\\/password\\/reset\\/{token}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Auth\\ForgotPasswordController@sendResetLinkEmail\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"auth\\/logout\",\"name\":\"auth.logout\",\"action\":\"Pterodactyl\\Http\\Controllers\\Auth\\LoginController@logout\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\",\"name\":\"server.index\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\ConsoleController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/console\",\"name\":\"server.console\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\ConsoleController@console\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/settings\\/allocation\",\"name\":\"server.settings.allocation\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Settings\\AllocationController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/settings\\/name\",\"name\":\"server.settings.name\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Settings\\NameController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/settings\\/sftp\",\"name\":\"server.settings.sftp\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Settings\\SftpController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/settings\\/startup\",\"name\":\"server.settings.startup\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Settings\\StartupController@index\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"server\\/{server}\\/settings\\/allocation\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Settings\\AllocationController@update\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"server\\/{server}\\/settings\\/name\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Settings\\NameController@update\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"server\\/{server}\\/settings\\/startup\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Settings\\StartupController@update\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/databases\",\"name\":\"server.databases.index\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\DatabaseController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"server\\/{server}\\/databases\\/new\",\"name\":\"server.databases.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\DatabaseController@store\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"server\\/{server}\\/databases\\/password\",\"name\":\"server.databases.password\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\DatabaseController@update\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"server\\/{server}\\/databases\\/delete\\/{database}\",\"name\":\"server.databases.delete\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\DatabaseController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/files\",\"name\":\"server.files.index\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Files\\FileActionsController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/files\\/add\",\"name\":\"server.files.add\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Files\\FileActionsController@create\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/files\\/edit\\/{file}\",\"name\":\"server.files.edit\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Files\\FileActionsController@view\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/files\\/download\\/{file}\",\"name\":\"server.files.edit\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Files\\DownloadController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"server\\/{server}\\/files\\/directory-list\",\"name\":\"server.files.directory-list\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Files\\RemoteRequestController@directory\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"server\\/{server}\\/files\\/save\",\"name\":\"server.files.save\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Files\\RemoteRequestController@store\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/users\",\"name\":\"server.subusers\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\SubuserController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/users\\/new\",\"name\":\"server.subusers.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\SubuserController@create\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"server\\/{server}\\/users\\/new\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\SubuserController@store\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/users\\/view\\/{subuser}\",\"name\":\"server.subusers.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\SubuserController@view\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"server\\/{server}\\/users\\/view\\/{subuser}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\SubuserController@update\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"server\\/{server}\\/users\\/view\\/{subuser}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\SubuserController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/schedules\",\"name\":\"server.schedules\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Tasks\\TaskManagementController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/schedules\\/new\",\"name\":\"server.schedules.new\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Tasks\\TaskManagementController@create\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"server\\/{server}\\/schedules\\/new\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Tasks\\TaskManagementController@store\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"server\\/{server}\\/schedules\\/view\\/{schedule}\",\"name\":\"server.schedules.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Tasks\\TaskManagementController@view\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"server\\/{server}\\/schedules\\/view\\/{schedule}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Tasks\\TaskManagementController@update\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"server\\/{server}\\/schedules\\/view\\/{schedule}\\/toggle\",\"name\":\"server.schedules.toggle\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Tasks\\ActionController@toggle\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"server\\/{server}\\/schedules\\/view\\/{schedule}\\/trigger\",\"name\":\"server.schedules.trigger\",\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Tasks\\ActionController@trigger\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"server\\/{server}\\/schedules\\/view\\/{schedule}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Server\\Tasks\\TaskManagementController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/users\",\"name\":\"api.application.users\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Users\\UserController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/users\\/{user}\",\"name\":\"api.application.users.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Users\\UserController@view\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/users\\/external\\/{external_id}\",\"name\":\"api.application.users.external\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Users\\ExternalUserController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/users\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Users\\UserController@store\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"api\\/application\\/users\\/{user}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Users\\UserController@update\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"api\\/application\\/users\\/{user}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Users\\UserController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/nodes\",\"name\":\"api.application.nodes\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes\\NodeController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/nodes\\/{node}\",\"name\":\"api.application.nodes.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes\\NodeController@view\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/nodes\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes\\NodeController@store\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"api\\/application\\/nodes\\/{node}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes\\NodeController@update\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"api\\/application\\/nodes\\/{node}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes\\NodeController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/nodes\\/{node}\\/allocations\",\"name\":\"api.application.allocations\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes\\AllocationController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/nodes\\/{node}\\/allocations\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes\\AllocationController@store\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"api\\/application\\/nodes\\/{node}\\/allocations\\/{allocation}\",\"name\":\"api.application.allocations.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nodes\\AllocationController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/locations\",\"name\":\"api.applications.locations\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Locations\\LocationController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/locations\\/{location}\",\"name\":\"api.application.locations.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Locations\\LocationController@view\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/locations\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Locations\\LocationController@store\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"api\\/application\\/locations\\/{location}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Locations\\LocationController@update\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"api\\/application\\/locations\\/{location}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Locations\\LocationController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/servers\",\"name\":\"api.application.servers\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/servers\\/{server}\",\"name\":\"api.application.servers.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerController@view\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/servers\\/external\\/{external_id}\",\"name\":\"api.application.servers.external\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ExternalServerController@index\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/details\",\"name\":\"api.application.servers.details\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerDetailsController@details\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/build\",\"name\":\"api.application.servers.build\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerDetailsController@build\"},{\"host\":null,\"methods\":[\"PATCH\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/startup\",\"name\":\"api.application.servers.startup\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\StartupController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/servers\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerController@store\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/suspend\",\"name\":\"api.application.servers.suspend\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerManagementController@suspend\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/unsuspend\",\"name\":\"api.application.servers.unsuspend\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerManagementController@unsuspend\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/reinstall\",\"name\":\"api.application.servers.reinstall\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerManagementController@reinstall\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/rebuild\",\"name\":\"api.application.servers.rebuild\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerManagementController@rebuild\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"api\\/application\\/servers\\/{server}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerController@delete\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/{force?}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\ServerController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/databases\",\"name\":\"api.application.servers.databases\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\DatabaseController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/databases\\/{database}\",\"name\":\"api.application.servers.databases.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\DatabaseController@view\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/databases\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\DatabaseController@store\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/databases\\/{database}\\/reset-password\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\DatabaseController@resetPassword\"},{\"host\":null,\"methods\":[\"DELETE\"],\"uri\":\"api\\/application\\/servers\\/{server}\\/databases\\/{database}\",\"name\":null,\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Servers\\DatabaseController@delete\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/nests\",\"name\":\"api.application.nests\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nests\\NestController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/nests\\/{nest}\",\"name\":\"api.application.nests.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nests\\NestController@view\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/nests\\/{nest}\\/eggs\",\"name\":\"api.application.nests.eggs\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nests\\EggController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/application\\/nests\\/{nest}\\/eggs\\/{egg}\",\"name\":\"api.application.nests.eggs.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Application\\Nests\\EggController@view\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/client\",\"name\":\"api.client.index\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Client\\ClientController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/client\\/servers\\/{server}\",\"name\":\"api.client.servers.view\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers\\ServerController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/client\\/servers\\/{server}\\/utilization\",\"name\":\"api.client.servers.resources\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers\\ResourceUtilizationController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/client\\/servers\\/{server}\\/command\",\"name\":\"api.client.servers.command\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers\\CommandController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/client\\/servers\\/{server}\\/power\",\"name\":\"api.client.servers.power\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Client\\Servers\\PowerController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/remote\\/authenticate\\/{token}\",\"name\":\"api.remote.authenticate\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Remote\\ValidateKeyController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/remote\\/download-file\",\"name\":\"api.remote.download_file\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Remote\\FileDownloadController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/remote\\/eggs\",\"name\":\"api.remote.eggs\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Remote\\EggRetrievalController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/remote\\/eggs\\/{uuid}\",\"name\":\"api.remote.eggs.download\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Remote\\EggRetrievalController@download\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"api\\/remote\\/scripts\\/{uuid}\",\"name\":\"api.remote.scripts\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Remote\\EggInstallController@index\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"api\\/remote\\/sftp\",\"name\":\"api.remote.sftp\",\"action\":\"Pterodactyl\\Http\\Controllers\\Api\\Remote\\SftpController@index\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"daemon\\/packs\\/pull\\/{uuid}\",\"name\":\"daemon.pack.pull\",\"action\":\"Pterodactyl\\Http\\Controllers\\Daemon\\PackController@pull\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"daemon\\/packs\\/pull\\/{uuid}\\/hash\",\"name\":\"daemon.pack.hash\",\"action\":\"Pterodactyl\\Http\\Controllers\\Daemon\\PackController@hash\"},{\"host\":null,\"methods\":[\"GET\",\"HEAD\"],\"uri\":\"daemon\\/configure\\/{token}\",\"name\":\"daemon.configuration\",\"action\":\"Pterodactyl\\Http\\Controllers\\Daemon\\ActionController@configuration\"},{\"host\":null,\"methods\":[\"POST\"],\"uri\":\"daemon\\/install\",\"name\":\"daemon.install\",\"action\":\"Pterodactyl\\Http\\Controllers\\Daemon\\ActionController@markInstall\"}],\n            prefix: '',\n\n            route : function (name, parameters, route) {\n                route = route || this.getByName(name);\n\n                if ( ! route ) {\n                    return undefined;\n                }\n\n                return this.toRoute(route, parameters);\n            },\n\n            url: function (url, parameters) {\n                parameters = parameters || [];\n\n                var uri = url + '/' + parameters.join('/');\n\n                return this.getCorrectUrl(uri);\n            },\n\n            toRoute : function (route, parameters) {\n                var uri = this.replaceNamedParameters(route.uri, parameters);\n                var qs  = this.getRouteQueryString(parameters);\n\n                if (this.absolute && this.isOtherHost(route)){\n                    return \"//\" + route.host + \"/\" + uri + qs;\n                }\n\n                return this.getCorrectUrl(uri + qs);\n            },\n\n            isOtherHost: function (route){\n                return route.host && route.host != window.location.hostname;\n            },\n\n            replaceNamedParameters : function (uri, parameters) {\n                uri = uri.replace(/\\{(.*?)\\??\\}/g, function(match, key) {\n                    if (parameters.hasOwnProperty(key)) {\n                        var value = parameters[key];\n                        delete parameters[key];\n                        return value;\n                    } else {\n                        return match;\n                    }\n                });\n\n                // Strip out any optional parameters that were not given\n                uri = uri.replace(/\\/\\{.*?\\?\\}/g, '');\n\n                return uri;\n            },\n\n            getRouteQueryString : function (parameters) {\n                var qs = [];\n                for (var key in parameters) {\n                    if (parameters.hasOwnProperty(key)) {\n                        qs.push(key + '=' + parameters[key]);\n                    }\n                }\n\n                if (qs.length < 1) {\n                    return '';\n                }\n\n                return '?' + qs.join('&');\n            },\n\n            getByName : function (name) {\n                for (var key in this.routes) {\n                    if (this.routes.hasOwnProperty(key) && this.routes[key].name === name) {\n                        return this.routes[key];\n                    }\n                }\n            },\n\n            getByAction : function(action) {\n                for (var key in this.routes) {\n                    if (this.routes.hasOwnProperty(key) && this.routes[key].action === action) {\n                        return this.routes[key];\n                    }\n                }\n            },\n\n            getCorrectUrl: function (uri) {\n                var url = this.prefix + '/' + uri.replace(/^\\/?/, '');\n\n                if ( ! this.absolute) {\n                    return url;\n                }\n\n                return this.rootUrl.replace('/\\/?$/', '') + url;\n            }\n        };\n\n        var getLinkAttributes = function(attributes) {\n            if ( ! attributes) {\n                return '';\n            }\n\n            var attrs = [];\n            for (var key in attributes) {\n                if (attributes.hasOwnProperty(key)) {\n                    attrs.push(key + '=\"' + attributes[key] + '\"');\n                }\n            }\n\n            return attrs.join(' ');\n        };\n\n        var getHtmlLink = function (url, title, attributes) {\n            title      = title || url;\n            attributes = getLinkAttributes(attributes);\n\n            return '<a href=\"' + url + '\" ' + attributes + '>' + title + '</a>';\n        };\n\n        return {\n            // Generate a url for a given controller action.\n            // Router.action('HomeController@getIndex', [params = {}])\n            action : function (name, parameters) {\n                parameters = parameters || {};\n\n                return routes.route(name, parameters, routes.getByAction(name));\n            },\n\n            // Generate a url for a given named route.\n            // Router.route('routeName', [params = {}])\n            route : function (route, parameters) {\n                parameters = parameters || {};\n\n                return routes.route(route, parameters);\n            },\n\n            // Generate a fully qualified URL to the given path.\n            // Router.route('url', [params = {}])\n            url : function (route, parameters) {\n                parameters = parameters || {};\n\n                return routes.url(route, parameters);\n            },\n\n            // Generate a html link to the given url.\n            // Router.link_to('foo/bar', [title = url], [attributes = {}])\n            link_to : function (url, title, attributes) {\n                url = this.url(url);\n\n                return getHtmlLink(url, title, attributes);\n            },\n\n            // Generate a html link to the given route.\n            // Router.link_to_route('route.name', [title=url], [parameters = {}], [attributes = {}])\n            link_to_route : function (route, title, parameters, attributes) {\n                var url = this.route(route, parameters);\n\n                return getHtmlLink(url, title, attributes);\n            },\n\n            // Generate a html link to the given controller action.\n            // Router.link_to_action('HomeController@getIndex', [title=url], [parameters = {}], [attributes = {}])\n            link_to_action : function(action, title, parameters, attributes) {\n                var url = this.action(action, parameters);\n\n                return getHtmlLink(url, title, attributes);\n            }\n\n        };\n\n    }).call(this);\n\n    /**\n     * Expose the class either via AMD, CommonJS or the global object\n     */\n    if (typeof define === 'function' && define.amd) {\n        define(function () {\n            return laroute;\n        });\n    }\n    else if (typeof module === 'object' && module.exports){\n        module.exports = laroute;\n    }\n    else {\n        window.Router = laroute;\n    }\n\n}).call(this);\n\n"
  },
  {
    "path": "public/robots.txt",
    "content": "User-agent: *\nDisallow: /\n"
  },
  {
    "path": "public/themes/pterodactyl/css/checkbox.css",
    "content": "/**\n * Bootsnip - \"Bootstrap Checkboxes/Radios\"\n * Bootstrap 3.2.0 Snippet by i-heart-php <http://bootsnipp.com/i-heart-php>\n *\n * Copyright (c) 2013 Bootsnipp.com\n *\n * Permission is hereby granted, free of charge, to any person obtaining a copy\n * of this software and associated documentation files (the \"Software\"), to deal\n * in the Software without restriction, including without limitation the rights\n * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n * copies of the Software, and to permit persons to whom the Software is\n * furnished to do so, subject to the following conditions:\n *\n * The above copyright notice and this permission notice shall be included in all\n * copies or substantial portions of the Software.\n *\n * THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n * SOFTWARE.\n */\n .checkbox {\n    padding-left: 20px;\n}\n.checkbox label {\n    display: inline-block;\n    position: relative;\n    padding-left: 5px;\n}\n.checkbox label::before {\n    content: \"\";\n    display: inline-block;\n    position: absolute;\n    width: 17px;\n    height: 17px;\n    left: 0;\n    top: 2.5px;\n    margin-left: -20px;\n    border: 1px solid #cccccc;\n    border-radius: 3px;\n    background-color: #fff;\n    -webkit-transition: border 0.15s ease-in-out, color 0.15s ease-in-out;\n    -o-transition: border 0.15s ease-in-out, color 0.15s ease-in-out;\n    transition: border 0.15s ease-in-out, color 0.15s ease-in-out;\n}\n.checkbox label::after {\n    display: inline-block;\n    position: absolute;\n    width: 16px;\n    height: 16px;\n    left: 0;\n    top: 2.5px;\n    margin-left: -20px;\n    padding-left: 3px;\n    padding-top: 1px;\n    font-size: 11px;\n    color: #555555;\n}\n.checkbox input[type=\"checkbox\"] {\n    opacity: 0;\n}\n.checkbox input[type=\"checkbox\"]:focus + label::before {\n    outline: thin dotted;\n    outline: 5px auto -webkit-focus-ring-color;\n    outline-offset: -2px;\n}\n.checkbox input[type=\"checkbox\"]:checked + label::after {\n    font-family: 'FontAwesome';\n    content: \"\\f00c\";\n}\n.checkbox input[type=\"checkbox\"]:disabled + label {\n    opacity: 0.65;\n}\n.checkbox input[type=\"checkbox\"]:disabled + label::before {\n    background-color: #eeeeee;\n    cursor: not-allowed;\n}\n.checkbox.checkbox-circle label::before {\n    border-radius: 50%;\n}\n.checkbox.checkbox-inline {\n    margin-top: 0;\n}\n.checkbox-primary input[type=\"checkbox\"]:checked + label::before {\n    background-color: #428bca;\n    border-color: #428bca;\n}\n.checkbox-primary input[type=\"checkbox\"]:checked + label::after {\n    color: #fff;\n}\n.checkbox-danger input[type=\"checkbox\"]:checked + label::before {\n    background-color: #d9534f;\n    border-color: #d9534f;\n}\n.checkbox-danger input[type=\"checkbox\"]:checked + label::after {\n    color: #fff;\n}\n.checkbox-info input[type=\"checkbox\"]:checked + label::before {\n    background-color: #5bc0de;\n    border-color: #5bc0de;\n}\n.checkbox-info input[type=\"checkbox\"]:checked + label::after {\n    color: #fff;\n}\n.checkbox-warning input[type=\"checkbox\"]:checked + label::before {\n    background-color: #f0ad4e;\n    border-color: #f0ad4e;\n}\n.checkbox-warning input[type=\"checkbox\"]:checked + label::after {\n    color: #fff;\n}\n.checkbox-success input[type=\"checkbox\"]:checked + label::before {\n    background-color: #5cb85c;\n    border-color: #5cb85c;\n}\n.checkbox-success input[type=\"checkbox\"]:checked + label::after {\n    color: #fff;\n}\n.radio {\n    padding-left: 20px;\n}\n.radio label {\n    display: inline-block;\n    position: relative;\n    padding-left: 5px;\n}\n.radio label::before {\n    content: \"\";\n    display: inline-block;\n    position: absolute;\n    width: 17px;\n    height: 17px;\n    left: 0;\n    margin-left: -20px;\n    border: 1px solid #cccccc;\n    border-radius: 50%;\n    background-color: #fff;\n    -webkit-transition: border 0.15s ease-in-out;\n    -o-transition: border 0.15s ease-in-out;\n    transition: border 0.15s ease-in-out;\n}\n.radio label::after {\n    display: inline-block;\n    position: absolute;\n    content: \" \";\n    width: 11px;\n    height: 11px;\n    left: 3px;\n    top: 3px;\n    margin-left: -20px;\n    border-radius: 50%;\n    background-color: #555555;\n    -webkit-transform: scale(0, 0);\n    -ms-transform: scale(0, 0);\n    -o-transform: scale(0, 0);\n    transform: scale(0, 0);\n    -webkit-transition: -webkit-transform 0.1s cubic-bezier(0.8, -0.33, 0.2, 1.33);\n    -moz-transition: -moz-transform 0.1s cubic-bezier(0.8, -0.33, 0.2, 1.33);\n    -o-transition: -o-transform 0.1s cubic-bezier(0.8, -0.33, 0.2, 1.33);\n    transition: transform 0.1s cubic-bezier(0.8, -0.33, 0.2, 1.33);\n}\n.radio input[type=\"radio\"] {\n    opacity: 0;\n}\n.radio input[type=\"radio\"]:focus + label::before {\n    outline: thin dotted;\n    outline: 5px auto -webkit-focus-ring-color;\n    outline-offset: -2px;\n}\n.radio input[type=\"radio\"]:checked + label::after {\n    -webkit-transform: scale(1, 1);\n    -ms-transform: scale(1, 1);\n    -o-transform: scale(1, 1);\n    transform: scale(1, 1);\n}\n.radio input[type=\"radio\"]:disabled + label {\n    opacity: 0.65;\n}\n.radio input[type=\"radio\"]:disabled + label::before {\n    cursor: not-allowed;\n}\n.radio.radio-inline {\n    margin-top: 0;\n}\n.radio-primary input[type=\"radio\"] + label::after {\n    background-color: #428bca;\n}\n.radio-primary input[type=\"radio\"]:checked + label::before {\n    border-color: #428bca;\n}\n.radio-primary input[type=\"radio\"]:checked + label::after {\n    background-color: #428bca;\n}\n.radio-danger input[type=\"radio\"] + label::after {\n    background-color: #d9534f;\n}\n.radio-danger input[type=\"radio\"]:checked + label::before {\n    border-color: #d9534f;\n}\n.radio-danger input[type=\"radio\"]:checked + label::after {\n    background-color: #d9534f;\n}\n.radio-info input[type=\"radio\"] + label::after {\n    background-color: #5bc0de;\n}\n.radio-info input[type=\"radio\"]:checked + label::before {\n    border-color: #5bc0de;\n}\n.radio-info input[type=\"radio\"]:checked + label::after {\n    background-color: #5bc0de;\n}\n.radio-warning input[type=\"radio\"] + label::after {\n    background-color: #f0ad4e;\n}\n.radio-warning input[type=\"radio\"]:checked + label::before {\n    border-color: #f0ad4e;\n}\n.radio-warning input[type=\"radio\"]:checked + label::after {\n    background-color: #f0ad4e;\n}\n.radio-success input[type=\"radio\"] + label::after {\n    background-color: #5cb85c;\n}\n.radio-success input[type=\"radio\"]:checked + label::before {\n    border-color: #5cb85c;\n}\n.radio-success input[type=\"radio\"]:checked + label::after {\n    background-color: #5cb85c;\n}\n"
  },
  {
    "path": "public/themes/pterodactyl/css/pterodactyl.css",
    "content": "/**\n * Pterodactyl - Panel\n * Copyright (c) 2015 - 2017 Dane Everitt <dane@daneeveritt.com>\n *\n * Permission is hereby granted, free of charge, to any person obtaining a copy\n * of this software and associated documentation files (the \"Software\"), to deal\n * in the Software without restriction, including without limitation the rights\n * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n * copies of the Software, and to permit persons to whom the Software is\n * furnished to do so, subject to the following conditions:\n *\n * The above copyright notice and this permission notice shall be included in all\n * copies or substantial portions of the Software.\n *\n * THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n * SOFTWARE.\n */\n @import 'checkbox.css';\n\n.login-page {\n    background: #10529f;\n}\n\n#login-position-elements {\n    margin: 25% auto;\n}\n\n.login-logo {\n    color: #fff;\n    font-weight: 400;\n}\n\n.login-copyright {\n    color: rgba(255, 255, 255, 0.3);\n}\n\n.login-copyright > a {\n    color: rgba(255, 255, 255, 0.6);\n}\n\n.particles-js-canvas-el {\n    position: absolute;\n    width: 100%;\n    height: 100%;\n    top: 0;\n    z-index: -1;\n}\n\n.pterodactyl-login-box {\n    background: rgba(0, 0, 0, 0.25);\n    border-radius: 3px;\n    padding: 20px;\n}\n\n.pterodactyl-login-input > input {\n    background: rgba(0, 0, 0, 0.4);\n    border: 1px solid #000;\n    border-radius: 2px;\n    color: #fff;\n}\n\n.pterodactyl-login-input > .form-control-feedback {\n    color: #fff;\n}\n\n.pterodactyl-login-button--main {\n    background: rgba(0, 0, 0, 0.4);\n    border: 1px solid #000;\n    border-radius: 2px;\n    color: #fff;\n}\n\n.pterodactyl-login-button--main:hover {\n    background: rgba(0, 0, 0, 0.7);\n    border: 1px solid #000;\n    border-radius: 2px;\n    color: #fff;\n}\n\n.pterodactyl-login-button--left {\n    background: rgba(255, 255, 255, 0.4);\n    border: 1px solid rgba(255, 255, 255, 0.6);\n    border-radius: 2px;\n    color: #fff;\n}\n\n.pterodactyl-login-button--left:hover {\n    background: rgba(255, 255, 255, 0.6);\n    border: 1px solid rgba(255, 255, 255, 0.8);\n    border-radius: 2px;\n    color: #fff;\n}\n\n.weight-100 {\n    font-weight: 100;\n}\n\n.weight-300 {\n    font-weight: 300;\n}\n\n.btn-clear {\n    background: transparent;\n}\n\n.user-panel > .info {\n    position: relative;\n    left: 0;\n}\n\ncode {\n    background-color: #eef1f6;\n    color: #596981;\n    border-radius: 2px;\n    padding-left: 4px;\n    padding-right: 4px;\n    line-height: 1.4;\n    font-size: 85%;\n    border: 1px solid rgba(0, 0, 0, .1);\n    display: inline-block;\n}\n\np {\n    line-height: 1.6 !important;\n}\n\np.small {\n    margin-top: 3px !important;\n}\n\n.control-sidebar-dark .control-sidebar-menu > li > a.active {\n    background: #1e282c;\n}\n\n.callout-nomargin {\n    margin: 0;\n}\n\n.table {\n    font-size: 14px !important;\n}\n\n.table .min-size {\n    width:1px;\n    white-space: nowrap;\n}\n\n@media (max-width:767px) {\n    .box-header > .box-tools {\n        position: relative !important;\n        padding: 0px 10px 10px;\n    }\n}\n\n.middle, .align-middle {\n    vertical-align: middle !important;\n}\n\n#fileOptionMenu.dropdown-menu > li > a {\n    padding:3px 6px;\n}\n\n.hasFileHover {\n    border: 2px dashed #0087F7;\n    border-top: 0 !important;\n    border-radius: 5px;\n    margin: 0;\n    opacity: 0.5;\n}\n\n.hasFileHover * {\n    pointer-events: none !important;\n}\n\ntd.has-progress {\n    padding: 0px !important;\n    border-top: 0px !important;\n}\n\n.progress.progress-table-bottom {\n    margin: 0 !important;\n    height:5px !important;\n    padding:0;\n    border:0;\n}\n\n.muted {\n    filter: alpha(opacity=20);\n    opacity: 0.2;\n}\n\n.muted-hover:hover {\n    filter: alpha(opacity=100);\n    opacity: 1;\n}\n\n.use-pointer {\n    cursor: pointer !important;\n}\n\n.input-loader {\n    display: none;\n    position:relative;\n    top: -25px;\n    float: right;\n    right: 5px;\n    color: #cccccc;\n    height: 0;\n}\n\n.box-header > .form-group {\n    margin-bottom: 0;\n}\n\n.box-header > .form-group > div > p.small {\n    margin: 0;\n}\n\n.no-margin {\n    margin: 0 !important;\n}\n\nli.select2-results__option--highlighted[aria-selected=\"false\"] > .user-block > .username > a {\n    color: #fff;\n}\n\nli.select2-results__option--highlighted[aria-selected=\"false\"] > .user-block > .description {\n    color: #eee;\n}\n\n.select2-selection.select2-selection--multiple {\n    min-height: 36px !important;\n}\n\n.select2-search--inline .select2-search__field:focus {\n    outline: none;\n    border: 0 !important;\n}\n\n.img-bordered-xs {\n    border: 1px solid #d2d6de;\n    padding: 1px;\n}\n\nspan[aria-labelledby=\"select2-pUserId-container\"] {\n    padding-left: 2px !important;\n}\n\n.box {\n    box-shadow: 0 0 0 1px rgba(89, 105, 128, .1), 0 1px 3px 0 rgba(89, 105, 128, .1), 0 1px 2px 0 rgba(0, 0, 0, .05) !important;\n}\n\n.alert-danger {\n    color: #ffffff !important;\n    background: #d64242 !important;\n    border: 1px solid #841d1d;\n}\n\n.alert-info {\n    color: #ffffff !important;\n    background: #408fec !important;\n    border: 1px solid #1055a5;\n}\n\n.alert-success {\n    color: #ffffff !important;\n    background: #51b060 !important;\n    border: 1px solid #2b5f33;\n}\n\n.alert-warning {\n    color: #ffffff !important;\n    background: #fa9636 !important;\n    border: 1px solid #b45b05;\n}\n\n.callout-slim a {\n    color: #555 !important;\n}\n\n.bg-purple {\n    background-color: #79589f !important;\n}\n\n.label-default {\n    background-color: #eef1f6 !important;\n}\n\n.callout.callout-info.callout-slim {\n    border: 1px solid #1055a5 !important;\n    border-left: 5px solid #1055a5 !important;\n    border-right: 5px solid #1055a5 !important;\n    color: #777 !important;\n    background: transparent !important;\n}\n\n.callout.callout-danger.callout-slim {\n    border: 1px solid #c23321 !important;\n    border-left: 5px solid #c23321 !important;\n    border-right: 5px solid #c23321 !important;\n    color: #777 !important;\n    background: transparent !important;\n}\n\n.callout.callout-warning.callout-slim {\n    border: 1px solid #c87f0a !important;\n    border-left: 5px solid #c87f0a !important;\n    border-right: 5px solid #c87f0a !important;\n    color: #777 !important;\n    background: transparent !important;\n}\n\n.callout.callout-success.callout-slim {\n    border: 1px solid #00733e !important;\n    border-left: 5px solid #00733e !important;\n    border-right: 5px solid #00733e !important;\n    color: #777 !important;\n    background: transparent !important;\n}\n\n.callout.callout-default.callout-slim {\n    border: 1px solid #eee !important;\n    border-left: 5px solid #eee !important;\n    border-right: 5px solid #eee !important;\n    color: #777 !important;\n    background: transparent !important;\n}\n\n.callout code {\n    background-color: #515f6cbb;\n    color: #c3c3c3;\n    border: 1px solid rgba(0, 0, 0, .25);\n}\n\n.tab-pane .box-footer {\n    margin: 0 -10px -10px;\n}\n\n.select2-container{ width: 100% !important; }\n\n.nav-tabs-custom > .nav-tabs > li:hover {\n    border-top-color:#3c8dbc;\n}\n\n.nav-tabs-custom > .nav-tabs > li.active.tab-danger, .nav-tabs-custom > .nav-tabs > li.tab-danger:hover {\n    border-top-color: #c23321;\n}\n\n.nav-tabs-custom > .nav-tabs > li.active.tab-success, .nav-tabs-custom > .nav-tabs > li.tab-success:hover {\n    border-top-color: #00733e;\n}\n\n.nav-tabs-custom > .nav-tabs > li.active.tab-info, .nav-tabs-custom > .nav-tabs > li.tab-info:hover {\n    border-top-color: #0097bc;\n}\n\n.nav-tabs-custom > .nav-tabs > li.active.tab-warning, .nav-tabs-custom > .nav-tabs > li.tab-warning:hover {\n    border-top-color: #c87f0a;\n}\n\n.nav-tabs-custom.nav-tabs-floating > .nav-tabs {\n    border-bottom: 0px !important;\n}\n\n.nav-tabs-custom.nav-tabs-floating > .nav-tabs > li {\n    margin-bottom: 0px !important;\n}\n\n.nav-tabs-custom.nav-tabs-floating > .nav-tabs > li:first-child.active,\n.nav-tabs-custom.nav-tabs-floating > .nav-tabs > li:first-child:hover {\n    border-radius: 3px 0 0 0;\n}\n\n.nav-tabs-custom.nav-tabs-floating > .nav-tabs > li:first-child.active > a {\n    border-radius: 0 0 0 3px;\n}\n\n.position-relative {\n    position: relative;\n}\n\n.no-pad-bottom {\n    padding-bottom: 0 !important;\n}\n\n.no-margin-bottom {\n    margin-bottom: 0 !important;\n}\n\n.btn-icon > i.fa {\n    line-height: 1.5;\n}\n\n.btn.active, .btn.active.focus {\n    background-color: #408fec;\n}\n\n.strong {\n    font-weight: bold !important;\n}\n\n.server-description > td {\n    padding-top: 0 !important;\n    border-top: 0 !important;\n}\n\ntr:hover + tr.server-description {\n    background-color: #f5f5f5 !important;\n}\n\n.login-corner-info {\n    position: absolute;\n    bottom: 5px;\n    right: 10px;\n    color: white;\n}\n\ninput.form-autocomplete-stop[readonly] {\n    background: inherit;\n    cursor: text;\n}\n\n/* fix Google Recaptcha badge */\n.grecaptcha-badge {\n    bottom: 54px !important;\n    background: white;\n    box-shadow: none !important;\n}\n\n.dropdown-massactions {\n    min-width: 80px;\n}\n\n.select-all-files {\n    position: relative;\n    bottom: 1px;\n    margin-right: 7px !important;\n}\n\n.select-file {\n    position: relative;\n    bottom: 1px;\n    margin-right: 2px !important;\n}\n\n.select-folder {\n    position: relative;\n    bottom: 1px;\n    margin-right: 5px !important;\n}\n\nlabel.control-label > span {\n    font-size: 80%;\n    font-weight: 400;\n    font-style: italic;\n    color: #dd4b39;\n}\n\nlabel.control-label > span.field-required:before {\n    content: \"必需\";\n    color: #dd4b39;\n}\n\nlabel.control-label > span.field-optional:before {\n    content: \"可选\";\n    color: #bbbbbb;\n}\n\n.pagination > li > a, .pagination > li > span {\n    padding: 3px 10px !important;\n}\n\n.logo-mini > img {\n    height: 42px;\n    width: auto;\n}\n\n.search01 {\n    width: 30%;\n}\n\n.number-info-box-content {\n    padding: 15px 10px 0;\n}\n\n\n/* *******\n\n  > Version v1.0\n\n******* */\n\nbody {\n    color: #cad1d8;\n}\n\n.fixed .main-header {\n    box-shadow: 0 4px 8px 0 rgba(0,0,0,.12), 0 2px 4px 0 rgba(0,0,0,.08);\n}\n\n.skin-blue .wrapper, .skin-blue .main-sidebar, .skin-blue .left-side {\n    background-color: #181f27;\n    box-shadow: 0 4px 8px 0 rgba(0,0,0,.12), 0 2px 4px 0 rgba(0,0,0,.08);\n}\n\n.skin-blue .main-header .logo {\n    background-color: #1f2933;\n    color: #9aa5b1;\n}\n\n.skin-blue .main-header .navbar .sidebar-toggle {\n    color: #9aa5b1;\n}\n\n.skin-blue .main-header .navbar .nav>li>a {\n    color: #9aa5b1;\n}\n\n.skin-blue .sidebar-menu>li.header {\n    color: #797979;\n    background: #0e111582;\n}\n\n.skin-blue .main-header .navbar {\n    background-color: #1f2933;\n}\n\n.skin-blue .main-header .navbar .sidebar-toggle:hover {\n    background-color: #1c252e;\n}\n\n.skin-blue .main-header .logo:hover {\n    background-color: #1c252e;\n}\n\n.main-footer {\n    background: #1f2933;\n    color: #9aa5b1;\n    border-top: 1px solid #1f2933;\n}\n\n.skin-blue .sidebar-menu>li.active>a {\n    border-left-color: #099aa5;\n}\n\n.text-gray {\n    color: #9aa5b1 !important;\n}\n\n.text-green {\n    color: #00a65a !important;\n}\n\n.text-muted {\n    color: #9aa5b1 !important;\n}\n\n.text-danger {\n    color: #ff1c00;\n}\n\n.content-wrapper {\n    background-color: #33404d;\n}\n\n.btn-success {\n    background-color: #189a1c;\n    border-color: #0f8513;\n}\n\n.btn.btn-green:hover {\n    background-color: #0f8513;\n    border-color: #0e7717;\n}\n\n.btn-primary {\n    background-color: #0967d3;\n    border-color: #0550b3;\n}\n\n.btn.btn-primary:hover {\n    background-color: #0550b3;\n    border-color: #0345a0;\n}\n\n.box {\n    box-shadow: 0 4px 8px 0 rgba(0,0,0,.12), 0 2px 4px 0 rgba(0,0,0,.08) !important;\n    background: #3f4d5a;\n    border-top: 3px solid #1f2933;\n}\n\n.box-header {\n    color: #cad1d8;\n    background: #1f2933;\n}\n\n.box-header.with-border {\n    border-bottom: 1px solid #1f2933;\n}\n\n.box.box-default {\n    border-top-color: #1f2933;\n}\n\n.box-footer {\n    border-top: 1px solid #4d5b69;\n    background-color: #3f4d5a;\n}\n.content-header>.breadcrumb>li>a {\n    color: #cad1d8;\n}\n\n.breadcrumb>.active {\n    color: #cad1d8;\n}\n\n.h1 .small, .h1 small, .h2 .small, .h2 small, .h3 .small, .h3 small, .h4 .small, .h4 small, .h5 .small, .h5 small, .h6 .small, .h6 small, h1 .small, h1 small, h2 .small, h2 small, h3 .small, h3 small, h4 .small, h4 small, h5 .small, h5 small, h6 .small, h6 small {\n    color: #cad1d8;\n}\n\n.table>thead>tr>th, .table>tbody>tr>th, .table>tfoot>tr>th, .table>thead>tr>td, .table>tbody>tr>td, .table>tfoot>tr>td {\n    border-top: 1px solid #4d5b69;\n}\n\n.table>thead>tr>th {\n    border-bottom: 2px solid #4d5b69;\n}\n\n.table-hover>tbody>tr:hover {\n    background-color: #33404d;\n}\n\na {\n    color: #007eff;\n}\n\n.nav-tabs-custom {\n    background: #1f2933;\n}\n\n.nav-tabs-custom>.nav-tabs>li.active {\n    border-top-color: #099aa5;\n}\n\n.nav-tabs-custom>.nav-tabs>li.active>a {\n    border-top-color: transparent;\n    border-left-color: #15161c;\n    border-right-color: #15161c;\n    background: #13181e;\n}\n\n.nav-tabs-custom>.nav-tabs>li>a {\n    color: #9aa5b1;\n}\n\n.nav-tabs-custom>.nav-tabs>li.active>a, .nav-tabs-custom>.nav-tabs>li.active:hover>a {\n    color: #9aa5b1;\n}\n\ninput.form-control {\n    padding: .75rem;\n    background-color: #515f6cbb;\n    border-width: 1px;\n    border-color: #606d7b;\n    border-radius: .25rem;\n    color: #cad1d8;\n    box-shadow: none;\n    -webkit-transition: border .15s linear,box-shaodw .15s ease-in;\n    transition: border .15s linear,box-shaodw .15s ease-in;\n}\n\ntextarea.form-control {\n    padding: .75rem;\n    background-color: #515f6cbb;\n    border-width: 1px;\n    border-color: #606d7b;\n    border-radius: .25rem;\n    color: #cad1d8;\n    box-shadow: none;\n    -webkit-transition: border .15s linear,box-shaodw .15s ease-in;\n    transition: border .15s linear,box-shaodw .15s ease-in;\n}\n\n.input-group .input-group-addon {\n    border-color: #606d7b;\n    background-color: #515f6cbb;\n    color: #cad1d8;\n}\n\n.select2-container--default .select2-selection--single, .select2-selection .select2-selection--single {\n    border: 1px solid #606d7b;\n}\n\n.select2-container--default .select2-selection--single {\n    background-color: #515f6cbb;\n}\n\n.select2-container--default .select2-selection--single .select2-selection__rendered {\n    color: #cad1d8;\n}\n\n.select2-container--default .select2-selection--multiple {\n    background-color: #515f6cbb;\n}\n\n.select2-container--default .select2-selection--multiple {\n    border: 1px solid #606d7b;\n    border-radius: 0;\n}\n\ncode {\n    background-color: #515f6cbb;\n    color: #c3c3c3;\n    border: 1px solid rgba(0, 0, 0, .25);\n}\n\n.btn-default {\n    background-color: #33404d;\n    color: #cad1d8;\n    border-color: #606d7b;\n}\n\n.select2-results__option {\n    background-color: #b5bcc1;\n    color: #444;\n}\n\n.select2-container--default .select2-results__option--highlighted[aria-selected] {\n    background-color: #3c8dbc;\n}\n\n.modal-body {\n    background: #3f4d5a;\n}\n\n.modal-header {\n    background: #3f4d5a;\n    border-bottom-color: #4d5b69;\n}\n\n.modal-footer {\n    background: #3f4d5a;\n    border-top-color: #4d5b69;\n}\n\n@media (max-width: 991px) {\n    .content-header>.breadcrumb {\n        background: #1f2933 !important;\n    }\n}\n\n.nav-tabs-custom>.nav-tabs>li.active>a, .nav-tabs-custom>.nav-tabs>li.active:hover>a {\n     background-color: #101216;\n}\n\n.select2-container--default .select2-results__option[aria-selected=true], .select2-container--default .select2-results__option[aria-selected=true]:hover {\n    color: #fff;\n}\n\n.select2-dropdown {\n    background-color: #515f6cbb;\n    border: 1px solid #606d7b;\n}\n.select2-container--default.select2-container--focus .select2-selection--multiple, .select2-container--default .select2-search--dropdown .select2-search__field {\n    border-color: #d2d6de !important;\n    background-color: #515f6cbb;\n}\n\n.select2-container--default .select2-results__option--highlighted[aria-selected] {\n    background-color: #099aa5;\n}\n\na {\n    color: #288afb;\n}\n\na:hover {\n    color: #206ec7;\n}\n\n.form-control {\n    border-color: #606d7b;\n    background-color: #515f6cbb;\n    color: #cad1d8;\n}\n\n.form-control[disabled], .form-control[readonly],\nfieldset[disabled] .form-control {\n    background-color: #1f2933;\n    color: #cad1d8;\n    cursor: not-allowed;\n}\n\n.well {\n    min-height: 20px;\n    padding: 19px;\n    margin-bottom: 20px;\n    background-color: #515f6cbb;\n    border: 1px solid #606d7b;\n}\n\n.well-lg {\n    padding: 24px;\n}\n\n.well-sm {\n    padding: 9px;\n}\n\n.small-box h3, .small-box p {\n    color: #c3c3c3;\n}\n\n.small-box-footer {\n    color: #288afb;\n}\n\n.small-box .icon {\n    color: #cad1d8;\n}\n\n.bg-gray {\n    background-color: #33404d !important;\n}\n\npre {\n    color: #cad1d8;\n    background-color: #515f6cbb;\n    border-color: #1f2933;\n}\n\n/* Make the row a flex container so all columns in the same row can have equal height */\n.equal-height {\n    display: flex;\n    flex-wrap: wrap;\n}\n\n.equal-height>[class*=\"col-\"] {\n    display: flex;\n}\n\n.equal-height .box {\n    display: flex;\n    flex-direction: column;\n    width: 100%;\n}\n\n.equal-height .box-body {\n    flex: 1;\n}\n"
  },
  {
    "path": "public/themes/pterodactyl/css/terminal.css",
    "content": "/*Design for Terminal*/\n@import url('https://fonts.googleapis.com/css?family=Source+Code+Pro');\n\n#terminal-body {\n    background: rgb(26, 26, 26);\n    margin: 0;\n    width: 100%;\n    height: 100%;\n    overflow: hidden;\n}\n\n#terminal {\n    font-family: 'Source Code Pro', monospace;\n    color: rgb(223, 223, 223);\n    background: rgb(26, 26, 26);\n    font-size: 12px;\n    line-height: 14px;\n    padding: 10px 10px 0;\n    box-sizing: border-box;\n    height: 500px;\n    max-height: 500px;\n    overflow-y: auto;\n    overflow-x: hidden;\n    border-radius: 5px 5px 0 0;\n}\n\n#terminal > .cmd {\n    padding: 1px 0;\n    word-wrap: break-word;\n    white-space: pre-wrap;\n}\n\n#terminal_input {\n    width: 100%;\n    background: rgb(26, 26, 26);\n    border-radius: 0 0 5px 5px;\n    padding: 0 0 0 10px !important;\n}\n\n.terminal_input--input, .terminal_input--prompt {\n    font-family: 'Source Code Pro', monospace;\n    margin-bottom: 0;\n    border: 0 !important;\n    background: transparent !important;\n    color: rgb(223, 223, 223);\n    font-size: 12px;\n    padding: 1px 0 4px !important;\n}\n.terminal_input--input {\n    margin-left: 6px;\n    line-height: 1;\n    outline: none !important;\n}\n\n.terminal-notify {\n    position: absolute;\n    right: 30px;\n    bottom: 30px;\n    padding: 3.5px 7px;\n    border-radius: 3px;\n    background: #fff;\n    color: #000;\n    opacity: .5;\n    font-size: 16px;\n    cursor: pointer;\n    z-index: 10;\n}\n\n.terminal-notify:hover {\n    opacity: .9;\n}\n\n.ansi-black-fg { color: rgb(0, 0, 0); }\n.ansi-red-fg { color: rgb(166, 0, 44); }\n.ansi-green-fg { color: rgb(55, 106, 27); }\n.ansi-yellow-fg { color: rgb(241, 133, 24); }\n.ansi-blue-fg { color: rgb(17, 56, 163); }\n.ansi-magenta-fg { color: rgb(67, 0, 117); }\n.ansi-cyan-fg { color: rgb(18, 95, 105); }\n.ansi-white-fg { color: rgb(255, 255, 255); }\n.ansi-bright-black-fg { color: rgb(51, 51, 51); }\n.ansi-bright-red-fg { color: rgb(223, 45, 39); }\n.ansi-bright-green-fg { color: rgb(105, 175, 45); }\n.ansi-bright-yellow-fg { color: rgb(254, 232, 57); }\n.ansi-bright-blue-fg { color: rgb(68, 145, 240); }\n.ansi-bright-magenta-fg { color: rgb(151, 50, 174); }\n.ansi-bright-cyan-fg{ color: rgb(37, 173, 98); }\n.ansi-bright-white-fg { color: rgb(208, 208, 208); }\n\n.ansi-black-bg { background: rgb(0, 0, 0); }\n.ansi-red-bg { background: rgb(166, 0, 44); }\n.ansi-green-bg { background: rgb(55, 106, 27); }\n.ansi-yellow-bg { background: rgb(241, 133, 24); }\n.ansi-blue-bg { background: rgb(17, 56, 163); }\n.ansi-magenta-bg { background: rgb(67, 0, 117); }\n.ansi-cyan-bg { background: rgb(18, 95, 105); }\n.ansi-white-bg { background: rgb(255, 255, 255); }\n.ansi-bright-black-bg { background: rgb(51, 51, 51); }\n.ansi-bright-red-bg { background: rgb(223, 45, 39); }\n.ansi-bright-green-bg { background: rgb(105, 175, 45); }\n.ansi-bright-yellow-bg { background: rgb(254, 232, 57); }\n.ansi-bright-blue-bg { background: rgb(68, 145, 240); }\n.ansi-bright-magenta-bg { background: rgb(151, 50, 174); }\n.ansi-bright-cyan-bg { background: rgb(37, 173, 98); }\n.ansi-bright-white-bg { background: rgb(208, 208, 208); }\n"
  },
  {
    "path": "public/themes/pterodactyl/js/admin/functions.js",
    "content": "// Copyright (c) 2015 - 2017 Dane Everitt <dane@daneeveritt.com>\n//\n// Permission is hereby granted, free of charge, to any person obtaining a copy\n// of this software and associated documentation files (the \"Software\"), to deal\n// in the Software without restriction, including without limitation the rights\n// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n// copies of the Software, and to permit persons to whom the Software is\n// furnished to do so, subject to the following conditions:\n//\n// The above copyright notice and this permission notice shall be included in all\n// copies or substantial portions of the Software.\n//\n// THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n// SOFTWARE.\n$.urlParam=function(name){var results=new RegExp(\"[\\\\?&]\"+name+\"=([^&#]*)\").exec(decodeURIComponent(window.location.href));if(results==null){return null}else{return results[1]||0}};function getPageName(url){var index=url.lastIndexOf(\"/\")+1;var filenameWithExtension=url.substr(index);var filename=filenameWithExtension.split(\".\")[0];return filename}\n// Remeber Active Tab and Navigate to it on Reload\nfor(var queryParameters={},queryString=location.search.substring(1),re=/([^&=]+)=([^&]*)/g,m;m=re.exec(queryString);)queryParameters[decodeURIComponent(m[1])]=decodeURIComponent(m[2]);$(\"a[data-toggle='tab']\").click(function(){queryParameters.tab=$(this).attr(\"href\").substring(1),window.history.pushState(null,null,location.pathname+\"?\"+$.param(queryParameters))});\nif($.urlParam('tab') != null){$('.nav.nav-tabs a[href=\"#' + $.urlParam('tab') + '\"]').tab('show');}\n"
  },
  {
    "path": "public/themes/pterodactyl/js/admin/new-server.js",
    "content": "// Copyright (c) 2015 - 2017 Dane Everitt <dane@daneeveritt.com>\n//\n// Permission is hereby granted, free of charge, to any person obtaining a copy\n// of this software and associated documentation files (the \"Software\"), to deal\n// in the Software without restriction, including without limitation the rights\n// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n// copies of the Software, and to permit persons to whom the Software is\n// furnished to do so, subject to the following conditions:\n//\n// The above copyright notice and this permission notice shall be included in all\n// copies or substantial portions of the Software.\n//\n// THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n// SOFTWARE.\n$(document).ready(function() {\n    $('#pNestId').select2({\n        placeholder: '选择预设组',\n    }).change();\n\n    $('#pEggId').select2({\n        placeholder: '选择预设',\n    });\n\n    $('#pPackId').select2({\n        placeholder: '选择服务包',\n    });\n\n    $('#pNodeId').select2({\n        placeholder: '选择节点',\n    }).change();\n\n    $('#pAllocation').select2({\n        placeholder: '选择默认网络分配',\n    });\n\n    $('#pAllocationAdditional').select2({\n        placeholder: '选择额外的网络分配',\n    });\n});\n\nlet lastActiveBox = null;\n$(document).on('click', function (event) {\n    if (lastActiveBox !== null) {\n        lastActiveBox.removeClass('box-primary');\n    }\n\n    lastActiveBox = $(event.target).closest('.box');\n    lastActiveBox.addClass('box-primary');\n});\n\n$('#pNodeId').on('change', function () {\n    currentNode = $(this).val();\n    $.each(Pterodactyl.nodeData, function (i, v) {\n        if (v.id == currentNode) {\n            $('#pAllocation').html('').select2({\n                data: v.allocations,\n                placeholder: '选择默认网络分配',\n            });\n\n            updateAdditionalAllocations();\n        }\n    });\n});\n\n$('#pNestId').on('change', function (event) {\n    $('#pEggId').html('').select2({\n        data: $.map(_.get(Pterodactyl.nests, $(this).val() + '.eggs', []), function (item) {\n            return {\n                id: item.id,\n                text: item.name,\n            };\n        }),\n    }).change();\n});\n\n$('#pEggId').on('change', function (event) {\n    let parentChain = _.get(Pterodactyl.nests, $('#pNestId').val(), null);\n    let objectChain = _.get(parentChain, 'eggs.' + $(this).val(), null);\n\n    const images = _.get(objectChain, 'docker_images', {})\n    $('#pDefaultContainer').html('');\n    const keys = Object.keys(images);\n    for (let i = 0; i < keys.length; i++) {\n        let opt = document.createElement('option');\n        opt.value = images[keys[i]];\n        opt.innerText = keys[i] + \" (\" + images[keys[i]] + \")\";\n        $('#pDefaultContainer').append(opt);\n    }\n\n    if (!_.get(objectChain, 'startup', false)) {\n        $('#pStartup').val(_.get(parentChain, 'startup', '错误：没有定义启动！'));\n    } else {\n        $('#pStartup').val(_.get(objectChain, 'startup'));\n    }\n\n    $('#pPackId').html('').select2({\n        data: [{ id: 0, text: 'No Service Pack' }].concat(\n            $.map(_.get(objectChain, 'packs', []), function (item, i) {\n                return {\n                    id: item.id,\n                    text: item.name + ' (' + item.version + ')',\n                };\n            })\n        ),\n    });\n\n    function escapeHtml(str) {\n        var div = document.createElement('div');\n        div.appendChild(document.createTextNode(str));\n        return div.innerHTML;\n    }\n\n    const variableIds = {};\n    $('#appendVariablesTo').html('');\n    $.each(_.get(objectChain, 'variables', []), function (i, item) {\n        variableIds[item.env_variable] = 'var_ref_' + item.id;\n\n        let isRequired = (item.required === 1) ? '<span class=\"label label-danger\">必需</span> ' : '';\n        let dataAppend = ' \\\n            <div class=\"form-group col-sm-6\"> \\\n                <label for=\"var_ref_' + escapeHtml(item.id) + '\" class=\"control-label\">' + isRequired + escapeHtml(item.name) + '</label> \\\n                <input type=\"text\" id=\"var_ref_' + escapeHtml(item.id) + '\" autocomplete=\"off\" name=\"environment[' + escapeHtml(item.env_variable) + ']\" class=\"form-control\" value=\"' + escapeHtml(item.default_value) + '\" /> \\\n                <p class=\"text-muted small\">' + escapeHtml(item.description) + '<br /> \\\n                <strong>启动时访问:</strong> <code>{{' + escapeHtml(item.env_variable) + '}}</code><br /> \\\n                <strong>验证规则:</strong> <code>' + escapeHtml(item.rules) + '</code></small></p> \\\n            </div> \\\n        ';\n        $('#appendVariablesTo').append(dataAppend);\n    });\n\n    // If you receive a warning on this line, it should be fine to ignore. this function is\n    // defined in \"resources/views/admin/servers/new.blade.php\" near the bottom of the file.\n    serviceVariablesUpdated($('#pEggId').val(), variableIds);\n});\n\n$('#pAllocation').on('change', function () {\n    updateAdditionalAllocations();\n});\n\nfunction updateAdditionalAllocations() {\n    let currentAllocation = $('#pAllocation').val();\n    let currentNode = $('#pNodeId').val();\n\n    $.each(Pterodactyl.nodeData, function (i, v) {\n        if (v.id == currentNode) {\n            let allocations = [];\n\n            for (let i = 0; i < v.allocations.length; i++) {\n                const allocation = v.allocations[i];\n\n                if (allocation.id != currentAllocation) {\n                    allocations.push(allocation);\n                }\n            }\n\n            $('#pAllocationAdditional').html('').select2({\n                data: allocations,\n                placeholder: '选择额外的网络分配',\n            });\n        }\n    });\n}\n\nfunction initUserIdSelect(data) {\n    function escapeHtml(str) {\n        var div = document.createElement('div');\n        div.appendChild(document.createTextNode(str));\n        return div.innerHTML;\n    }\n\n    $('#pUserId').select2({\n        ajax: {\n            url: '/admin/users/accounts.json',\n            dataType: 'json',\n            delay: 250,\n\n            data: function (params) {\n                return {\n                    filter: { email: params.term },\n                    page: params.page,\n                };\n            },\n\n            processResults: function (data, params) {\n                return { results: data };\n            },\n\n            cache: true,\n        },\n\n        data: data,\n        escapeMarkup: function (markup) { return markup; },\n        minimumInputLength: 2,\n        templateResult: function (data) {\n            if (data.loading) return escapeHtml(data.text);\n\n            return '<div class=\"user-block\"> \\\n                <img class=\"img-circle img-bordered-xs\" src=\"https://cravatar.cn/avatar/' + escapeHtml(data.md5) + '?s=120\" alt=\"User Image\"> \\\n                <span class=\"username\"> \\\n                    <a href=\"#\">' + escapeHtml(data.name_first) + ' ' + escapeHtml(data.name_last) +'</a> \\\n                </span> \\\n                <span class=\"description\"><strong>' + escapeHtml(data.email) + '</strong> - ' + escapeHtml(data.username) + '</span> \\\n            </div>';\n        },\n        templateSelection: function (data) {\n            return '<div> \\\n                <span> \\\n                    <img class=\"img-rounded img-bordered-xs\" src=\"https://cravatar.cn/avatar/' + escapeHtml(data.md5) + '?s=120\" style=\"height:28px;margin-top:-4px;\" alt=\"User Image\"> \\\n                </span> \\\n                <span style=\"padding-left:5px;\"> \\\n                    ' + escapeHtml(data.name_first) + ' ' + escapeHtml(data.name_last) + ' (<strong>' + escapeHtml(data.email) + '</strong>) \\\n                </span> \\\n            </div>';\n        }\n\n    });\n}\n"
  },
  {
    "path": "public/themes/pterodactyl/js/admin/server/transfer.js",
    "content": "$(document).ready(function () {\n    const $modal = $('#transferServerModal');\n\n    $('#pNodeId').select2({\n        placeholder: 'Select a Node',\n        dropdownParent: $modal,\n    }).change();\n\n    $('#pAllocation').select2({\n        placeholder: 'Select a Default Allocation',\n        dropdownParent: $modal,\n    });\n\n    $('#pAllocationAdditional').select2({\n        placeholder: 'Select Additional Allocations',\n        dropdownParent: $modal,\n    });\n});\n\n$('#pNodeId').on('change', function () {\n    let currentNode = $(this).val();\n    const $modal = $('#transferServerModal');\n\n    $.each(Pterodactyl.nodeData, function (i, v) {\n        if (v.id == currentNode) {\n            $('#pAllocation').html('').select2({\n                data: v.allocations,\n                placeholder: 'Select a Default Allocation',\n                dropdownParent: $modal,\n            });\n\n            updateAdditionalAllocations();\n        }\n    });\n});\n\n$('#pAllocation').on('change', function () {\n    updateAdditionalAllocations();\n});\n\nfunction updateAdditionalAllocations() {\n    let currentAllocation = $('#pAllocation').val();\n    let currentNode = $('#pNodeId').val();\n    const $modal = $('#transferServerModal');\n\n    $.each(Pterodactyl.nodeData, function (i, v) {\n        if (v.id == currentNode) {\n            let allocations = [];\n\n            for (let i = 0; i < v.allocations.length; i++) {\n                const allocation = v.allocations[i];\n\n                if (allocation.id != currentAllocation) {\n                    allocations.push(allocation);\n                }\n            }\n\n            $('#pAllocationAdditional').html('').select2({\n                data: allocations,\n                placeholder: 'Select Additional Allocations',\n                dropdownParent: $modal,\n            });\n        }\n    });\n}\n"
  },
  {
    "path": "public/themes/pterodactyl/js/plugins/minecraft/eula.js",
    "content": "// Copyright (c) 2015 - 2017 Dane Everitt <dane@daneeveritt.com>\n//\n// Permission is hereby granted, free of charge, to any person obtaining a copy\n// of this software and associated documentation files (the \"Software\"), to deal\n// in the Software without restriction, including without limitation the rights\n// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n// copies of the Software, and to permit persons to whom the Software is\n// furnished to do so, subject to the following conditions:\n//\n// The above copyright notice and this permission notice shall be included in all\n// copies or substantial portions of the Software.\n//\n// THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n// SOFTWARE.\n$(document).ready(function () {\n    Socket.on('console', function (data) {\n        if (typeof data === 'undefined' || typeof data.line === 'undefined') {\n            return;\n        }\n\n        if (~data.line.indexOf('You need to agree to the EULA in order to run the server')) {\n            swal({\n                title: 'EULA Acceptance',\n                text: 'By pressing \\'I Accept\\' below you are indicating your agreement to the <a href=\"https://account.mojang.com/documents/minecraft_eula\" target=\"_blank\">Mojang EULA</a>.',\n                type: 'info',\n                html: true,\n                showCancelButton: true,\n                showConfirmButton: true,\n                cancelButtonText: 'I do not Accept',\n                confirmButtonText: 'I Accept',\n                closeOnConfirm: false,\n                showLoaderOnConfirm: true\n            }, function () {\n                $.ajax({\n                    type: 'POST',\n                    url: Pterodactyl.meta.saveFile,\n                    headers: { 'X-CSRF-Token': Pterodactyl.meta.csrfToken, },\n                    data: {\n                        file: 'eula.txt',\n                        contents: 'eula=true'\n                    }\n                }).done(function (data) {\n                    $('[data-attr=\"power\"][data-action=\"start\"]').trigger('click');\n                    swal({\n                        type: 'success',\n                        title: '',\n                        text: 'The EULA for this server has been accepted, restarting server now.',\n                    });\n                }).fail(function (jqXHR) {\n                    console.error(jqXHR);\n                    swal({\n                        title: 'Whoops!',\n                        text: 'An error occurred while attempting to set the EULA as accepted: ' + jqXHR.responseJSON.error,\n                        type: 'error'\n                    })\n                });\n            });\n        }\n    });\n});\n"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ace.js",
    "content": "(function(){function o(n){var i=e;n&&(e[n]||(e[n]={}),i=e[n]);if(!i.define||!i.define.packaged)t.original=i.define,i.define=t,i.define.packaged=!0;if(!i.require||!i.require.packaged)r.original=i.require,i.require=r,i.require.packaged=!0}var ACE_NAMESPACE=\"\",e=function(){return this}();!e&&typeof window!=\"undefined\"&&(e=window);if(!ACE_NAMESPACE&&typeof requirejs!=\"undefined\")return;var t=function(e,n,r){if(typeof e!=\"string\"){t.original?t.original.apply(this,arguments):(console.error(\"dropping module because define wasn't a string.\"),console.trace());return}arguments.length==2&&(r=n),t.modules[e]||(t.payloads[e]=r,t.modules[e]=null)};t.modules={},t.payloads={};var n=function(e,t,n){if(typeof t==\"string\"){var i=s(e,t);if(i!=undefined)return n&&n(),i}else if(Object.prototype.toString.call(t)===\"[object Array]\"){var o=[];for(var u=0,a=t.length;u<a;++u){var f=s(e,t[u]);if(f==undefined&&r.original)return;o.push(f)}return n&&n.apply(null,o)||!0}},r=function(e,t){var i=n(\"\",e,t);return i==undefined&&r.original?r.original.apply(this,arguments):i},i=function(e,t){if(t.indexOf(\"!\")!==-1){var n=t.split(\"!\");return i(e,n[0])+\"!\"+i(e,n[1])}if(t.charAt(0)==\".\"){var r=e.split(\"/\").slice(0,-1).join(\"/\");t=r+\"/\"+t;while(t.indexOf(\".\")!==-1&&s!=t){var s=t;t=t.replace(/\\/\\.\\//,\"/\").replace(/[^\\/]+\\/\\.\\.\\//,\"\")}}return t},s=function(e,r){r=i(e,r);var s=t.modules[r];if(!s){s=t.payloads[r];if(typeof s==\"function\"){var o={},u={id:r,uri:\"\",exports:o,packaged:!0},a=function(e,t){return n(r,e,t)},f=s(a,o,u);o=f||u.exports,t.modules[r]=o,delete t.payloads[r]}s=t.modules[r]=o||s}return s};o(ACE_NAMESPACE)})(),define(\"ace/lib/regexp\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function o(e){return(e.global?\"g\":\"\")+(e.ignoreCase?\"i\":\"\")+(e.multiline?\"m\":\"\")+(e.extended?\"x\":\"\")+(e.sticky?\"y\":\"\")}function u(e,t,n){if(Array.prototype.indexOf)return e.indexOf(t,n);for(var r=n||0;r<e.length;r++)if(e[r]===t)return r;return-1}var r={exec:RegExp.prototype.exec,test:RegExp.prototype.test,match:String.prototype.match,replace:String.prototype.replace,split:String.prototype.split},i=r.exec.call(/()??/,\"\")[1]===undefined,s=function(){var e=/^/g;return r.test.call(e,\"\"),!e.lastIndex}();if(s&&i)return;RegExp.prototype.exec=function(e){var t=r.exec.apply(this,arguments),n,a;if(typeof e==\"string\"&&t){!i&&t.length>1&&u(t,\"\")>-1&&(a=RegExp(this.source,r.replace.call(o(this),\"g\",\"\")),r.replace.call(e.slice(t.index),a,function(){for(var e=1;e<arguments.length-2;e++)arguments[e]===undefined&&(t[e]=undefined)}));if(this._xregexp&&this._xregexp.captureNames)for(var f=1;f<t.length;f++)n=this._xregexp.captureNames[f-1],n&&(t[n]=t[f]);!s&&this.global&&!t[0].length&&this.lastIndex>t.index&&this.lastIndex--}return t},s||(RegExp.prototype.test=function(e){var t=r.exec.call(this,e);return t&&this.global&&!t[0].length&&this.lastIndex>t.index&&this.lastIndex--,!!t})}),define(\"ace/lib/es5-shim\",[\"require\",\"exports\",\"module\"],function(e,t,n){function r(){}function w(e){try{return Object.defineProperty(e,\"sentinel\",{}),\"sentinel\"in e}catch(t){}}function H(e){return e=+e,e!==e?e=0:e!==0&&e!==1/0&&e!==-1/0&&(e=(e>0||-1)*Math.floor(Math.abs(e))),e}function B(e){var t=typeof e;return e===null||t===\"undefined\"||t===\"boolean\"||t===\"number\"||t===\"string\"}function j(e){var t,n,r;if(B(e))return e;n=e.valueOf;if(typeof n==\"function\"){t=n.call(e);if(B(t))return t}r=e.toString;if(typeof r==\"function\"){t=r.call(e);if(B(t))return t}throw new TypeError}Function.prototype.bind||(Function.prototype.bind=function(t){var n=this;if(typeof n!=\"function\")throw new TypeError(\"Function.prototype.bind called on incompatible \"+n);var i=u.call(arguments,1),s=function(){if(this instanceof s){var e=n.apply(this,i.concat(u.call(arguments)));return Object(e)===e?e:this}return n.apply(t,i.concat(u.call(arguments)))};return n.prototype&&(r.prototype=n.prototype,s.prototype=new r,r.prototype=null),s});var i=Function.prototype.call,s=Array.prototype,o=Object.prototype,u=s.slice,a=i.bind(o.toString),f=i.bind(o.hasOwnProperty),l,c,h,p,d;if(d=f(o,\"__defineGetter__\"))l=i.bind(o.__defineGetter__),c=i.bind(o.__defineSetter__),h=i.bind(o.__lookupGetter__),p=i.bind(o.__lookupSetter__);if([1,2].splice(0).length!=2)if(!function(){function e(e){var t=new Array(e+2);return t[0]=t[1]=0,t}var t=[],n;t.splice.apply(t,e(20)),t.splice.apply(t,e(26)),n=t.length,t.splice(5,0,\"XXX\"),n+1==t.length;if(n+1==t.length)return!0}())Array.prototype.splice=function(e,t){var n=this.length;e>0?e>n&&(e=n):e==void 0?e=0:e<0&&(e=Math.max(n+e,0)),e+t<n||(t=n-e);var r=this.slice(e,e+t),i=u.call(arguments,2),s=i.length;if(e===n)s&&this.push.apply(this,i);else{var o=Math.min(t,n-e),a=e+o,f=a+s-o,l=n-a,c=n-o;if(f<a)for(var h=0;h<l;++h)this[f+h]=this[a+h];else if(f>a)for(h=l;h--;)this[f+h]=this[a+h];if(s&&e===c)this.length=c,this.push.apply(this,i);else{this.length=c+s;for(h=0;h<s;++h)this[e+h]=i[h]}}return r};else{var v=Array.prototype.splice;Array.prototype.splice=function(e,t){return arguments.length?v.apply(this,[e===void 0?0:e,t===void 0?this.length-e:t].concat(u.call(arguments,2))):[]}}Array.isArray||(Array.isArray=function(t){return a(t)==\"[object Array]\"});var m=Object(\"a\"),g=m[0]!=\"a\"||!(0 in m);Array.prototype.forEach||(Array.prototype.forEach=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=arguments[1],s=-1,o=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError;while(++s<o)s in r&&t.call(i,r[s],s,n)}),Array.prototype.map||(Array.prototype.map=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=Array(i),o=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var u=0;u<i;u++)u in r&&(s[u]=t.call(o,r[u],u,n));return s}),Array.prototype.filter||(Array.prototype.filter=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=[],o,u=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var f=0;f<i;f++)f in r&&(o=r[f],t.call(u,o,f,n)&&s.push(o));return s}),Array.prototype.every||(Array.prototype.every=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&!t.call(s,r[o],o,n))return!1;return!0}),Array.prototype.some||(Array.prototype.some=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&t.call(s,r[o],o,n))return!0;return!1}),Array.prototype.reduce||(Array.prototype.reduce=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduce of empty array with no initial value\");var s=0,o;if(arguments.length>=2)o=arguments[1];else do{if(s in r){o=r[s++];break}if(++s>=i)throw new TypeError(\"reduce of empty array with no initial value\")}while(!0);for(;s<i;s++)s in r&&(o=t.call(void 0,o,r[s],s,n));return o}),Array.prototype.reduceRight||(Array.prototype.reduceRight=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduceRight of empty array with no initial value\");var s,o=i-1;if(arguments.length>=2)s=arguments[1];else do{if(o in r){s=r[o--];break}if(--o<0)throw new TypeError(\"reduceRight of empty array with no initial value\")}while(!0);do o in this&&(s=t.call(void 0,s,r[o],o,n));while(o--);return s});if(!Array.prototype.indexOf||[0,1].indexOf(1,2)!=-1)Array.prototype.indexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=0;arguments.length>1&&(i=H(arguments[1])),i=i>=0?i:Math.max(0,r+i);for(;i<r;i++)if(i in n&&n[i]===t)return i;return-1};if(!Array.prototype.lastIndexOf||[0,1].lastIndexOf(0,-3)!=-1)Array.prototype.lastIndexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=r-1;arguments.length>1&&(i=Math.min(i,H(arguments[1]))),i=i>=0?i:r-Math.abs(i);for(;i>=0;i--)if(i in n&&t===n[i])return i;return-1};Object.getPrototypeOf||(Object.getPrototypeOf=function(t){return t.__proto__||(t.constructor?t.constructor.prototype:o)});if(!Object.getOwnPropertyDescriptor){var y=\"Object.getOwnPropertyDescriptor called on a non-object: \";Object.getOwnPropertyDescriptor=function(t,n){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(y+t);if(!f(t,n))return;var r,i,s;r={enumerable:!0,configurable:!0};if(d){var u=t.__proto__;t.__proto__=o;var i=h(t,n),s=p(t,n);t.__proto__=u;if(i||s)return i&&(r.get=i),s&&(r.set=s),r}return r.value=t[n],r}}Object.getOwnPropertyNames||(Object.getOwnPropertyNames=function(t){return Object.keys(t)});if(!Object.create){var b;Object.prototype.__proto__===null?b=function(){return{__proto__:null}}:b=function(){var e={};for(var t in e)e[t]=null;return e.constructor=e.hasOwnProperty=e.propertyIsEnumerable=e.isPrototypeOf=e.toLocaleString=e.toString=e.valueOf=e.__proto__=null,e},Object.create=function(t,n){var r;if(t===null)r=b();else{if(typeof t!=\"object\")throw new TypeError(\"typeof prototype[\"+typeof t+\"] != 'object'\");var i=function(){};i.prototype=t,r=new i,r.__proto__=t}return n!==void 0&&Object.defineProperties(r,n),r}}if(Object.defineProperty){var E=w({}),S=typeof document==\"undefined\"||w(document.createElement(\"div\"));if(!E||!S)var x=Object.defineProperty}if(!Object.defineProperty||x){var T=\"Property description must be an object: \",N=\"Object.defineProperty called on non-object: \",C=\"getters & setters can not be defined on this javascript engine\";Object.defineProperty=function(t,n,r){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(N+t);if(typeof r!=\"object\"&&typeof r!=\"function\"||r===null)throw new TypeError(T+r);if(x)try{return x.call(Object,t,n,r)}catch(i){}if(f(r,\"value\"))if(d&&(h(t,n)||p(t,n))){var s=t.__proto__;t.__proto__=o,delete t[n],t[n]=r.value,t.__proto__=s}else t[n]=r.value;else{if(!d)throw new TypeError(C);f(r,\"get\")&&l(t,n,r.get),f(r,\"set\")&&c(t,n,r.set)}return t}}Object.defineProperties||(Object.defineProperties=function(t,n){for(var r in n)f(n,r)&&Object.defineProperty(t,r,n[r]);return t}),Object.seal||(Object.seal=function(t){return t}),Object.freeze||(Object.freeze=function(t){return t});try{Object.freeze(function(){})}catch(k){Object.freeze=function(t){return function(n){return typeof n==\"function\"?n:t(n)}}(Object.freeze)}Object.preventExtensions||(Object.preventExtensions=function(t){return t}),Object.isSealed||(Object.isSealed=function(t){return!1}),Object.isFrozen||(Object.isFrozen=function(t){return!1}),Object.isExtensible||(Object.isExtensible=function(t){if(Object(t)===t)throw new TypeError;var n=\"\";while(f(t,n))n+=\"?\";t[n]=!0;var r=f(t,n);return delete t[n],r});if(!Object.keys){var L=!0,A=[\"toString\",\"toLocaleString\",\"valueOf\",\"hasOwnProperty\",\"isPrototypeOf\",\"propertyIsEnumerable\",\"constructor\"],O=A.length;for(var M in{toString:null})L=!1;Object.keys=function I(e){if(typeof e!=\"object\"&&typeof e!=\"function\"||e===null)throw new TypeError(\"Object.keys called on a non-object\");var I=[];for(var t in e)f(e,t)&&I.push(t);if(L)for(var n=0,r=O;n<r;n++){var i=A[n];f(e,i)&&I.push(i)}return I}}Date.now||(Date.now=function(){return(new Date).getTime()});var _=\"\t\\n\u000b\\f\\r \\u00a0\\u1680\\u180e\\u2000\\u2001\\u2002\\u2003\\u2004\\u2005\\u2006\\u2007\\u2008\\u2009\\u200a\\u202f\\u205f\\u3000\\u2028\\u2029\\ufeff\";if(!String.prototype.trim||_.trim()){_=\"[\"+_+\"]\";var D=new RegExp(\"^\"+_+_+\"*\"),P=new RegExp(_+_+\"*$\");String.prototype.trim=function(){return String(this).replace(D,\"\").replace(P,\"\")}}var F=function(e){if(e==null)throw new TypeError(\"can't convert \"+e+\" to object\");return Object(e)}}),define(\"ace/lib/fixoldbrowsers\",[\"require\",\"exports\",\"module\",\"ace/lib/regexp\",\"ace/lib/es5-shim\"],function(e,t,n){\"use strict\";e(\"./regexp\"),e(\"./es5-shim\")}),define(\"ace/lib/dom\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=\"http://www.w3.org/1999/xhtml\";t.getDocumentHead=function(e){return e||(e=document),e.head||e.getElementsByTagName(\"head\")[0]||e.documentElement},t.createElement=function(e,t){return document.createElementNS?document.createElementNS(t||r,e):document.createElement(e)},t.hasCssClass=function(e,t){var n=(e.className+\"\").split(/\\s+/g);return n.indexOf(t)!==-1},t.addCssClass=function(e,n){t.hasCssClass(e,n)||(e.className+=\" \"+n)},t.removeCssClass=function(e,t){var n=e.className.split(/\\s+/g);for(;;){var r=n.indexOf(t);if(r==-1)break;n.splice(r,1)}e.className=n.join(\" \")},t.toggleCssClass=function(e,t){var n=e.className.split(/\\s+/g),r=!0;for(;;){var i=n.indexOf(t);if(i==-1)break;r=!1,n.splice(i,1)}return r&&n.push(t),e.className=n.join(\" \"),r},t.setCssClass=function(e,n,r){r?t.addCssClass(e,n):t.removeCssClass(e,n)},t.hasCssString=function(e,t){var n=0,r;t=t||document;if(t.createStyleSheet&&(r=t.styleSheets)){while(n<r.length)if(r[n++].owningElement.id===e)return!0}else if(r=t.getElementsByTagName(\"style\"))while(n<r.length)if(r[n++].id===e)return!0;return!1},t.importCssString=function(n,r,i){i=i||document;if(r&&t.hasCssString(r,i))return null;var s;r&&(n+=\"\\n/*# sourceURL=ace/css/\"+r+\" */\"),i.createStyleSheet?(s=i.createStyleSheet(),s.cssText=n,r&&(s.owningElement.id=r)):(s=t.createElement(\"style\"),s.appendChild(i.createTextNode(n)),r&&(s.id=r),t.getDocumentHead(i).appendChild(s))},t.importCssStylsheet=function(e,n){if(n.createStyleSheet)n.createStyleSheet(e);else{var r=t.createElement(\"link\");r.rel=\"stylesheet\",r.href=e,t.getDocumentHead(n).appendChild(r)}},t.getInnerWidth=function(e){return parseInt(t.computedStyle(e,\"paddingLeft\"),10)+parseInt(t.computedStyle(e,\"paddingRight\"),10)+e.clientWidth},t.getInnerHeight=function(e){return parseInt(t.computedStyle(e,\"paddingTop\"),10)+parseInt(t.computedStyle(e,\"paddingBottom\"),10)+e.clientHeight},t.scrollbarWidth=function(e){var n=t.createElement(\"ace_inner\");n.style.width=\"100%\",n.style.minWidth=\"0px\",n.style.height=\"200px\",n.style.display=\"block\";var r=t.createElement(\"ace_outer\"),i=r.style;i.position=\"absolute\",i.left=\"-10000px\",i.overflow=\"hidden\",i.width=\"200px\",i.minWidth=\"0px\",i.height=\"150px\",i.display=\"block\",r.appendChild(n);var s=e.documentElement;s.appendChild(r);var o=n.offsetWidth;i.overflow=\"scroll\";var u=n.offsetWidth;return o==u&&(u=r.clientWidth),s.removeChild(r),o-u};if(typeof document==\"undefined\"){t.importCssString=function(){};return}window.pageYOffset!==undefined?(t.getPageScrollTop=function(){return window.pageYOffset},t.getPageScrollLeft=function(){return window.pageXOffset}):(t.getPageScrollTop=function(){return document.body.scrollTop},t.getPageScrollLeft=function(){return document.body.scrollLeft}),window.getComputedStyle?t.computedStyle=function(e,t){return t?(window.getComputedStyle(e,\"\")||{})[t]||\"\":window.getComputedStyle(e,\"\")||{}}:t.computedStyle=function(e,t){return t?e.currentStyle[t]:e.currentStyle},t.setInnerHtml=function(e,t){var n=e.cloneNode(!1);return n.innerHTML=t,e.parentNode.replaceChild(n,e),n},\"textContent\"in document.documentElement?(t.setInnerText=function(e,t){e.textContent=t},t.getInnerText=function(e){return e.textContent}):(t.setInnerText=function(e,t){e.innerText=t},t.getInnerText=function(e){return e.innerText}),t.getParentWindow=function(e){return e.defaultView||e.parentWindow}}),define(\"ace/lib/oop\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.inherits=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})},t.mixin=function(e,t){for(var n in t)e[n]=t[n];return e},t.implement=function(e,n){t.mixin(e,n)}}),define(\"ace/lib/keys\",[\"require\",\"exports\",\"module\",\"ace/lib/fixoldbrowsers\",\"ace/lib/oop\"],function(e,t,n){\"use strict\";e(\"./fixoldbrowsers\");var r=e(\"./oop\"),i=function(){var e={MODIFIER_KEYS:{16:\"Shift\",17:\"Ctrl\",18:\"Alt\",224:\"Meta\"},KEY_MODS:{ctrl:1,alt:2,option:2,shift:4,\"super\":8,meta:8,command:8,cmd:8},FUNCTION_KEYS:{8:\"Backspace\",9:\"Tab\",13:\"Return\",19:\"Pause\",27:\"Esc\",32:\"Space\",33:\"PageUp\",34:\"PageDown\",35:\"End\",36:\"Home\",37:\"Left\",38:\"Up\",39:\"Right\",40:\"Down\",44:\"Print\",45:\"Insert\",46:\"Delete\",96:\"Numpad0\",97:\"Numpad1\",98:\"Numpad2\",99:\"Numpad3\",100:\"Numpad4\",101:\"Numpad5\",102:\"Numpad6\",103:\"Numpad7\",104:\"Numpad8\",105:\"Numpad9\",\"-13\":\"NumpadEnter\",112:\"F1\",113:\"F2\",114:\"F3\",115:\"F4\",116:\"F5\",117:\"F6\",118:\"F7\",119:\"F8\",120:\"F9\",121:\"F10\",122:\"F11\",123:\"F12\",144:\"Numlock\",145:\"Scrolllock\"},PRINTABLE_KEYS:{32:\" \",48:\"0\",49:\"1\",50:\"2\",51:\"3\",52:\"4\",53:\"5\",54:\"6\",55:\"7\",56:\"8\",57:\"9\",59:\";\",61:\"=\",65:\"a\",66:\"b\",67:\"c\",68:\"d\",69:\"e\",70:\"f\",71:\"g\",72:\"h\",73:\"i\",74:\"j\",75:\"k\",76:\"l\",77:\"m\",78:\"n\",79:\"o\",80:\"p\",81:\"q\",82:\"r\",83:\"s\",84:\"t\",85:\"u\",86:\"v\",87:\"w\",88:\"x\",89:\"y\",90:\"z\",107:\"+\",109:\"-\",110:\".\",186:\";\",187:\"=\",188:\",\",189:\"-\",190:\".\",191:\"/\",192:\"`\",219:\"[\",220:\"\\\\\",221:\"]\",222:\"'\",111:\"/\",106:\"*\"}},t,n;for(n in e.FUNCTION_KEYS)t=e.FUNCTION_KEYS[n].toLowerCase(),e[t]=parseInt(n,10);for(n in e.PRINTABLE_KEYS)t=e.PRINTABLE_KEYS[n].toLowerCase(),e[t]=parseInt(n,10);return r.mixin(e,e.MODIFIER_KEYS),r.mixin(e,e.PRINTABLE_KEYS),r.mixin(e,e.FUNCTION_KEYS),e.enter=e[\"return\"],e.escape=e.esc,e.del=e[\"delete\"],e[173]=\"-\",function(){var t=[\"cmd\",\"ctrl\",\"alt\",\"shift\"];for(var n=Math.pow(2,t.length);n--;)e.KEY_MODS[n]=t.filter(function(t){return n&e.KEY_MODS[t]}).join(\"-\")+\"-\"}(),e.KEY_MODS[0]=\"\",e.KEY_MODS[-1]=\"input-\",e}();r.mixin(t,i),t.keyCodeToString=function(e){var t=i[e];return typeof t!=\"string\"&&(t=String.fromCharCode(e)),t.toLowerCase()}}),define(\"ace/lib/useragent\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.OS={LINUX:\"LINUX\",MAC:\"MAC\",WINDOWS:\"WINDOWS\"},t.getOS=function(){return t.isMac?t.OS.MAC:t.isLinux?t.OS.LINUX:t.OS.WINDOWS};if(typeof navigator!=\"object\")return;var r=(navigator.platform.match(/mac|win|linux/i)||[\"other\"])[0].toLowerCase(),i=navigator.userAgent;t.isWin=r==\"win\",t.isMac=r==\"mac\",t.isLinux=r==\"linux\",t.isIE=navigator.appName==\"Microsoft Internet Explorer\"||navigator.appName.indexOf(\"MSAppHost\")>=0?parseFloat((i.match(/(?:MSIE |Trident\\/[0-9]+[\\.0-9]+;.*rv:)([0-9]+[\\.0-9]+)/)||[])[1]):parseFloat((i.match(/(?:Trident\\/[0-9]+[\\.0-9]+;.*rv:)([0-9]+[\\.0-9]+)/)||[])[1]),t.isOldIE=t.isIE&&t.isIE<9,t.isGecko=t.isMozilla=(window.Controllers||window.controllers)&&window.navigator.product===\"Gecko\",t.isOldGecko=t.isGecko&&parseInt((i.match(/rv:(\\d+)/)||[])[1],10)<4,t.isOpera=window.opera&&Object.prototype.toString.call(window.opera)==\"[object Opera]\",t.isWebKit=parseFloat(i.split(\"WebKit/\")[1])||undefined,t.isChrome=parseFloat(i.split(\" Chrome/\")[1])||undefined,t.isAIR=i.indexOf(\"AdobeAIR\")>=0,t.isIPad=i.indexOf(\"iPad\")>=0,t.isTouchPad=i.indexOf(\"TouchPad\")>=0,t.isChromeOS=i.indexOf(\" CrOS \")>=0}),define(\"ace/lib/event\",[\"require\",\"exports\",\"module\",\"ace/lib/keys\",\"ace/lib/useragent\"],function(e,t,n){\"use strict\";function a(e,t,n){var a=u(t);if(!i.isMac&&s){t.getModifierState&&(t.getModifierState(\"OS\")||t.getModifierState(\"Win\"))&&(a|=8);if(s.altGr){if((3&a)==3)return;s.altGr=0}if(n===18||n===17){var f=\"location\"in t?t.location:t.keyLocation;if(n===17&&f===1)s[n]==1&&(o=t.timeStamp);else if(n===18&&a===3&&f===2){var l=t.timeStamp-o;l<50&&(s.altGr=!0)}}}n in r.MODIFIER_KEYS&&(n=-1),a&8&&n>=91&&n<=93&&(n=-1);if(!a&&n===13){var f=\"location\"in t?t.location:t.keyLocation;if(f===3){e(t,a,-n);if(t.defaultPrevented)return}}if(i.isChromeOS&&a&8){e(t,a,n);if(t.defaultPrevented)return;a&=-9}return!!a||n in r.FUNCTION_KEYS||n in r.PRINTABLE_KEYS?e(t,a,n):!1}function f(){s=Object.create(null)}var r=e(\"./keys\"),i=e(\"./useragent\"),s=null,o=0;t.addListener=function(e,t,n){if(e.addEventListener)return e.addEventListener(t,n,!1);if(e.attachEvent){var r=function(){n.call(e,window.event)};n._wrapper=r,e.attachEvent(\"on\"+t,r)}},t.removeListener=function(e,t,n){if(e.removeEventListener)return e.removeEventListener(t,n,!1);e.detachEvent&&e.detachEvent(\"on\"+t,n._wrapper||n)},t.stopEvent=function(e){return t.stopPropagation(e),t.preventDefault(e),!1},t.stopPropagation=function(e){e.stopPropagation?e.stopPropagation():e.cancelBubble=!0},t.preventDefault=function(e){e.preventDefault?e.preventDefault():e.returnValue=!1},t.getButton=function(e){return e.type==\"dblclick\"?0:e.type==\"contextmenu\"||i.isMac&&e.ctrlKey&&!e.altKey&&!e.shiftKey?2:e.preventDefault?e.button:{1:0,2:2,4:1}[e.button]},t.capture=function(e,n,r){function i(e){n&&n(e),r&&r(e),t.removeListener(document,\"mousemove\",n,!0),t.removeListener(document,\"mouseup\",i,!0),t.removeListener(document,\"dragstart\",i,!0)}return t.addListener(document,\"mousemove\",n,!0),t.addListener(document,\"mouseup\",i,!0),t.addListener(document,\"dragstart\",i,!0),i},t.addTouchMoveListener=function(e,n){if(\"ontouchmove\"in e){var r,i;t.addListener(e,\"touchstart\",function(e){var t=e.changedTouches[0];r=t.clientX,i=t.clientY}),t.addListener(e,\"touchmove\",function(e){var t=1,s=e.changedTouches[0];e.wheelX=-(s.clientX-r)/t,e.wheelY=-(s.clientY-i)/t,r=s.clientX,i=s.clientY,n(e)})}},t.addMouseWheelListener=function(e,n){\"onmousewheel\"in e?t.addListener(e,\"mousewheel\",function(e){var t=8;e.wheelDeltaX!==undefined?(e.wheelX=-e.wheelDeltaX/t,e.wheelY=-e.wheelDeltaY/t):(e.wheelX=0,e.wheelY=-e.wheelDelta/t),n(e)}):\"onwheel\"in e?t.addListener(e,\"wheel\",function(e){var t=.35;switch(e.deltaMode){case e.DOM_DELTA_PIXEL:e.wheelX=e.deltaX*t||0,e.wheelY=e.deltaY*t||0;break;case e.DOM_DELTA_LINE:case e.DOM_DELTA_PAGE:e.wheelX=(e.deltaX||0)*5,e.wheelY=(e.deltaY||0)*5}n(e)}):t.addListener(e,\"DOMMouseScroll\",function(e){e.axis&&e.axis==e.HORIZONTAL_AXIS?(e.wheelX=(e.detail||0)*5,e.wheelY=0):(e.wheelX=0,e.wheelY=(e.detail||0)*5),n(e)})},t.addMultiMouseDownListener=function(e,n,r,s){function c(e){t.getButton(e)!==0?o=0:e.detail>1?(o++,o>4&&(o=1)):o=1;if(i.isIE){var c=Math.abs(e.clientX-u)>5||Math.abs(e.clientY-a)>5;if(!f||c)o=1;f&&clearTimeout(f),f=setTimeout(function(){f=null},n[o-1]||600),o==1&&(u=e.clientX,a=e.clientY)}e._clicks=o,r[s](\"mousedown\",e);if(o>4)o=0;else if(o>1)return r[s](l[o],e)}function h(e){o=2,f&&clearTimeout(f),f=setTimeout(function(){f=null},n[o-1]||600),r[s](\"mousedown\",e),r[s](l[o],e)}var o=0,u,a,f,l={2:\"dblclick\",3:\"tripleclick\",4:\"quadclick\"};Array.isArray(e)||(e=[e]),e.forEach(function(e){t.addListener(e,\"mousedown\",c),i.isOldIE&&t.addListener(e,\"dblclick\",h)})};var u=!i.isMac||!i.isOpera||\"KeyboardEvent\"in window?function(e){return 0|(e.ctrlKey?1:0)|(e.altKey?2:0)|(e.shiftKey?4:0)|(e.metaKey?8:0)}:function(e){return 0|(e.metaKey?1:0)|(e.altKey?2:0)|(e.shiftKey?4:0)|(e.ctrlKey?8:0)};t.getModifierString=function(e){return r.KEY_MODS[u(e)]},t.addCommandKeyListener=function(e,n){var r=t.addListener;if(i.isOldGecko||i.isOpera&&!(\"KeyboardEvent\"in window)){var o=null;r(e,\"keydown\",function(e){o=e.keyCode}),r(e,\"keypress\",function(e){return a(n,e,o)})}else{var u=null;r(e,\"keydown\",function(e){s[e.keyCode]=(s[e.keyCode]||0)+1;var t=a(n,e,e.keyCode);return u=e.defaultPrevented,t}),r(e,\"keypress\",function(e){u&&(e.ctrlKey||e.altKey||e.shiftKey||e.metaKey)&&(t.stopEvent(e),u=null)}),r(e,\"keyup\",function(e){s[e.keyCode]=null}),s||(f(),r(window,\"focus\",f))}};if(typeof window==\"object\"&&window.postMessage&&!i.isOldIE){var l=1;t.nextTick=function(e,n){n=n||window;var r=\"zero-timeout-message-\"+l;t.addListener(n,\"message\",function i(s){s.data==r&&(t.stopPropagation(s),t.removeListener(n,\"message\",i),e())}),n.postMessage(r,\"*\")}}t.nextFrame=typeof window==\"object\"&&(window.requestAnimationFrame||window.mozRequestAnimationFrame||window.webkitRequestAnimationFrame||window.msRequestAnimationFrame||window.oRequestAnimationFrame),t.nextFrame?t.nextFrame=t.nextFrame.bind(window):t.nextFrame=function(e){setTimeout(e,17)}}),define(\"ace/lib/lang\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.last=function(e){return e[e.length-1]},t.stringReverse=function(e){return e.split(\"\").reverse().join(\"\")},t.stringRepeat=function(e,t){var n=\"\";while(t>0){t&1&&(n+=e);if(t>>=1)e+=e}return n};var r=/^\\s\\s*/,i=/\\s\\s*$/;t.stringTrimLeft=function(e){return e.replace(r,\"\")},t.stringTrimRight=function(e){return e.replace(i,\"\")},t.copyObject=function(e){var t={};for(var n in e)t[n]=e[n];return t},t.copyArray=function(e){var t=[];for(var n=0,r=e.length;n<r;n++)e[n]&&typeof e[n]==\"object\"?t[n]=this.copyObject(e[n]):t[n]=e[n];return t},t.deepCopy=function s(e){if(typeof e!=\"object\"||!e)return e;var t;if(Array.isArray(e)){t=[];for(var n=0;n<e.length;n++)t[n]=s(e[n]);return t}if(Object.prototype.toString.call(e)!==\"[object Object]\")return e;t={};for(var n in e)t[n]=s(e[n]);return t},t.arrayToMap=function(e){var t={};for(var n=0;n<e.length;n++)t[e[n]]=1;return t},t.createMap=function(e){var t=Object.create(null);for(var n in e)t[n]=e[n];return t},t.arrayRemove=function(e,t){for(var n=0;n<=e.length;n++)t===e[n]&&e.splice(n,1)},t.escapeRegExp=function(e){return e.replace(/([.*+?^${}()|[\\]\\/\\\\])/g,\"\\\\$1\")},t.escapeHTML=function(e){return e.replace(/&/g,\"&#38;\").replace(/\"/g,\"&#34;\").replace(/'/g,\"&#39;\").replace(/</g,\"&#60;\")},t.getMatchOffsets=function(e,t){var n=[];return e.replace(t,function(e){n.push({offset:arguments[arguments.length-2],length:e.length})}),n},t.deferredCall=function(e){var t=null,n=function(){t=null,e()},r=function(e){return r.cancel(),t=setTimeout(n,e||0),r};return r.schedule=r,r.call=function(){return this.cancel(),e(),r},r.cancel=function(){return clearTimeout(t),t=null,r},r.isPending=function(){return t},r},t.delayedCall=function(e,t){var n=null,r=function(){n=null,e()},i=function(e){n==null&&(n=setTimeout(r,e||t))};return i.delay=function(e){n&&clearTimeout(n),n=setTimeout(r,e||t)},i.schedule=i,i.call=function(){this.cancel(),e()},i.cancel=function(){n&&clearTimeout(n),n=null},i.isPending=function(){return n},i}}),define(\"ace/keyboard/textinput\",[\"require\",\"exports\",\"module\",\"ace/lib/event\",\"ace/lib/useragent\",\"ace/lib/dom\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../lib/event\"),i=e(\"../lib/useragent\"),s=e(\"../lib/dom\"),o=e(\"../lib/lang\"),u=i.isChrome<18,a=i.isIE,f=function(e,t){function b(e){if(h)return;h=!0;if(k)t=0,r=e?0:n.value.length-1;else var t=e?2:1,r=2;try{n.setSelectionRange(t,r)}catch(i){}h=!1}function w(){if(h)return;n.value=f,i.isWebKit&&y.schedule()}function R(){clearTimeout(q),q=setTimeout(function(){p&&(n.style.cssText=p,p=\"\"),t.renderer.$keepTextAreaAtCursor==null&&(t.renderer.$keepTextAreaAtCursor=!0,t.renderer.$moveTextAreaToCursor())},i.isOldIE?200:0)}var n=s.createElement(\"textarea\");n.className=\"ace_text-input\",i.isTouchPad&&n.setAttribute(\"x-palm-disable-auto-cap\",!0),n.setAttribute(\"wrap\",\"off\"),n.setAttribute(\"autocorrect\",\"off\"),n.setAttribute(\"autocapitalize\",\"off\"),n.setAttribute(\"spellcheck\",!1),n.style.opacity=\"0\",i.isOldIE&&(n.style.top=\"-1000px\"),e.insertBefore(n,e.firstChild);var f=\"\u0001\u0001\",l=!1,c=!1,h=!1,p=\"\",d=!0;try{var v=document.activeElement===n}catch(m){}r.addListener(n,\"blur\",function(e){t.onBlur(e),v=!1}),r.addListener(n,\"focus\",function(e){v=!0,t.onFocus(e),b()}),this.focus=function(){if(p)return n.focus();var e=n.style.top;n.style.position=\"fixed\",n.style.top=\"0px\",n.focus(),setTimeout(function(){n.style.position=\"\",n.style.top==\"0px\"&&(n.style.top=e)},0)},this.blur=function(){n.blur()},this.isFocused=function(){return v};var g=o.delayedCall(function(){v&&b(d)}),y=o.delayedCall(function(){h||(n.value=f,v&&b())});i.isWebKit||t.addEventListener(\"changeSelection\",function(){t.selection.isEmpty()!=d&&(d=!d,g.schedule())}),w(),v&&t.onFocus();var E=function(e){return e.selectionStart===0&&e.selectionEnd===e.value.length};!n.setSelectionRange&&n.createTextRange&&(n.setSelectionRange=function(e,t){var n=this.createTextRange();n.collapse(!0),n.moveStart(\"character\",e),n.moveEnd(\"character\",t),n.select()},E=function(e){try{var t=e.ownerDocument.selection.createRange()}catch(n){}return!t||t.parentElement()!=e?!1:t.text==e.value});if(i.isOldIE){var S=!1,x=function(e){if(S)return;var t=n.value;if(h||!t||t==f)return;if(e&&t==f[0])return T.schedule();A(t),S=!0,w(),S=!1},T=o.delayedCall(x);r.addListener(n,\"propertychange\",x);var N={13:1,27:1};r.addListener(n,\"keyup\",function(e){h&&(!n.value||N[e.keyCode])&&setTimeout(F,0);if((n.value.charCodeAt(0)||0)<129)return T.call();h?j():B()}),r.addListener(n,\"keydown\",function(e){T.schedule(50)})}var C=function(e){l?l=!1:E(n)?(t.selectAll(),b()):k&&b(t.selection.isEmpty())},k=null;this.setInputHandler=function(e){k=e},this.getInputHandler=function(){return k};var L=!1,A=function(e){k&&(e=k(e),k=null),c?(b(),e&&t.onPaste(e),c=!1):e==f.charAt(0)?L?t.execCommand(\"del\",{source:\"ace\"}):t.execCommand(\"backspace\",{source:\"ace\"}):(e.substring(0,2)==f?e=e.substr(2):e.charAt(0)==f.charAt(0)?e=e.substr(1):e.charAt(e.length-1)==f.charAt(0)&&(e=e.slice(0,-1)),e.charAt(e.length-1)==f.charAt(0)&&(e=e.slice(0,-1)),e&&t.onTextInput(e)),L&&(L=!1)},O=function(e){if(h)return;var t=n.value;A(t),w()},M=function(e,t,n){var r=e.clipboardData||window.clipboardData;if(!r||u)return;var i=a||n?\"Text\":\"text/plain\";try{return t?r.setData(i,t)!==!1:r.getData(i)}catch(e){if(!n)return M(e,t,!0)}},_=function(e,i){var s=t.getCopyText();if(!s)return r.preventDefault(e);M(e,s)?(i?t.onCut():t.onCopy(),r.preventDefault(e)):(l=!0,n.value=s,n.select(),setTimeout(function(){l=!1,w(),b(),i?t.onCut():t.onCopy()}))},D=function(e){_(e,!0)},P=function(e){_(e,!1)},H=function(e){var s=M(e);typeof s==\"string\"?(s&&t.onPaste(s,e),i.isIE&&setTimeout(b),r.preventDefault(e)):(n.value=\"\",c=!0)};r.addCommandKeyListener(n,t.onCommandKey.bind(t)),r.addListener(n,\"select\",C),r.addListener(n,\"input\",O),r.addListener(n,\"cut\",D),r.addListener(n,\"copy\",P),r.addListener(n,\"paste\",H),(!(\"oncut\"in n)||!(\"oncopy\"in n)||!(\"onpaste\"in n))&&r.addListener(e,\"keydown\",function(e){if(i.isMac&&!e.metaKey||!e.ctrlKey)return;switch(e.keyCode){case 67:P(e);break;case 86:H(e);break;case 88:D(e)}});var B=function(e){if(h||!t.onCompositionStart||t.$readOnly)return;h={},h.canUndo=t.session.$undoManager,t.onCompositionStart(),setTimeout(j,0),t.on(\"mousedown\",F),h.canUndo&&!t.selection.isEmpty()&&(t.insert(\"\"),t.session.markUndoGroup(),t.selection.clearSelection()),t.session.markUndoGroup()},j=function(){if(!h||!t.onCompositionUpdate||t.$readOnly)return;var e=n.value.replace(/\\x01/g,\"\");if(h.lastValue===e)return;t.onCompositionUpdate(e),h.lastValue&&t.undo(),h.canUndo&&(h.lastValue=e);if(h.lastValue){var r=t.selection.getRange();t.insert(h.lastValue),t.session.markUndoGroup(),h.range=t.selection.getRange(),t.selection.setRange(r),t.selection.clearSelection()}},F=function(e){if(!t.onCompositionEnd||t.$readOnly)return;var r=h;h=!1;var s=setTimeout(function(){s=null;var e=n.value.replace(/\\x01/g,\"\");if(h)return;e==r.lastValue?w():!r.lastValue&&e&&(w(),A(e))});k=function(n){return s&&clearTimeout(s),n=n.replace(/\\x01/g,\"\"),n==r.lastValue?\"\":(r.lastValue&&s&&t.undo(),n)},t.onCompositionEnd(),t.removeListener(\"mousedown\",F),e.type==\"compositionend\"&&r.range&&t.selection.setRange(r.range),i.isChrome&&i.isChrome>=53&&O()},I=o.delayedCall(j,50);r.addListener(n,\"compositionstart\",B),i.isGecko?r.addListener(n,\"text\",function(){I.schedule()}):(r.addListener(n,\"keyup\",function(){I.schedule()}),r.addListener(n,\"keydown\",function(){I.schedule()})),r.addListener(n,\"compositionend\",F),this.getElement=function(){return n},this.setReadOnly=function(e){n.readOnly=e},this.onContextMenu=function(e){L=!0,b(t.selection.isEmpty()),t._emit(\"nativecontextmenu\",{target:t,domEvent:e}),this.moveToMouse(e,!0)},this.moveToMouse=function(e,o){if(!o&&i.isOldIE)return;p||(p=n.style.cssText),n.style.cssText=(o?\"z-index:100000;\":\"\")+\"height:\"+n.style.height+\";\"+(i.isIE?\"opacity:0.1;\":\"\");var u=t.container.getBoundingClientRect(),a=s.computedStyle(t.container),f=u.top+(parseInt(a.borderTopWidth)||0),l=u.left+(parseInt(u.borderLeftWidth)||0),c=u.bottom-f-n.clientHeight-2,h=function(e){n.style.left=e.clientX-l-2+\"px\",n.style.top=Math.min(e.clientY-f-2,c)+\"px\"};h(e);if(e.type!=\"mousedown\")return;t.renderer.$keepTextAreaAtCursor&&(t.renderer.$keepTextAreaAtCursor=null),clearTimeout(q),i.isWin&&!i.isOldIE&&r.capture(t.container,h,R)},this.onContextMenuClose=R;var q,U=function(e){t.textInput.onContextMenu(e),R()};r.addListener(n,\"mouseup\",U),r.addListener(n,\"mousedown\",function(e){e.preventDefault(),R()}),r.addListener(t.renderer.scroller,\"contextmenu\",U),r.addListener(n,\"contextmenu\",U)};t.TextInput=f}),define(\"ace/mouse/default_handlers\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\",\"ace/lib/event\",\"ace/lib/useragent\"],function(e,t,n){\"use strict\";function u(e){e.$clickSelection=null;var t=e.editor;t.setDefaultHandler(\"mousedown\",this.onMouseDown.bind(e)),t.setDefaultHandler(\"dblclick\",this.onDoubleClick.bind(e)),t.setDefaultHandler(\"tripleclick\",this.onTripleClick.bind(e)),t.setDefaultHandler(\"quadclick\",this.onQuadClick.bind(e)),t.setDefaultHandler(\"mousewheel\",this.onMouseWheel.bind(e)),t.setDefaultHandler(\"touchmove\",this.onTouchMove.bind(e));var n=[\"select\",\"startSelect\",\"selectEnd\",\"selectAllEnd\",\"selectByWordsEnd\",\"selectByLinesEnd\",\"dragWait\",\"dragWaitEnd\",\"focusWait\"];n.forEach(function(t){e[t]=this[t]},this),e.selectByLines=this.extendSelectionBy.bind(e,\"getLineRange\"),e.selectByWords=this.extendSelectionBy.bind(e,\"getWordRange\")}function a(e,t,n,r){return Math.sqrt(Math.pow(n-e,2)+Math.pow(r-t,2))}function f(e,t){if(e.start.row==e.end.row)var n=2*t.column-e.start.column-e.end.column;else if(e.start.row==e.end.row-1&&!e.start.column&&!e.end.column)var n=t.column-4;else var n=2*t.row-e.start.row-e.end.row;return n<0?{cursor:e.start,anchor:e.end}:{cursor:e.end,anchor:e.start}}var r=e(\"../lib/dom\"),i=e(\"../lib/event\"),s=e(\"../lib/useragent\"),o=0;(function(){this.onMouseDown=function(e){var t=e.inSelection(),n=e.getDocumentPosition();this.mousedownEvent=e;var r=this.editor,i=e.getButton();if(i!==0){var s=r.getSelectionRange(),o=s.isEmpty();r.$blockScrolling++,(o||i==1)&&r.selection.moveToPosition(n),r.$blockScrolling--,i==2&&r.textInput.onContextMenu(e.domEvent);return}this.mousedownEvent.time=Date.now();if(t&&!r.isFocused()){r.focus();if(this.$focusTimout&&!this.$clickSelection&&!r.inMultiSelectMode){this.setState(\"focusWait\"),this.captureMouse(e);return}}return this.captureMouse(e),this.startSelect(n,e.domEvent._clicks>1),e.preventDefault()},this.startSelect=function(e,t){e=e||this.editor.renderer.screenToTextCoordinates(this.x,this.y);var n=this.editor;n.$blockScrolling++,this.mousedownEvent.getShiftKey()?n.selection.selectToPosition(e):t||n.selection.moveToPosition(e),t||this.select(),n.renderer.scroller.setCapture&&n.renderer.scroller.setCapture(),n.setStyle(\"ace_selecting\"),this.setState(\"select\"),n.$blockScrolling--},this.select=function(){var e,t=this.editor,n=t.renderer.screenToTextCoordinates(this.x,this.y);t.$blockScrolling++;if(this.$clickSelection){var r=this.$clickSelection.comparePoint(n);if(r==-1)e=this.$clickSelection.end;else if(r==1)e=this.$clickSelection.start;else{var i=f(this.$clickSelection,n);n=i.cursor,e=i.anchor}t.selection.setSelectionAnchor(e.row,e.column)}t.selection.selectToPosition(n),t.$blockScrolling--,t.renderer.scrollCursorIntoView()},this.extendSelectionBy=function(e){var t,n=this.editor,r=n.renderer.screenToTextCoordinates(this.x,this.y),i=n.selection[e](r.row,r.column);n.$blockScrolling++;if(this.$clickSelection){var s=this.$clickSelection.comparePoint(i.start),o=this.$clickSelection.comparePoint(i.end);if(s==-1&&o<=0){t=this.$clickSelection.end;if(i.end.row!=r.row||i.end.column!=r.column)r=i.start}else if(o==1&&s>=0){t=this.$clickSelection.start;if(i.start.row!=r.row||i.start.column!=r.column)r=i.end}else if(s==-1&&o==1)r=i.end,t=i.start;else{var u=f(this.$clickSelection,r);r=u.cursor,t=u.anchor}n.selection.setSelectionAnchor(t.row,t.column)}n.selection.selectToPosition(r),n.$blockScrolling--,n.renderer.scrollCursorIntoView()},this.selectEnd=this.selectAllEnd=this.selectByWordsEnd=this.selectByLinesEnd=function(){this.$clickSelection=null,this.editor.unsetStyle(\"ace_selecting\"),this.editor.renderer.scroller.releaseCapture&&this.editor.renderer.scroller.releaseCapture()},this.focusWait=function(){var e=a(this.mousedownEvent.x,this.mousedownEvent.y,this.x,this.y),t=Date.now();(e>o||t-this.mousedownEvent.time>this.$focusTimout)&&this.startSelect(this.mousedownEvent.getDocumentPosition())},this.onDoubleClick=function(e){var t=e.getDocumentPosition(),n=this.editor,r=n.session,i=r.getBracketRange(t);i?(i.isEmpty()&&(i.start.column--,i.end.column++),this.setState(\"select\")):(i=n.selection.getWordRange(t.row,t.column),this.setState(\"selectByWords\")),this.$clickSelection=i,this.select()},this.onTripleClick=function(e){var t=e.getDocumentPosition(),n=this.editor;this.setState(\"selectByLines\");var r=n.getSelectionRange();r.isMultiLine()&&r.contains(t.row,t.column)?(this.$clickSelection=n.selection.getLineRange(r.start.row),this.$clickSelection.end=n.selection.getLineRange(r.end.row).end):this.$clickSelection=n.selection.getLineRange(t.row),this.select()},this.onQuadClick=function(e){var t=this.editor;t.selectAll(),this.$clickSelection=t.getSelectionRange(),this.setState(\"selectAll\")},this.onMouseWheel=function(e){if(e.getAccelKey())return;e.getShiftKey()&&e.wheelY&&!e.wheelX&&(e.wheelX=e.wheelY,e.wheelY=0);var t=e.domEvent.timeStamp,n=t-(this.$lastScrollTime||0),r=this.editor,i=r.renderer.isScrollableBy(e.wheelX*e.speed,e.wheelY*e.speed);if(i||n<200)return this.$lastScrollTime=t,r.renderer.scrollBy(e.wheelX*e.speed,e.wheelY*e.speed),e.stop()},this.onTouchMove=function(e){var t=e.domEvent.timeStamp,n=t-(this.$lastScrollTime||0),r=this.editor,i=r.renderer.isScrollableBy(e.wheelX*e.speed,e.wheelY*e.speed);if(i||n<200)return this.$lastScrollTime=t,r.renderer.scrollBy(e.wheelX*e.speed,e.wheelY*e.speed),e.stop()}}).call(u.prototype),t.DefaultHandlers=u}),define(\"ace/tooltip\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/dom\"],function(e,t,n){\"use strict\";function s(e){this.isOpen=!1,this.$element=null,this.$parentNode=e}var r=e(\"./lib/oop\"),i=e(\"./lib/dom\");(function(){this.$init=function(){return this.$element=i.createElement(\"div\"),this.$element.className=\"ace_tooltip\",this.$element.style.display=\"none\",this.$parentNode.appendChild(this.$element),this.$element},this.getElement=function(){return this.$element||this.$init()},this.setText=function(e){i.setInnerText(this.getElement(),e)},this.setHtml=function(e){this.getElement().innerHTML=e},this.setPosition=function(e,t){this.getElement().style.left=e+\"px\",this.getElement().style.top=t+\"px\"},this.setClassName=function(e){i.addCssClass(this.getElement(),e)},this.show=function(e,t,n){e!=null&&this.setText(e),t!=null&&n!=null&&this.setPosition(t,n),this.isOpen||(this.getElement().style.display=\"block\",this.isOpen=!0)},this.hide=function(){this.isOpen&&(this.getElement().style.display=\"none\",this.isOpen=!1)},this.getHeight=function(){return this.getElement().offsetHeight},this.getWidth=function(){return this.getElement().offsetWidth}}).call(s.prototype),t.Tooltip=s}),define(\"ace/mouse/default_gutter_handler\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\",\"ace/lib/oop\",\"ace/lib/event\",\"ace/tooltip\"],function(e,t,n){\"use strict\";function u(e){function l(){var r=u.getDocumentPosition().row,s=n.$annotations[r];if(!s)return c();var o=t.session.getLength();if(r==o){var a=t.renderer.pixelToScreenCoordinates(0,u.y).row,l=u.$pos;if(a>t.session.documentToScreenRow(l.row,l.column))return c()}if(f==s)return;f=s.text.join(\"<br/>\"),i.setHtml(f),i.show(),t._signal(\"showGutterTooltip\",i),t.on(\"mousewheel\",c);if(e.$tooltipFollowsMouse)h(u);else{var p=u.domEvent.target,d=p.getBoundingClientRect(),v=i.getElement().style;v.left=d.right+\"px\",v.top=d.bottom+\"px\"}}function c(){o&&(o=clearTimeout(o)),f&&(i.hide(),f=null,t._signal(\"hideGutterTooltip\",i),t.removeEventListener(\"mousewheel\",c))}function h(e){i.setPosition(e.x,e.y)}var t=e.editor,n=t.renderer.$gutterLayer,i=new a(t.container);e.editor.setDefaultHandler(\"guttermousedown\",function(r){if(!t.isFocused()||r.getButton()!=0)return;var i=n.getRegion(r);if(i==\"foldWidgets\")return;var s=r.getDocumentPosition().row,o=t.session.selection;if(r.getShiftKey())o.selectTo(s,0);else{if(r.domEvent.detail==2)return t.selectAll(),r.preventDefault();e.$clickSelection=t.selection.getLineRange(s)}return e.setState(\"selectByLines\"),e.captureMouse(r),r.preventDefault()});var o,u,f;e.editor.setDefaultHandler(\"guttermousemove\",function(t){var n=t.domEvent.target||t.domEvent.srcElement;if(r.hasCssClass(n,\"ace_fold-widget\"))return c();f&&e.$tooltipFollowsMouse&&h(t),u=t;if(o)return;o=setTimeout(function(){o=null,u&&!e.isMousePressed?l():c()},50)}),s.addListener(t.renderer.$gutter,\"mouseout\",function(e){u=null;if(!f||o)return;o=setTimeout(function(){o=null,c()},50)}),t.on(\"changeSession\",c)}function a(e){o.call(this,e)}var r=e(\"../lib/dom\"),i=e(\"../lib/oop\"),s=e(\"../lib/event\"),o=e(\"../tooltip\").Tooltip;i.inherits(a,o),function(){this.setPosition=function(e,t){var n=window.innerWidth||document.documentElement.clientWidth,r=window.innerHeight||document.documentElement.clientHeight,i=this.getWidth(),s=this.getHeight();e+=15,t+=15,e+i>n&&(e-=e+i-n),t+s>r&&(t-=20+s),o.prototype.setPosition.call(this,e,t)}}.call(a.prototype),t.GutterHandler=u}),define(\"ace/mouse/mouse_event\",[\"require\",\"exports\",\"module\",\"ace/lib/event\",\"ace/lib/useragent\"],function(e,t,n){\"use strict\";var r=e(\"../lib/event\"),i=e(\"../lib/useragent\"),s=t.MouseEvent=function(e,t){this.domEvent=e,this.editor=t,this.x=this.clientX=e.clientX,this.y=this.clientY=e.clientY,this.$pos=null,this.$inSelection=null,this.propagationStopped=!1,this.defaultPrevented=!1};(function(){this.stopPropagation=function(){r.stopPropagation(this.domEvent),this.propagationStopped=!0},this.preventDefault=function(){r.preventDefault(this.domEvent),this.defaultPrevented=!0},this.stop=function(){this.stopPropagation(),this.preventDefault()},this.getDocumentPosition=function(){return this.$pos?this.$pos:(this.$pos=this.editor.renderer.screenToTextCoordinates(this.clientX,this.clientY),this.$pos)},this.inSelection=function(){if(this.$inSelection!==null)return this.$inSelection;var e=this.editor,t=e.getSelectionRange();if(t.isEmpty())this.$inSelection=!1;else{var n=this.getDocumentPosition();this.$inSelection=t.contains(n.row,n.column)}return this.$inSelection},this.getButton=function(){return r.getButton(this.domEvent)},this.getShiftKey=function(){return this.domEvent.shiftKey},this.getAccelKey=i.isMac?function(){return this.domEvent.metaKey}:function(){return this.domEvent.ctrlKey}}).call(s.prototype)}),define(\"ace/mouse/dragdrop_handler\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\",\"ace/lib/event\",\"ace/lib/useragent\"],function(e,t,n){\"use strict\";function f(e){function T(e,n){var r=Date.now(),i=!n||e.row!=n.row,s=!n||e.column!=n.column;if(!S||i||s)t.$blockScrolling+=1,t.moveCursorToPosition(e),t.$blockScrolling-=1,S=r,x={x:p,y:d};else{var o=l(x.x,x.y,p,d);o>a?S=null:r-S>=u&&(t.renderer.scrollCursorIntoView(),S=null)}}function N(e,n){var r=Date.now(),i=t.renderer.layerConfig.lineHeight,s=t.renderer.layerConfig.characterWidth,u=t.renderer.scroller.getBoundingClientRect(),a={x:{left:p-u.left,right:u.right-p},y:{top:d-u.top,bottom:u.bottom-d}},f=Math.min(a.x.left,a.x.right),l=Math.min(a.y.top,a.y.bottom),c={row:e.row,column:e.column};f/s<=2&&(c.column+=a.x.left<a.x.right?-3:2),l/i<=1&&(c.row+=a.y.top<a.y.bottom?-1:1);var h=e.row!=c.row,v=e.column!=c.column,m=!n||e.row!=n.row;h||v&&!m?E?r-E>=o&&t.renderer.scrollCursorIntoView(c):E=r:E=null}function C(){var e=g;g=t.renderer.screenToTextCoordinates(p,d),T(g,e),N(g,e)}function k(){m=t.selection.toOrientedRange(),h=t.session.addMarker(m,\"ace_selection\",t.getSelectionStyle()),t.clearSelection(),t.isFocused()&&t.renderer.$cursorLayer.setBlinking(!1),clearInterval(v),C(),v=setInterval(C,20),y=0,i.addListener(document,\"mousemove\",O)}function L(){clearInterval(v),t.session.removeMarker(h),h=null,t.$blockScrolling+=1,t.selection.fromOrientedRange(m),t.$blockScrolling-=1,t.isFocused()&&!w&&t.renderer.$cursorLayer.setBlinking(!t.getReadOnly()),m=null,g=null,y=0,E=null,S=null,i.removeListener(document,\"mousemove\",O)}function O(){A==null&&(A=setTimeout(function(){A!=null&&h&&L()},20))}function M(e){var t=e.types;return!t||Array.prototype.some.call(t,function(e){return e==\"text/plain\"||e==\"Text\"})}function _(e){var t=[\"copy\",\"copymove\",\"all\",\"uninitialized\"],n=[\"move\",\"copymove\",\"linkmove\",\"all\",\"uninitialized\"],r=s.isMac?e.altKey:e.ctrlKey,i=\"uninitialized\";try{i=e.dataTransfer.effectAllowed.toLowerCase()}catch(e){}var o=\"none\";return r&&t.indexOf(i)>=0?o=\"copy\":n.indexOf(i)>=0?o=\"move\":t.indexOf(i)>=0&&(o=\"copy\"),o}var t=e.editor,n=r.createElement(\"img\");n.src=\"data:image/gif;base64,R0lGODlhAQABAAAAACH5BAEKAAEALAAAAAABAAEAAAICTAEAOw==\",s.isOpera&&(n.style.cssText=\"width:1px;height:1px;position:fixed;top:0;left:0;z-index:2147483647;opacity:0;\");var f=[\"dragWait\",\"dragWaitEnd\",\"startDrag\",\"dragReadyEnd\",\"onMouseDrag\"];f.forEach(function(t){e[t]=this[t]},this),t.addEventListener(\"mousedown\",this.onMouseDown.bind(e));var c=t.container,h,p,d,v,m,g,y=0,b,w,E,S,x;this.onDragStart=function(e){if(this.cancelDrag||!c.draggable){var r=this;return setTimeout(function(){r.startSelect(),r.captureMouse(e)},0),e.preventDefault()}m=t.getSelectionRange();var i=e.dataTransfer;i.effectAllowed=t.getReadOnly()?\"copy\":\"copyMove\",s.isOpera&&(t.container.appendChild(n),n.scrollTop=0),i.setDragImage&&i.setDragImage(n,0,0),s.isOpera&&t.container.removeChild(n),i.clearData(),i.setData(\"Text\",t.session.getTextRange()),w=!0,this.setState(\"drag\")},this.onDragEnd=function(e){c.draggable=!1,w=!1,this.setState(null);if(!t.getReadOnly()){var n=e.dataTransfer.dropEffect;!b&&n==\"move\"&&t.session.remove(t.getSelectionRange()),t.renderer.$cursorLayer.setBlinking(!0)}this.editor.unsetStyle(\"ace_dragging\"),this.editor.renderer.setCursorStyle(\"\")},this.onDragEnter=function(e){if(t.getReadOnly()||!M(e.dataTransfer))return;return p=e.clientX,d=e.clientY,h||k(),y++,e.dataTransfer.dropEffect=b=_(e),i.preventDefault(e)},this.onDragOver=function(e){if(t.getReadOnly()||!M(e.dataTransfer))return;return p=e.clientX,d=e.clientY,h||(k(),y++),A!==null&&(A=null),e.dataTransfer.dropEffect=b=_(e),i.preventDefault(e)},this.onDragLeave=function(e){y--;if(y<=0&&h)return L(),b=null,i.preventDefault(e)},this.onDrop=function(e){if(!g)return;var n=e.dataTransfer;if(w)switch(b){case\"move\":m.contains(g.row,g.column)?m={start:g,end:g}:m=t.moveText(m,g);break;case\"copy\":m=t.moveText(m,g,!0)}else{var r=n.getData(\"Text\");m={start:g,end:t.session.insert(g,r)},t.focus(),b=null}return L(),i.preventDefault(e)},i.addListener(c,\"dragstart\",this.onDragStart.bind(e)),i.addListener(c,\"dragend\",this.onDragEnd.bind(e)),i.addListener(c,\"dragenter\",this.onDragEnter.bind(e)),i.addListener(c,\"dragover\",this.onDragOver.bind(e)),i.addListener(c,\"dragleave\",this.onDragLeave.bind(e)),i.addListener(c,\"drop\",this.onDrop.bind(e));var A=null}function l(e,t,n,r){return Math.sqrt(Math.pow(n-e,2)+Math.pow(r-t,2))}var r=e(\"../lib/dom\"),i=e(\"../lib/event\"),s=e(\"../lib/useragent\"),o=200,u=200,a=5;(function(){this.dragWait=function(){var e=Date.now()-this.mousedownEvent.time;e>this.editor.getDragDelay()&&this.startDrag()},this.dragWaitEnd=function(){var e=this.editor.container;e.draggable=!1,this.startSelect(this.mousedownEvent.getDocumentPosition()),this.selectEnd()},this.dragReadyEnd=function(e){this.editor.renderer.$cursorLayer.setBlinking(!this.editor.getReadOnly()),this.editor.unsetStyle(\"ace_dragging\"),this.editor.renderer.setCursorStyle(\"\"),this.dragWaitEnd()},this.startDrag=function(){this.cancelDrag=!1;var e=this.editor,t=e.container;t.draggable=!0,e.renderer.$cursorLayer.setBlinking(!1),e.setStyle(\"ace_dragging\");var n=s.isWin?\"default\":\"move\";e.renderer.setCursorStyle(n),this.setState(\"dragReady\")},this.onMouseDrag=function(e){var t=this.editor.container;if(s.isIE&&this.state==\"dragReady\"){var n=l(this.mousedownEvent.x,this.mousedownEvent.y,this.x,this.y);n>3&&t.dragDrop()}if(this.state===\"dragWait\"){var n=l(this.mousedownEvent.x,this.mousedownEvent.y,this.x,this.y);n>0&&(t.draggable=!1,this.startSelect(this.mousedownEvent.getDocumentPosition()))}},this.onMouseDown=function(e){if(!this.$dragEnabled)return;this.mousedownEvent=e;var t=this.editor,n=e.inSelection(),r=e.getButton(),i=e.domEvent.detail||1;if(i===1&&r===0&&n){if(e.editor.inMultiSelectMode&&(e.getAccelKey()||e.getShiftKey()))return;this.mousedownEvent.time=Date.now();var o=e.domEvent.target||e.domEvent.srcElement;\"unselectable\"in o&&(o.unselectable=\"on\");if(t.getDragDelay()){if(s.isWebKit){this.cancelDrag=!0;var u=t.container;u.draggable=!0}this.setState(\"dragWait\")}else this.startDrag();this.captureMouse(e,this.onMouseDrag.bind(this)),e.defaultPrevented=!0}}}).call(f.prototype),t.DragdropHandler=f}),define(\"ace/lib/net\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\"],function(e,t,n){\"use strict\";var r=e(\"./dom\");t.get=function(e,t){var n=new XMLHttpRequest;n.open(\"GET\",e,!0),n.onreadystatechange=function(){n.readyState===4&&t(n.responseText)},n.send(null)},t.loadScript=function(e,t){var n=r.getDocumentHead(),i=document.createElement(\"script\");i.src=e,n.appendChild(i),i.onload=i.onreadystatechange=function(e,n){if(n||!i.readyState||i.readyState==\"loaded\"||i.readyState==\"complete\")i=i.onload=i.onreadystatechange=null,n||t()}},t.qualifyURL=function(e){var t=document.createElement(\"a\");return t.href=e,t.href}}),define(\"ace/lib/event_emitter\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={},i=function(){this.propagationStopped=!0},s=function(){this.defaultPrevented=!0};r._emit=r._dispatchEvent=function(e,t){this._eventRegistry||(this._eventRegistry={}),this._defaultHandlers||(this._defaultHandlers={});var n=this._eventRegistry[e]||[],r=this._defaultHandlers[e];if(!n.length&&!r)return;if(typeof t!=\"object\"||!t)t={};t.type||(t.type=e),t.stopPropagation||(t.stopPropagation=i),t.preventDefault||(t.preventDefault=s),n=n.slice();for(var o=0;o<n.length;o++){n[o](t,this);if(t.propagationStopped)break}if(r&&!t.defaultPrevented)return r(t,this)},r._signal=function(e,t){var n=(this._eventRegistry||{})[e];if(!n)return;n=n.slice();for(var r=0;r<n.length;r++)n[r](t,this)},r.once=function(e,t){var n=this;t&&this.addEventListener(e,function r(){n.removeEventListener(e,r),t.apply(null,arguments)})},r.setDefaultHandler=function(e,t){var n=this._defaultHandlers;n||(n=this._defaultHandlers={_disabled_:{}});if(n[e]){var r=n[e],i=n._disabled_[e];i||(n._disabled_[e]=i=[]),i.push(r);var s=i.indexOf(t);s!=-1&&i.splice(s,1)}n[e]=t},r.removeDefaultHandler=function(e,t){var n=this._defaultHandlers;if(!n)return;var r=n._disabled_[e];if(n[e]==t){var i=n[e];r&&this.setDefaultHandler(e,r.pop())}else if(r){var s=r.indexOf(t);s!=-1&&r.splice(s,1)}},r.on=r.addEventListener=function(e,t,n){this._eventRegistry=this._eventRegistry||{};var r=this._eventRegistry[e];return r||(r=this._eventRegistry[e]=[]),r.indexOf(t)==-1&&r[n?\"unshift\":\"push\"](t),t},r.off=r.removeListener=r.removeEventListener=function(e,t){this._eventRegistry=this._eventRegistry||{};var n=this._eventRegistry[e];if(!n)return;var r=n.indexOf(t);r!==-1&&n.splice(r,1)},r.removeAllListeners=function(e){this._eventRegistry&&(this._eventRegistry[e]=[])},t.EventEmitter=r}),define(\"ace/lib/app_config\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/event_emitter\"],function(e,t,n){\"no use strict\";function o(e){typeof console!=\"undefined\"&&console.warn&&console.warn.apply(console,arguments)}function u(e,t){var n=new Error(e);n.data=t,typeof console==\"object\"&&console.error&&console.error(n),setTimeout(function(){throw n})}var r=e(\"./oop\"),i=e(\"./event_emitter\").EventEmitter,s={setOptions:function(e){Object.keys(e).forEach(function(t){this.setOption(t,e[t])},this)},getOptions:function(e){var t={};return e?Array.isArray(e)||(t=e,e=Object.keys(t)):e=Object.keys(this.$options),e.forEach(function(e){t[e]=this.getOption(e)},this),t},setOption:function(e,t){if(this[\"$\"+e]===t)return;var n=this.$options[e];if(!n)return o('misspelled option \"'+e+'\"');if(n.forwardTo)return this[n.forwardTo]&&this[n.forwardTo].setOption(e,t);n.handlesSet||(this[\"$\"+e]=t),n&&n.set&&n.set.call(this,t)},getOption:function(e){var t=this.$options[e];return t?t.forwardTo?this[t.forwardTo]&&this[t.forwardTo].getOption(e):t&&t.get?t.get.call(this):this[\"$\"+e]:o('misspelled option \"'+e+'\"')}},a=function(){this.$defaultOptions={}};(function(){r.implement(this,i),this.defineOptions=function(e,t,n){return e.$options||(this.$defaultOptions[t]=e.$options={}),Object.keys(n).forEach(function(t){var r=n[t];typeof r==\"string\"&&(r={forwardTo:r}),r.name||(r.name=t),e.$options[r.name]=r,\"initialValue\"in r&&(e[\"$\"+r.name]=r.initialValue)}),r.implement(e,s),this},this.resetOptions=function(e){Object.keys(e.$options).forEach(function(t){var n=e.$options[t];\"value\"in n&&e.setOption(t,n.value)})},this.setDefaultValue=function(e,t,n){var r=this.$defaultOptions[e]||(this.$defaultOptions[e]={});r[t]&&(r.forwardTo?this.setDefaultValue(r.forwardTo,t,n):r[t].value=n)},this.setDefaultValues=function(e,t){Object.keys(t).forEach(function(n){this.setDefaultValue(e,n,t[n])},this)},this.warn=o,this.reportError=u}).call(a.prototype),t.AppConfig=a}),define(\"ace/config\",[\"require\",\"exports\",\"module\",\"ace/lib/lang\",\"ace/lib/oop\",\"ace/lib/net\",\"ace/lib/app_config\"],function(e,t,n){\"no use strict\";function f(r){if(!u||!u.document)return;a.packaged=r||e.packaged||n.packaged||u.define&&define.packaged;var i={},s=\"\",o=document.currentScript||document._currentScript,f=o&&o.ownerDocument||document,c=f.getElementsByTagName(\"script\");for(var h=0;h<c.length;h++){var p=c[h],d=p.src||p.getAttribute(\"src\");if(!d)continue;var v=p.attributes;for(var m=0,g=v.length;m<g;m++){var y=v[m];y.name.indexOf(\"data-ace-\")===0&&(i[l(y.name.replace(/^data-ace-/,\"\"))]=y.value)}var b=d.match(/^(.*)\\/ace(\\-\\w+)?\\.js(\\?|$)/);b&&(s=b[1])}s&&(i.base=i.base||s,i.packaged=!0),i.basePath=i.base,i.workerPath=i.workerPath||i.base,i.modePath=i.modePath||i.base,i.themePath=i.themePath||i.base,delete i.base;for(var w in i)typeof i[w]!=\"undefined\"&&t.set(w,i[w])}function l(e){return e.replace(/-(.)/g,function(e,t){return t.toUpperCase()})}var r=e(\"./lib/lang\"),i=e(\"./lib/oop\"),s=e(\"./lib/net\"),o=e(\"./lib/app_config\").AppConfig;n.exports=t=new o;var u=function(){return this||typeof window!=\"undefined\"&&window}(),a={packaged:!1,workerPath:null,modePath:null,themePath:null,basePath:\"\",suffix:\".js\",$moduleUrls:{}};t.get=function(e){if(!a.hasOwnProperty(e))throw new Error(\"Unknown config key: \"+e);return a[e]},t.set=function(e,t){if(!a.hasOwnProperty(e))throw new Error(\"Unknown config key: \"+e);a[e]=t},t.all=function(){return r.copyObject(a)},t.moduleUrl=function(e,t){if(a.$moduleUrls[e])return a.$moduleUrls[e];var n=e.split(\"/\");t=t||n[n.length-2]||\"\";var r=t==\"snippets\"?\"/\":\"-\",i=n[n.length-1];if(t==\"worker\"&&r==\"-\"){var s=new RegExp(\"^\"+t+\"[\\\\-_]|[\\\\-_]\"+t+\"$\",\"g\");i=i.replace(s,\"\")}(!i||i==t)&&n.length>1&&(i=n[n.length-2]);var o=a[t+\"Path\"];return o==null?o=a.basePath:r==\"/\"&&(t=r=\"\"),o&&o.slice(-1)!=\"/\"&&(o+=\"/\"),o+t+r+i+this.get(\"suffix\")},t.setModuleUrl=function(e,t){return a.$moduleUrls[e]=t},t.$loading={},t.loadModule=function(n,r){var i,o;Array.isArray(n)&&(o=n[0],n=n[1]);try{i=e(n)}catch(u){}if(i&&!t.$loading[n])return r&&r(i);t.$loading[n]||(t.$loading[n]=[]),t.$loading[n].push(r);if(t.$loading[n].length>1)return;var a=function(){e([n],function(e){t._emit(\"load.module\",{name:n,module:e});var r=t.$loading[n];t.$loading[n]=null,r.forEach(function(t){t&&t(e)})})};if(!t.get(\"packaged\"))return a();s.loadScript(t.moduleUrl(n,o),a)},t.init=f}),define(\"ace/mouse/mouse_handler\",[\"require\",\"exports\",\"module\",\"ace/lib/event\",\"ace/lib/useragent\",\"ace/mouse/default_handlers\",\"ace/mouse/default_gutter_handler\",\"ace/mouse/mouse_event\",\"ace/mouse/dragdrop_handler\",\"ace/config\"],function(e,t,n){\"use strict\";var r=e(\"../lib/event\"),i=e(\"../lib/useragent\"),s=e(\"./default_handlers\").DefaultHandlers,o=e(\"./default_gutter_handler\").GutterHandler,u=e(\"./mouse_event\").MouseEvent,a=e(\"./dragdrop_handler\").DragdropHandler,f=e(\"../config\"),l=function(e){var t=this;this.editor=e,new s(this),new o(this),new a(this);var n=function(t){var n=!document.hasFocus||!document.hasFocus()||!e.isFocused()&&document.activeElement==(e.textInput&&e.textInput.getElement());n&&window.focus(),e.focus()},u=e.renderer.getMouseEventTarget();r.addListener(u,\"click\",this.onMouseEvent.bind(this,\"click\")),r.addListener(u,\"mousemove\",this.onMouseMove.bind(this,\"mousemove\")),r.addMultiMouseDownListener([u,e.renderer.scrollBarV&&e.renderer.scrollBarV.inner,e.renderer.scrollBarH&&e.renderer.scrollBarH.inner,e.textInput&&e.textInput.getElement()].filter(Boolean),[400,300,250],this,\"onMouseEvent\"),r.addMouseWheelListener(e.container,this.onMouseWheel.bind(this,\"mousewheel\")),r.addTouchMoveListener(e.container,this.onTouchMove.bind(this,\"touchmove\"));var f=e.renderer.$gutter;r.addListener(f,\"mousedown\",this.onMouseEvent.bind(this,\"guttermousedown\")),r.addListener(f,\"click\",this.onMouseEvent.bind(this,\"gutterclick\")),r.addListener(f,\"dblclick\",this.onMouseEvent.bind(this,\"gutterdblclick\")),r.addListener(f,\"mousemove\",this.onMouseEvent.bind(this,\"guttermousemove\")),r.addListener(u,\"mousedown\",n),r.addListener(f,\"mousedown\",n),i.isIE&&e.renderer.scrollBarV&&(r.addListener(e.renderer.scrollBarV.element,\"mousedown\",n),r.addListener(e.renderer.scrollBarH.element,\"mousedown\",n)),e.on(\"mousemove\",function(n){if(t.state||t.$dragDelay||!t.$dragEnabled)return;var r=e.renderer.screenToTextCoordinates(n.x,n.y),i=e.session.selection.getRange(),s=e.renderer;!i.isEmpty()&&i.insideStart(r.row,r.column)?s.setCursorStyle(\"default\"):s.setCursorStyle(\"\")})};(function(){this.onMouseEvent=function(e,t){this.editor._emit(e,new u(t,this.editor))},this.onMouseMove=function(e,t){var n=this.editor._eventRegistry&&this.editor._eventRegistry.mousemove;if(!n||!n.length)return;this.editor._emit(e,new u(t,this.editor))},this.onMouseWheel=function(e,t){var n=new u(t,this.editor);n.speed=this.$scrollSpeed*2,n.wheelX=t.wheelX,n.wheelY=t.wheelY,this.editor._emit(e,n)},this.onTouchMove=function(e,t){var n=new u(t,this.editor);n.speed=1,n.wheelX=t.wheelX,n.wheelY=t.wheelY,this.editor._emit(e,n)},this.setState=function(e){this.state=e},this.captureMouse=function(e,t){this.x=e.x,this.y=e.y,this.isMousePressed=!0;var n=this.editor.renderer;n.$keepTextAreaAtCursor&&(n.$keepTextAreaAtCursor=null);var s=this,o=function(e){if(!e)return;if(i.isWebKit&&!e.which&&s.releaseMouse)return s.releaseMouse();s.x=e.clientX,s.y=e.clientY,t&&t(e),s.mouseEvent=new u(e,s.editor),s.$mouseMoved=!0},a=function(e){clearInterval(l),f(),s[s.state+\"End\"]&&s[s.state+\"End\"](e),s.state=\"\",n.$keepTextAreaAtCursor==null&&(n.$keepTextAreaAtCursor=!0,n.$moveTextAreaToCursor()),s.isMousePressed=!1,s.$onCaptureMouseMove=s.releaseMouse=null,e&&s.onMouseEvent(\"mouseup\",e)},f=function(){s[s.state]&&s[s.state](),s.$mouseMoved=!1};if(i.isOldIE&&e.domEvent.type==\"dblclick\")return setTimeout(function(){a(e)});s.$onCaptureMouseMove=o,s.releaseMouse=r.capture(this.editor.container,o,a);var l=setInterval(f,20)},this.releaseMouse=null,this.cancelContextMenu=function(){var e=function(t){if(t&&t.domEvent&&t.domEvent.type!=\"contextmenu\")return;this.editor.off(\"nativecontextmenu\",e),t&&t.domEvent&&r.stopEvent(t.domEvent)}.bind(this);setTimeout(e,10),this.editor.on(\"nativecontextmenu\",e)}}).call(l.prototype),f.defineOptions(l.prototype,\"mouseHandler\",{scrollSpeed:{initialValue:2},dragDelay:{initialValue:i.isMac?150:0},dragEnabled:{initialValue:!0},focusTimout:{initialValue:0},tooltipFollowsMouse:{initialValue:!0}}),t.MouseHandler=l}),define(\"ace/mouse/fold_handler\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function r(e){e.on(\"click\",function(t){var n=t.getDocumentPosition(),r=e.session,i=r.getFoldAt(n.row,n.column,1);i&&(t.getAccelKey()?r.removeFold(i):r.expandFold(i),t.stop())}),e.on(\"gutterclick\",function(t){var n=e.renderer.$gutterLayer.getRegion(t);if(n==\"foldWidgets\"){var r=t.getDocumentPosition().row,i=e.session;i.foldWidgets&&i.foldWidgets[r]&&e.session.onFoldWidgetClick(r,t),e.isFocused()||e.focus(),t.stop()}}),e.on(\"gutterdblclick\",function(t){var n=e.renderer.$gutterLayer.getRegion(t);if(n==\"foldWidgets\"){var r=t.getDocumentPosition().row,i=e.session,s=i.getParentFoldRangeData(r,!0),o=s.range||s.firstRange;if(o){r=o.start.row;var u=i.getFoldAt(r,i.getLine(r).length,1);u?i.removeFold(u):(i.addFold(\"...\",o),e.renderer.scrollCursorIntoView({row:o.start.row,column:0}))}t.stop()}})}t.FoldHandler=r}),define(\"ace/keyboard/keybinding\",[\"require\",\"exports\",\"module\",\"ace/lib/keys\",\"ace/lib/event\"],function(e,t,n){\"use strict\";var r=e(\"../lib/keys\"),i=e(\"../lib/event\"),s=function(e){this.$editor=e,this.$data={editor:e},this.$handlers=[],this.setDefaultHandler(e.commands)};(function(){this.setDefaultHandler=function(e){this.removeKeyboardHandler(this.$defaultHandler),this.$defaultHandler=e,this.addKeyboardHandler(e,0)},this.setKeyboardHandler=function(e){var t=this.$handlers;if(t[t.length-1]==e)return;while(t[t.length-1]&&t[t.length-1]!=this.$defaultHandler)this.removeKeyboardHandler(t[t.length-1]);this.addKeyboardHandler(e,1)},this.addKeyboardHandler=function(e,t){if(!e)return;typeof e==\"function\"&&!e.handleKeyboard&&(e.handleKeyboard=e);var n=this.$handlers.indexOf(e);n!=-1&&this.$handlers.splice(n,1),t==undefined?this.$handlers.push(e):this.$handlers.splice(t,0,e),n==-1&&e.attach&&e.attach(this.$editor)},this.removeKeyboardHandler=function(e){var t=this.$handlers.indexOf(e);return t==-1?!1:(this.$handlers.splice(t,1),e.detach&&e.detach(this.$editor),!0)},this.getKeyboardHandler=function(){return this.$handlers[this.$handlers.length-1]},this.getStatusText=function(){var e=this.$data,t=e.editor;return this.$handlers.map(function(n){return n.getStatusText&&n.getStatusText(t,e)||\"\"}).filter(Boolean).join(\" \")},this.$callKeyboardHandlers=function(e,t,n,r){var s,o=!1,u=this.$editor.commands;for(var a=this.$handlers.length;a--;){s=this.$handlers[a].handleKeyboard(this.$data,e,t,n,r);if(!s||!s.command)continue;s.command==\"null\"?o=!0:o=u.exec(s.command,this.$editor,s.args,r),o&&r&&e!=-1&&s.passEvent!=1&&s.command.passEvent!=1&&i.stopEvent(r);if(o)break}return!o&&e==-1&&(s={command:\"insertstring\"},o=u.exec(\"insertstring\",this.$editor,t)),o&&this.$editor._signal&&this.$editor._signal(\"keyboardActivity\",s),o},this.onCommandKey=function(e,t,n){var i=r.keyCodeToString(n);this.$callKeyboardHandlers(t,i,n,e)},this.onTextInput=function(e){this.$callKeyboardHandlers(-1,e)}}).call(s.prototype),t.KeyBinding=s}),define(\"ace/range\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(e,t){return e.row-t.row||e.column-t.column},i=function(e,t,n,r){this.start={row:e,column:t},this.end={row:n,column:r}};(function(){this.isEqual=function(e){return this.start.row===e.start.row&&this.end.row===e.end.row&&this.start.column===e.start.column&&this.end.column===e.end.column},this.toString=function(){return\"Range: [\"+this.start.row+\"/\"+this.start.column+\"] -> [\"+this.end.row+\"/\"+this.end.column+\"]\"},this.contains=function(e,t){return this.compare(e,t)==0},this.compareRange=function(e){var t,n=e.end,r=e.start;return t=this.compare(n.row,n.column),t==1?(t=this.compare(r.row,r.column),t==1?2:t==0?1:0):t==-1?-2:(t=this.compare(r.row,r.column),t==-1?-1:t==1?42:0)},this.comparePoint=function(e){return this.compare(e.row,e.column)},this.containsRange=function(e){return this.comparePoint(e.start)==0&&this.comparePoint(e.end)==0},this.intersects=function(e){var t=this.compareRange(e);return t==-1||t==0||t==1},this.isEnd=function(e,t){return this.end.row==e&&this.end.column==t},this.isStart=function(e,t){return this.start.row==e&&this.start.column==t},this.setStart=function(e,t){typeof e==\"object\"?(this.start.column=e.column,this.start.row=e.row):(this.start.row=e,this.start.column=t)},this.setEnd=function(e,t){typeof e==\"object\"?(this.end.column=e.column,this.end.row=e.row):(this.end.row=e,this.end.column=t)},this.inside=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)||this.isStart(e,t)?!1:!0:!1},this.insideStart=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)?!1:!0:!1},this.insideEnd=function(e,t){return this.compare(e,t)==0?this.isStart(e,t)?!1:!0:!1},this.compare=function(e,t){return!this.isMultiLine()&&e===this.start.row?t<this.start.column?-1:t>this.end.column?1:0:e<this.start.row?-1:e>this.end.row?1:this.start.row===e?t>=this.start.column?0:-1:this.end.row===e?t<=this.end.column?0:1:0},this.compareStart=function(e,t){return this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.compareEnd=function(e,t){return this.end.row==e&&this.end.column==t?1:this.compare(e,t)},this.compareInside=function(e,t){return this.end.row==e&&this.end.column==t?1:this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.clipRows=function(e,t){if(this.end.row>t)var n={row:t+1,column:0};else if(this.end.row<e)var n={row:e,column:0};if(this.start.row>t)var r={row:t+1,column:0};else if(this.start.row<e)var r={row:e,column:0};return i.fromPoints(r||this.start,n||this.end)},this.extend=function(e,t){var n=this.compare(e,t);if(n==0)return this;if(n==-1)var r={row:e,column:t};else var s={row:e,column:t};return i.fromPoints(r||this.start,s||this.end)},this.isEmpty=function(){return this.start.row===this.end.row&&this.start.column===this.end.column},this.isMultiLine=function(){return this.start.row!==this.end.row},this.clone=function(){return i.fromPoints(this.start,this.end)},this.collapseRows=function(){return this.end.column==0?new i(this.start.row,0,Math.max(this.start.row,this.end.row-1),0):new i(this.start.row,0,this.end.row,0)},this.toScreenRange=function(e){var t=e.documentToScreenPosition(this.start),n=e.documentToScreenPosition(this.end);return new i(t.row,t.column,n.row,n.column)},this.moveBy=function(e,t){this.start.row+=e,this.start.column+=t,this.end.row+=e,this.end.column+=t}}).call(i.prototype),i.fromPoints=function(e,t){return new i(e.row,e.column,t.row,t.column)},i.comparePoints=r,i.comparePoints=function(e,t){return e.row-t.row||e.column-t.column},t.Range=i}),define(\"ace/selection\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/lib/event_emitter\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/lang\"),s=e(\"./lib/event_emitter\").EventEmitter,o=e(\"./range\").Range,u=function(e){this.session=e,this.doc=e.getDocument(),this.clearSelection(),this.lead=this.selectionLead=this.doc.createAnchor(0,0),this.anchor=this.selectionAnchor=this.doc.createAnchor(0,0);var t=this;this.lead.on(\"change\",function(e){t._emit(\"changeCursor\"),t.$isEmpty||t._emit(\"changeSelection\"),!t.$keepDesiredColumnOnChange&&e.old.column!=e.value.column&&(t.$desiredColumn=null)}),this.selectionAnchor.on(\"change\",function(){t.$isEmpty||t._emit(\"changeSelection\")})};(function(){r.implement(this,s),this.isEmpty=function(){return this.$isEmpty||this.anchor.row==this.lead.row&&this.anchor.column==this.lead.column},this.isMultiLine=function(){return this.isEmpty()?!1:this.getRange().isMultiLine()},this.getCursor=function(){return this.lead.getPosition()},this.setSelectionAnchor=function(e,t){this.anchor.setPosition(e,t),this.$isEmpty&&(this.$isEmpty=!1,this._emit(\"changeSelection\"))},this.getSelectionAnchor=function(){return this.$isEmpty?this.getSelectionLead():this.anchor.getPosition()},this.getSelectionLead=function(){return this.lead.getPosition()},this.shiftSelection=function(e){if(this.$isEmpty){this.moveCursorTo(this.lead.row,this.lead.column+e);return}var t=this.getSelectionAnchor(),n=this.getSelectionLead(),r=this.isBackwards();(!r||t.column!==0)&&this.setSelectionAnchor(t.row,t.column+e),(r||n.column!==0)&&this.$moveSelection(function(){this.moveCursorTo(n.row,n.column+e)})},this.isBackwards=function(){var e=this.anchor,t=this.lead;return e.row>t.row||e.row==t.row&&e.column>t.column},this.getRange=function(){var e=this.anchor,t=this.lead;return this.isEmpty()?o.fromPoints(t,t):this.isBackwards()?o.fromPoints(t,e):o.fromPoints(e,t)},this.clearSelection=function(){this.$isEmpty||(this.$isEmpty=!0,this._emit(\"changeSelection\"))},this.selectAll=function(){var e=this.doc.getLength()-1;this.setSelectionAnchor(0,0),this.moveCursorTo(e,this.doc.getLine(e).length)},this.setRange=this.setSelectionRange=function(e,t){t?(this.setSelectionAnchor(e.end.row,e.end.column),this.selectTo(e.start.row,e.start.column)):(this.setSelectionAnchor(e.start.row,e.start.column),this.selectTo(e.end.row,e.end.column)),this.getRange().isEmpty()&&(this.$isEmpty=!0),this.$desiredColumn=null},this.$moveSelection=function(e){var t=this.lead;this.$isEmpty&&this.setSelectionAnchor(t.row,t.column),e.call(this)},this.selectTo=function(e,t){this.$moveSelection(function(){this.moveCursorTo(e,t)})},this.selectToPosition=function(e){this.$moveSelection(function(){this.moveCursorToPosition(e)})},this.moveTo=function(e,t){this.clearSelection(),this.moveCursorTo(e,t)},this.moveToPosition=function(e){this.clearSelection(),this.moveCursorToPosition(e)},this.selectUp=function(){this.$moveSelection(this.moveCursorUp)},this.selectDown=function(){this.$moveSelection(this.moveCursorDown)},this.selectRight=function(){this.$moveSelection(this.moveCursorRight)},this.selectLeft=function(){this.$moveSelection(this.moveCursorLeft)},this.selectLineStart=function(){this.$moveSelection(this.moveCursorLineStart)},this.selectLineEnd=function(){this.$moveSelection(this.moveCursorLineEnd)},this.selectFileEnd=function(){this.$moveSelection(this.moveCursorFileEnd)},this.selectFileStart=function(){this.$moveSelection(this.moveCursorFileStart)},this.selectWordRight=function(){this.$moveSelection(this.moveCursorWordRight)},this.selectWordLeft=function(){this.$moveSelection(this.moveCursorWordLeft)},this.getWordRange=function(e,t){if(typeof t==\"undefined\"){var n=e||this.lead;e=n.row,t=n.column}return this.session.getWordRange(e,t)},this.selectWord=function(){this.setSelectionRange(this.getWordRange())},this.selectAWord=function(){var e=this.getCursor(),t=this.session.getAWordRange(e.row,e.column);this.setSelectionRange(t)},this.getLineRange=function(e,t){var n=typeof e==\"number\"?e:this.lead.row,r,i=this.session.getFoldLine(n);return i?(n=i.start.row,r=i.end.row):r=n,t===!0?new o(n,0,r,this.session.getLine(r).length):new o(n,0,r+1,0)},this.selectLine=function(){this.setSelectionRange(this.getLineRange())},this.moveCursorUp=function(){this.moveCursorBy(-1,0)},this.moveCursorDown=function(){this.moveCursorBy(1,0)},this.moveCursorLeft=function(){var e=this.lead.getPosition(),t;if(t=this.session.getFoldAt(e.row,e.column,-1))this.moveCursorTo(t.start.row,t.start.column);else if(e.column===0)e.row>0&&this.moveCursorTo(e.row-1,this.doc.getLine(e.row-1).length);else{var n=this.session.getTabSize();this.session.isTabStop(e)&&this.doc.getLine(e.row).slice(e.column-n,e.column).split(\" \").length-1==n?this.moveCursorBy(0,-n):this.moveCursorBy(0,-1)}},this.moveCursorRight=function(){var e=this.lead.getPosition(),t;if(t=this.session.getFoldAt(e.row,e.column,1))this.moveCursorTo(t.end.row,t.end.column);else if(this.lead.column==this.doc.getLine(this.lead.row).length)this.lead.row<this.doc.getLength()-1&&this.moveCursorTo(this.lead.row+1,0);else{var n=this.session.getTabSize(),e=this.lead;this.session.isTabStop(e)&&this.doc.getLine(e.row).slice(e.column,e.column+n).split(\" \").length-1==n?this.moveCursorBy(0,n):this.moveCursorBy(0,1)}},this.moveCursorLineStart=function(){var e=this.lead.row,t=this.lead.column,n=this.session.documentToScreenRow(e,t),r=this.session.screenToDocumentPosition(n,0),i=this.session.getDisplayLine(e,null,r.row,r.column),s=i.match(/^\\s*/);s[0].length!=t&&!this.session.$useEmacsStyleLineStart&&(r.column+=s[0].length),this.moveCursorToPosition(r)},this.moveCursorLineEnd=function(){var e=this.lead,t=this.session.getDocumentLastRowColumnPosition(e.row,e.column);if(this.lead.column==t.column){var n=this.session.getLine(t.row);if(t.column==n.length){var r=n.search(/\\s+$/);r>0&&(t.column=r)}}this.moveCursorTo(t.row,t.column)},this.moveCursorFileEnd=function(){var e=this.doc.getLength()-1,t=this.doc.getLine(e).length;this.moveCursorTo(e,t)},this.moveCursorFileStart=function(){this.moveCursorTo(0,0)},this.moveCursorLongWordRight=function(){var e=this.lead.row,t=this.lead.column,n=this.doc.getLine(e),r=n.substring(t),i;this.session.nonTokenRe.lastIndex=0,this.session.tokenRe.lastIndex=0;var s=this.session.getFoldAt(e,t,1);if(s){this.moveCursorTo(s.end.row,s.end.column);return}if(i=this.session.nonTokenRe.exec(r))t+=this.session.nonTokenRe.lastIndex,this.session.nonTokenRe.lastIndex=0,r=n.substring(t);if(t>=n.length){this.moveCursorTo(e,n.length),this.moveCursorRight(),e<this.doc.getLength()-1&&this.moveCursorWordRight();return}if(i=this.session.tokenRe.exec(r))t+=this.session.tokenRe.lastIndex,this.session.tokenRe.lastIndex=0;this.moveCursorTo(e,t)},this.moveCursorLongWordLeft=function(){var e=this.lead.row,t=this.lead.column,n;if(n=this.session.getFoldAt(e,t,-1)){this.moveCursorTo(n.start.row,n.start.column);return}var r=this.session.getFoldStringAt(e,t,-1);r==null&&(r=this.doc.getLine(e).substring(0,t));var s=i.stringReverse(r),o;this.session.nonTokenRe.lastIndex=0,this.session.tokenRe.lastIndex=0;if(o=this.session.nonTokenRe.exec(s))t-=this.session.nonTokenRe.lastIndex,s=s.slice(this.session.nonTokenRe.lastIndex),this.session.nonTokenRe.lastIndex=0;if(t<=0){this.moveCursorTo(e,0),this.moveCursorLeft(),e>0&&this.moveCursorWordLeft();return}if(o=this.session.tokenRe.exec(s))t-=this.session.tokenRe.lastIndex,this.session.tokenRe.lastIndex=0;this.moveCursorTo(e,t)},this.$shortWordEndIndex=function(e){var t,n=0,r,i=/\\s/,s=this.session.tokenRe;s.lastIndex=0;if(t=this.session.tokenRe.exec(e))n=this.session.tokenRe.lastIndex;else{while((r=e[n])&&i.test(r))n++;if(n<1){s.lastIndex=0;while((r=e[n])&&!s.test(r)){s.lastIndex=0,n++;if(i.test(r)){if(n>2){n--;break}while((r=e[n])&&i.test(r))n++;if(n>2)break}}}}return s.lastIndex=0,n},this.moveCursorShortWordRight=function(){var e=this.lead.row,t=this.lead.column,n=this.doc.getLine(e),r=n.substring(t),i=this.session.getFoldAt(e,t,1);if(i)return this.moveCursorTo(i.end.row,i.end.column);if(t==n.length){var s=this.doc.getLength();do e++,r=this.doc.getLine(e);while(e<s&&/^\\s*$/.test(r));/^\\s+/.test(r)||(r=\"\"),t=0}var o=this.$shortWordEndIndex(r);this.moveCursorTo(e,t+o)},this.moveCursorShortWordLeft=function(){var e=this.lead.row,t=this.lead.column,n;if(n=this.session.getFoldAt(e,t,-1))return this.moveCursorTo(n.start.row,n.start.column);var r=this.session.getLine(e).substring(0,t);if(t===0){do e--,r=this.doc.getLine(e);while(e>0&&/^\\s*$/.test(r));t=r.length,/\\s+$/.test(r)||(r=\"\")}var s=i.stringReverse(r),o=this.$shortWordEndIndex(s);return this.moveCursorTo(e,t-o)},this.moveCursorWordRight=function(){this.session.$selectLongWords?this.moveCursorLongWordRight():this.moveCursorShortWordRight()},this.moveCursorWordLeft=function(){this.session.$selectLongWords?this.moveCursorLongWordLeft():this.moveCursorShortWordLeft()},this.moveCursorBy=function(e,t){var n=this.session.documentToScreenPosition(this.lead.row,this.lead.column);t===0&&(this.$desiredColumn?n.column=this.$desiredColumn:this.$desiredColumn=n.column);var r=this.session.screenToDocumentPosition(n.row+e,n.column);e!==0&&t===0&&r.row===this.lead.row&&r.column===this.lead.column&&this.session.lineWidgets&&this.session.lineWidgets[r.row]&&(r.row>0||e>0)&&r.row++,this.moveCursorTo(r.row,r.column+t,t===0)},this.moveCursorToPosition=function(e){this.moveCursorTo(e.row,e.column)},this.moveCursorTo=function(e,t,n){var r=this.session.getFoldAt(e,t,1);r&&(e=r.start.row,t=r.start.column),this.$keepDesiredColumnOnChange=!0,this.lead.setPosition(e,t),this.$keepDesiredColumnOnChange=!1,n||(this.$desiredColumn=null)},this.moveCursorToScreen=function(e,t,n){var r=this.session.screenToDocumentPosition(e,t);this.moveCursorTo(r.row,r.column,n)},this.detach=function(){this.lead.detach(),this.anchor.detach(),this.session=this.doc=null},this.fromOrientedRange=function(e){this.setSelectionRange(e,e.cursor==e.start),this.$desiredColumn=e.desiredColumn||this.$desiredColumn},this.toOrientedRange=function(e){var t=this.getRange();return e?(e.start.column=t.start.column,e.start.row=t.start.row,e.end.column=t.end.column,e.end.row=t.end.row):e=t,e.cursor=this.isBackwards()?e.start:e.end,e.desiredColumn=this.$desiredColumn,e},this.getRangeOfMovements=function(e){var t=this.getCursor();try{e(this);var n=this.getCursor();return o.fromPoints(t,n)}catch(r){return o.fromPoints(t,t)}finally{this.moveCursorToPosition(t)}},this.toJSON=function(){if(this.rangeCount)var e=this.ranges.map(function(e){var t=e.clone();return t.isBackwards=e.cursor==e.start,t});else{var e=this.getRange();e.isBackwards=this.isBackwards()}return e},this.fromJSON=function(e){if(e.start==undefined){if(this.rangeList){this.toSingleRange(e[0]);for(var t=e.length;t--;){var n=o.fromPoints(e[t].start,e[t].end);e[t].isBackwards&&(n.cursor=n.start),this.addRange(n,!0)}return}e=e[0]}this.rangeList&&this.toSingleRange(e),this.setSelectionRange(e,e.isBackwards)},this.isEqual=function(e){if((e.length||this.rangeCount)&&e.length!=this.rangeCount)return!1;if(!e.length||!this.ranges)return this.getRange().isEqual(e);for(var t=this.ranges.length;t--;)if(!this.ranges[t].isEqual(e[t]))return!1;return!0}}).call(u.prototype),t.Selection=u}),define(\"ace/tokenizer\",[\"require\",\"exports\",\"module\",\"ace/config\"],function(e,t,n){\"use strict\";var r=e(\"./config\"),i=2e3,s=function(e){this.states=e,this.regExps={},this.matchMappings={};for(var t in this.states){var n=this.states[t],r=[],i=0,s=this.matchMappings[t]={defaultToken:\"text\"},o=\"g\",u=[];for(var a=0;a<n.length;a++){var f=n[a];f.defaultToken&&(s.defaultToken=f.defaultToken),f.caseInsensitive&&(o=\"gi\");if(f.regex==null)continue;f.regex instanceof RegExp&&(f.regex=f.regex.toString().slice(1,-1));var l=f.regex,c=(new RegExp(\"(?:(\"+l+\")|(.))\")).exec(\"a\").length-2;Array.isArray(f.token)?f.token.length==1||c==1?f.token=f.token[0]:c-1!=f.token.length?(this.reportError(\"number of classes and regexp groups doesn't match\",{rule:f,groupCount:c-1}),f.token=f.token[0]):(f.tokenArray=f.token,f.token=null,f.onMatch=this.$arrayTokens):typeof f.token==\"function\"&&!f.onMatch&&(c>1?f.onMatch=this.$applyToken:f.onMatch=f.token),c>1&&(/\\\\\\d/.test(f.regex)?l=f.regex.replace(/\\\\([0-9]+)/g,function(e,t){return\"\\\\\"+(parseInt(t,10)+i+1)}):(c=1,l=this.removeCapturingGroups(f.regex)),!f.splitRegex&&typeof f.token!=\"string\"&&u.push(f)),s[i]=a,i+=c,r.push(l),f.onMatch||(f.onMatch=null)}r.length||(s[0]=0,r.push(\"$\")),u.forEach(function(e){e.splitRegex=this.createSplitterRegexp(e.regex,o)},this),this.regExps[t]=new RegExp(\"(\"+r.join(\")|(\")+\")|($)\",o)}};(function(){this.$setMaxTokenCount=function(e){i=e|0},this.$applyToken=function(e){var t=this.splitRegex.exec(e).slice(1),n=this.token.apply(this,t);if(typeof n==\"string\")return[{type:n,value:e}];var r=[];for(var i=0,s=n.length;i<s;i++)t[i]&&(r[r.length]={type:n[i],value:t[i]});return r},this.$arrayTokens=function(e){if(!e)return[];var t=this.splitRegex.exec(e);if(!t)return\"text\";var n=[],r=this.tokenArray;for(var i=0,s=r.length;i<s;i++)t[i+1]&&(n[n.length]={type:r[i],value:t[i+1]});return n},this.removeCapturingGroups=function(e){var t=e.replace(/\\[(?:\\\\.|[^\\]])*?\\]|\\\\.|\\(\\?[:=!]|(\\()/g,function(e,t){return t?\"(?:\":e});return t},this.createSplitterRegexp=function(e,t){if(e.indexOf(\"(?=\")!=-1){var n=0,r=!1,i={};e.replace(/(\\\\.)|(\\((?:\\?[=!])?)|(\\))|([\\[\\]])/g,function(e,t,s,o,u,a){return r?r=u!=\"]\":u?r=!0:o?(n==i.stack&&(i.end=a+1,i.stack=-1),n--):s&&(n++,s.length!=1&&(i.stack=n,i.start=a)),e}),i.end!=null&&/^\\)*$/.test(e.substr(i.end))&&(e=e.substring(0,i.start)+e.substr(i.end))}return e.charAt(0)!=\"^\"&&(e=\"^\"+e),e.charAt(e.length-1)!=\"$\"&&(e+=\"$\"),new RegExp(e,(t||\"\").replace(\"g\",\"\"))},this.getLineTokens=function(e,t){if(t&&typeof t!=\"string\"){var n=t.slice(0);t=n[0],t===\"#tmp\"&&(n.shift(),t=n.shift())}else var n=[];var r=t||\"start\",s=this.states[r];s||(r=\"start\",s=this.states[r]);var o=this.matchMappings[r],u=this.regExps[r];u.lastIndex=0;var a,f=[],l=0,c=0,h={type:null,value:\"\"};while(a=u.exec(e)){var p=o.defaultToken,d=null,v=a[0],m=u.lastIndex;if(m-v.length>l){var g=e.substring(l,m-v.length);h.type==p?h.value+=g:(h.type&&f.push(h),h={type:p,value:g})}for(var y=0;y<a.length-2;y++){if(a[y+1]===undefined)continue;d=s[o[y]],d.onMatch?p=d.onMatch(v,r,n):p=d.token,d.next&&(typeof d.next==\"string\"?r=d.next:r=d.next(r,n),s=this.states[r],s||(this.reportError(\"state doesn't exist\",r),r=\"start\",s=this.states[r]),o=this.matchMappings[r],l=m,u=this.regExps[r],u.lastIndex=m);break}if(v)if(typeof p==\"string\")!!d&&d.merge===!1||h.type!==p?(h.type&&f.push(h),h={type:p,value:v}):h.value+=v;else if(p){h.type&&f.push(h),h={type:null,value:\"\"};for(var y=0;y<p.length;y++)f.push(p[y])}if(l==e.length)break;l=m;if(c++>i){c>2*e.length&&this.reportError(\"infinite loop with in ace tokenizer\",{startState:t,line:e});while(l<e.length)h.type&&f.push(h),h={value:e.substring(l,l+=2e3),type:\"overflow\"};r=\"start\",n=[];break}}return h.type&&f.push(h),n.length>1&&n[0]!==r&&n.unshift(\"#tmp\",r),{tokens:f,state:n.length?n:r}},this.reportError=r.reportError}).call(s.prototype),t.Tokenizer=s}),define(\"ace/mode/text_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../lib/lang\"),i=function(){this.$rules={start:[{token:\"empty_line\",regex:\"^$\"},{defaultToken:\"text\"}]}};(function(){this.addRules=function(e,t){if(!t){for(var n in e)this.$rules[n]=e[n];return}for(var n in e){var r=e[n];for(var i=0;i<r.length;i++){var s=r[i];if(s.next||s.onMatch)typeof s.next==\"string\"&&s.next.indexOf(t)!==0&&(s.next=t+s.next),s.nextState&&s.nextState.indexOf(t)!==0&&(s.nextState=t+s.nextState)}this.$rules[t+n]=r}},this.getRules=function(){return this.$rules},this.embedRules=function(e,t,n,i,s){var o=typeof e==\"function\"?(new e).getRules():e;if(i)for(var u=0;u<i.length;u++)i[u]=t+i[u];else{i=[];for(var a in o)i.push(t+a)}this.addRules(o,t);if(n){var f=Array.prototype[s?\"push\":\"unshift\"];for(var u=0;u<i.length;u++)f.apply(this.$rules[i[u]],r.deepCopy(n))}this.$embeds||(this.$embeds=[]),this.$embeds.push(t)},this.getEmbeds=function(){return this.$embeds};var e=function(e,t){return(e!=\"start\"||t.length)&&t.unshift(this.nextState,e),this.nextState},t=function(e,t){return t.shift(),t.shift()||\"start\"};this.normalizeRules=function(){function i(s){var o=r[s];o.processed=!0;for(var u=0;u<o.length;u++){var a=o[u],f=null;Array.isArray(a)&&(f=a,a={}),!a.regex&&a.start&&(a.regex=a.start,a.next||(a.next=[]),a.next.push({defaultToken:a.token},{token:a.token+\".end\",regex:a.end||a.start,next:\"pop\"}),a.token=a.token+\".start\",a.push=!0);var l=a.next||a.push;if(l&&Array.isArray(l)){var c=a.stateName;c||(c=a.token,typeof c!=\"string\"&&(c=c[0]||\"\"),r[c]&&(c+=n++)),r[c]=l,a.next=c,i(c)}else l==\"pop\"&&(a.next=t);a.push&&(a.nextState=a.next||a.push,a.next=e,delete a.push);if(a.rules)for(var h in a.rules)r[h]?r[h].push&&r[h].push.apply(r[h],a.rules[h]):r[h]=a.rules[h];var p=typeof a==\"string\"?a:typeof a.include==\"string\"?a.include:\"\";p&&(f=r[p]);if(f){var d=[u,1].concat(f);a.noEscape&&(d=d.filter(function(e){return!e.next})),o.splice.apply(o,d),u--}a.keywordMap&&(a.token=this.createKeywordMapper(a.keywordMap,a.defaultToken||\"text\",a.caseInsensitive),delete a.defaultToken)}}var n=0,r=this.$rules;Object.keys(r).forEach(i,this)},this.createKeywordMapper=function(e,t,n,r){var i=Object.create(null);return Object.keys(e).forEach(function(t){var s=e[t];n&&(s=s.toLowerCase());var o=s.split(r||\"|\");for(var u=o.length;u--;)i[o[u]]=t}),Object.getPrototypeOf(i)&&(i.__proto__=null),this.$keywordList=Object.keys(i),e=null,n?function(e){return i[e.toLowerCase()]||t}:function(e){return i[e]||t}},this.getKeywords=function(){return this.$keywords}}).call(i.prototype),t.TextHighlightRules=i}),define(\"ace/mode/behaviour\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(){this.$behaviours={}};(function(){this.add=function(e,t,n){switch(undefined){case this.$behaviours:this.$behaviours={};case this.$behaviours[e]:this.$behaviours[e]={}}this.$behaviours[e][t]=n},this.addBehaviours=function(e){for(var t in e)for(var n in e[t])this.add(t,n,e[t][n])},this.remove=function(e){this.$behaviours&&this.$behaviours[e]&&delete this.$behaviours[e]},this.inherit=function(e,t){if(typeof e==\"function\")var n=(new e).getBehaviours(t);else var n=e.getBehaviours(t);this.addBehaviours(n)},this.getBehaviours=function(e){if(!e)return this.$behaviours;var t={};for(var n=0;n<e.length;n++)this.$behaviours[e[n]]&&(t[e[n]]=this.$behaviours[e[n]]);return t}}).call(r.prototype),t.Behaviour=r}),define(\"ace/token_iterator\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(e,t,n){this.$session=e,this.$row=t,this.$rowTokens=e.getTokens(t);var r=e.getTokenAt(t,n);this.$tokenIndex=r?r.index:-1};(function(){this.stepBackward=function(){this.$tokenIndex-=1;while(this.$tokenIndex<0){this.$row-=1;if(this.$row<0)return this.$row=0,null;this.$rowTokens=this.$session.getTokens(this.$row),this.$tokenIndex=this.$rowTokens.length-1}return this.$rowTokens[this.$tokenIndex]},this.stepForward=function(){this.$tokenIndex+=1;var e;while(this.$tokenIndex>=this.$rowTokens.length){this.$row+=1,e||(e=this.$session.getLength());if(this.$row>=e)return this.$row=e-1,null;this.$rowTokens=this.$session.getTokens(this.$row),this.$tokenIndex=0}return this.$rowTokens[this.$tokenIndex]},this.getCurrentToken=function(){return this.$rowTokens[this.$tokenIndex]},this.getCurrentTokenRow=function(){return this.$row},this.getCurrentTokenColumn=function(){var e=this.$rowTokens,t=this.$tokenIndex,n=e[t].start;if(n!==undefined)return n;n=0;while(t>0)t-=1,n+=e[t].value.length;return n},this.getCurrentTokenPosition=function(){return{row:this.$row,column:this.getCurrentTokenColumn()}}}).call(r.prototype),t.TokenIterator=r}),define(\"ace/mode/behaviour/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/token_iterator\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"../../token_iterator\").TokenIterator,o=e(\"../../lib/lang\"),u=[\"text\",\"paren.rparen\",\"punctuation.operator\"],a=[\"text\",\"paren.rparen\",\"punctuation.operator\",\"comment\"],f,l={},c=function(e){var t=-1;e.multiSelect&&(t=e.selection.index,l.rangeCount!=e.multiSelect.rangeCount&&(l={rangeCount:e.multiSelect.rangeCount}));if(l[t])return f=l[t];f=l[t]={autoInsertedBrackets:0,autoInsertedRow:-1,autoInsertedLineEnd:\"\",maybeInsertedBrackets:0,maybeInsertedRow:-1,maybeInsertedLineStart:\"\",maybeInsertedLineEnd:\"\"}},h=function(e,t,n,r){var i=e.end.row-e.start.row;return{text:n+t+r,selection:[0,e.start.column+1,i,e.end.column+(i?0:1)]}},p=function(){this.add(\"braces\",\"insertion\",function(e,t,n,r,i){var s=n.getCursorPosition(),u=r.doc.getLine(s.row);if(i==\"{\"){c(n);var a=n.getSelectionRange(),l=r.doc.getTextRange(a);if(l!==\"\"&&l!==\"{\"&&n.getWrapBehavioursEnabled())return h(a,l,\"{\",\"}\");if(p.isSaneInsertion(n,r))return/[\\]\\}\\)]/.test(u[s.column])||n.inMultiSelectMode?(p.recordAutoInsert(n,r,\"}\"),{text:\"{}\",selection:[1,1]}):(p.recordMaybeInsert(n,r,\"{\"),{text:\"{\",selection:[1,1]})}else if(i==\"}\"){c(n);var d=u.substring(s.column,s.column+1);if(d==\"}\"){var v=r.$findOpeningBracket(\"}\",{column:s.column+1,row:s.row});if(v!==null&&p.isAutoInsertedClosing(s,u,i))return p.popAutoInsertedClosing(),{text:\"\",selection:[1,1]}}}else{if(i==\"\\n\"||i==\"\\r\\n\"){c(n);var m=\"\";p.isMaybeInsertedClosing(s,u)&&(m=o.stringRepeat(\"}\",f.maybeInsertedBrackets),p.clearMaybeInsertedClosing());var d=u.substring(s.column,s.column+1);if(d===\"}\"){var g=r.findMatchingBracket({row:s.row,column:s.column+1},\"}\");if(!g)return null;var y=this.$getIndent(r.getLine(g.row))}else{if(!m){p.clearMaybeInsertedClosing();return}var y=this.$getIndent(u)}var b=y+r.getTabString();return{text:\"\\n\"+b+\"\\n\"+y+m,selection:[1,b.length,1,b.length]}}p.clearMaybeInsertedClosing()}}),this.add(\"braces\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&s==\"{\"){c(n);var o=r.doc.getLine(i.start.row),u=o.substring(i.end.column,i.end.column+1);if(u==\"}\")return i.end.column++,i;f.maybeInsertedBrackets--}}),this.add(\"parens\",\"insertion\",function(e,t,n,r,i){if(i==\"(\"){c(n);var s=n.getSelectionRange(),o=r.doc.getTextRange(s);if(o!==\"\"&&n.getWrapBehavioursEnabled())return h(s,o,\"(\",\")\");if(p.isSaneInsertion(n,r))return p.recordAutoInsert(n,r,\")\"),{text:\"()\",selection:[1,1]}}else if(i==\")\"){c(n);var u=n.getCursorPosition(),a=r.doc.getLine(u.row),f=a.substring(u.column,u.column+1);if(f==\")\"){var l=r.$findOpeningBracket(\")\",{column:u.column+1,row:u.row});if(l!==null&&p.isAutoInsertedClosing(u,a,i))return p.popAutoInsertedClosing(),{text:\"\",selection:[1,1]}}}}),this.add(\"parens\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&s==\"(\"){c(n);var o=r.doc.getLine(i.start.row),u=o.substring(i.start.column+1,i.start.column+2);if(u==\")\")return i.end.column++,i}}),this.add(\"brackets\",\"insertion\",function(e,t,n,r,i){if(i==\"[\"){c(n);var s=n.getSelectionRange(),o=r.doc.getTextRange(s);if(o!==\"\"&&n.getWrapBehavioursEnabled())return h(s,o,\"[\",\"]\");if(p.isSaneInsertion(n,r))return p.recordAutoInsert(n,r,\"]\"),{text:\"[]\",selection:[1,1]}}else if(i==\"]\"){c(n);var u=n.getCursorPosition(),a=r.doc.getLine(u.row),f=a.substring(u.column,u.column+1);if(f==\"]\"){var l=r.$findOpeningBracket(\"]\",{column:u.column+1,row:u.row});if(l!==null&&p.isAutoInsertedClosing(u,a,i))return p.popAutoInsertedClosing(),{text:\"\",selection:[1,1]}}}}),this.add(\"brackets\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&s==\"[\"){c(n);var o=r.doc.getLine(i.start.row),u=o.substring(i.start.column+1,i.start.column+2);if(u==\"]\")return i.end.column++,i}}),this.add(\"string_dquotes\",\"insertion\",function(e,t,n,r,i){if(i=='\"'||i==\"'\"){if(this.lineCommentStart&&this.lineCommentStart.indexOf(i)!=-1)return;c(n);var s=i,o=n.getSelectionRange(),u=r.doc.getTextRange(o);if(u!==\"\"&&u!==\"'\"&&u!='\"'&&n.getWrapBehavioursEnabled())return h(o,u,s,s);if(!u){var a=n.getCursorPosition(),f=r.doc.getLine(a.row),l=f.substring(a.column-1,a.column),p=f.substring(a.column,a.column+1),d=r.getTokenAt(a.row,a.column),v=r.getTokenAt(a.row,a.column+1);if(l==\"\\\\\"&&d&&/escape/.test(d.type))return null;var m=d&&/string|escape/.test(d.type),g=!v||/string|escape/.test(v.type),y;if(p==s)y=m!==g,y&&/string\\.end/.test(v.type)&&(y=!1);else{if(m&&!g)return null;if(m&&g)return null;var b=r.$mode.tokenRe;b.lastIndex=0;var w=b.test(l);b.lastIndex=0;var E=b.test(l);if(w||E)return null;if(p&&!/[\\s;,.})\\]\\\\]/.test(p))return null;y=!0}return{text:y?s+s:\"\",selection:[1,1]}}}}),this.add(\"string_dquotes\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&(s=='\"'||s==\"'\")){c(n);var o=r.doc.getLine(i.start.row),u=o.substring(i.start.column+1,i.start.column+2);if(u==s)return i.end.column++,i}})};p.isSaneInsertion=function(e,t){var n=e.getCursorPosition(),r=new s(t,n.row,n.column);if(!this.$matchTokenType(r.getCurrentToken()||\"text\",u)){var i=new s(t,n.row,n.column+1);if(!this.$matchTokenType(i.getCurrentToken()||\"text\",u))return!1}return r.stepForward(),r.getCurrentTokenRow()!==n.row||this.$matchTokenType(r.getCurrentToken()||\"text\",a)},p.$matchTokenType=function(e,t){return t.indexOf(e.type||e)>-1},p.recordAutoInsert=function(e,t,n){var r=e.getCursorPosition(),i=t.doc.getLine(r.row);this.isAutoInsertedClosing(r,i,f.autoInsertedLineEnd[0])||(f.autoInsertedBrackets=0),f.autoInsertedRow=r.row,f.autoInsertedLineEnd=n+i.substr(r.column),f.autoInsertedBrackets++},p.recordMaybeInsert=function(e,t,n){var r=e.getCursorPosition(),i=t.doc.getLine(r.row);this.isMaybeInsertedClosing(r,i)||(f.maybeInsertedBrackets=0),f.maybeInsertedRow=r.row,f.maybeInsertedLineStart=i.substr(0,r.column)+n,f.maybeInsertedLineEnd=i.substr(r.column),f.maybeInsertedBrackets++},p.isAutoInsertedClosing=function(e,t,n){return f.autoInsertedBrackets>0&&e.row===f.autoInsertedRow&&n===f.autoInsertedLineEnd[0]&&t.substr(e.column)===f.autoInsertedLineEnd},p.isMaybeInsertedClosing=function(e,t){return f.maybeInsertedBrackets>0&&e.row===f.maybeInsertedRow&&t.substr(e.column)===f.maybeInsertedLineEnd&&t.substr(0,e.column)==f.maybeInsertedLineStart},p.popAutoInsertedClosing=function(){f.autoInsertedLineEnd=f.autoInsertedLineEnd.substr(1),f.autoInsertedBrackets--},p.clearMaybeInsertedClosing=function(){f&&(f.maybeInsertedBrackets=0,f.maybeInsertedRow=-1)},r.inherits(p,i),t.CstyleBehaviour=p}),define(\"ace/unicode\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function r(e){var n=/\\w{4}/g;for(var r in e)t.packages[r]=e[r].replace(n,\"\\\\u$&\")}t.packages={},r({L:\"0041-005A0061-007A00AA00B500BA00C0-00D600D8-00F600F8-02C102C6-02D102E0-02E402EC02EE0370-037403760377037A-037D03860388-038A038C038E-03A103A3-03F503F7-0481048A-05250531-055605590561-058705D0-05EA05F0-05F20621-064A066E066F0671-06D306D506E506E606EE06EF06FA-06FC06FF07100712-072F074D-07A507B107CA-07EA07F407F507FA0800-0815081A082408280904-0939093D09500958-0961097109720979-097F0985-098C098F09900993-09A809AA-09B009B209B6-09B909BD09CE09DC09DD09DF-09E109F009F10A05-0A0A0A0F0A100A13-0A280A2A-0A300A320A330A350A360A380A390A59-0A5C0A5E0A72-0A740A85-0A8D0A8F-0A910A93-0AA80AAA-0AB00AB20AB30AB5-0AB90ABD0AD00AE00AE10B05-0B0C0B0F0B100B13-0B280B2A-0B300B320B330B35-0B390B3D0B5C0B5D0B5F-0B610B710B830B85-0B8A0B8E-0B900B92-0B950B990B9A0B9C0B9E0B9F0BA30BA40BA8-0BAA0BAE-0BB90BD00C05-0C0C0C0E-0C100C12-0C280C2A-0C330C35-0C390C3D0C580C590C600C610C85-0C8C0C8E-0C900C92-0CA80CAA-0CB30CB5-0CB90CBD0CDE0CE00CE10D05-0D0C0D0E-0D100D12-0D280D2A-0D390D3D0D600D610D7A-0D7F0D85-0D960D9A-0DB10DB3-0DBB0DBD0DC0-0DC60E01-0E300E320E330E40-0E460E810E820E840E870E880E8A0E8D0E94-0E970E99-0E9F0EA1-0EA30EA50EA70EAA0EAB0EAD-0EB00EB20EB30EBD0EC0-0EC40EC60EDC0EDD0F000F40-0F470F49-0F6C0F88-0F8B1000-102A103F1050-1055105A-105D106110651066106E-10701075-1081108E10A0-10C510D0-10FA10FC1100-1248124A-124D1250-12561258125A-125D1260-1288128A-128D1290-12B012B2-12B512B8-12BE12C012C2-12C512C8-12D612D8-13101312-13151318-135A1380-138F13A0-13F41401-166C166F-167F1681-169A16A0-16EA1700-170C170E-17111720-17311740-17511760-176C176E-17701780-17B317D717DC1820-18771880-18A818AA18B0-18F51900-191C1950-196D1970-19741980-19AB19C1-19C71A00-1A161A20-1A541AA71B05-1B331B45-1B4B1B83-1BA01BAE1BAF1C00-1C231C4D-1C4F1C5A-1C7D1CE9-1CEC1CEE-1CF11D00-1DBF1E00-1F151F18-1F1D1F20-1F451F48-1F4D1F50-1F571F591F5B1F5D1F5F-1F7D1F80-1FB41FB6-1FBC1FBE1FC2-1FC41FC6-1FCC1FD0-1FD31FD6-1FDB1FE0-1FEC1FF2-1FF41FF6-1FFC2071207F2090-209421022107210A-211321152119-211D212421262128212A-212D212F-2139213C-213F2145-2149214E218321842C00-2C2E2C30-2C5E2C60-2CE42CEB-2CEE2D00-2D252D30-2D652D6F2D80-2D962DA0-2DA62DA8-2DAE2DB0-2DB62DB8-2DBE2DC0-2DC62DC8-2DCE2DD0-2DD62DD8-2DDE2E2F300530063031-3035303B303C3041-3096309D-309F30A1-30FA30FC-30FF3105-312D3131-318E31A0-31B731F0-31FF3400-4DB54E00-9FCBA000-A48CA4D0-A4FDA500-A60CA610-A61FA62AA62BA640-A65FA662-A66EA67F-A697A6A0-A6E5A717-A71FA722-A788A78BA78CA7FB-A801A803-A805A807-A80AA80C-A822A840-A873A882-A8B3A8F2-A8F7A8FBA90A-A925A930-A946A960-A97CA984-A9B2A9CFAA00-AA28AA40-AA42AA44-AA4BAA60-AA76AA7AAA80-AAAFAAB1AAB5AAB6AAB9-AABDAAC0AAC2AADB-AADDABC0-ABE2AC00-D7A3D7B0-D7C6D7CB-D7FBF900-FA2DFA30-FA6DFA70-FAD9FB00-FB06FB13-FB17FB1DFB1F-FB28FB2A-FB36FB38-FB3CFB3EFB40FB41FB43FB44FB46-FBB1FBD3-FD3DFD50-FD8FFD92-FDC7FDF0-FDFBFE70-FE74FE76-FEFCFF21-FF3AFF41-FF5AFF66-FFBEFFC2-FFC7FFCA-FFCFFFD2-FFD7FFDA-FFDC\",Ll:\"0061-007A00AA00B500BA00DF-00F600F8-00FF01010103010501070109010B010D010F01110113011501170119011B011D011F01210123012501270129012B012D012F01310133013501370138013A013C013E014001420144014601480149014B014D014F01510153015501570159015B015D015F01610163016501670169016B016D016F0171017301750177017A017C017E-0180018301850188018C018D019201950199-019B019E01A101A301A501A801AA01AB01AD01B001B401B601B901BA01BD-01BF01C601C901CC01CE01D001D201D401D601D801DA01DC01DD01DF01E101E301E501E701E901EB01ED01EF01F001F301F501F901FB01FD01FF02010203020502070209020B020D020F02110213021502170219021B021D021F02210223022502270229022B022D022F02310233-0239023C023F0240024202470249024B024D024F-02930295-02AF037103730377037B-037D039003AC-03CE03D003D103D5-03D703D903DB03DD03DF03E103E303E503E703E903EB03ED03EF-03F303F503F803FB03FC0430-045F04610463046504670469046B046D046F04710473047504770479047B047D047F0481048B048D048F04910493049504970499049B049D049F04A104A304A504A704A904AB04AD04AF04B104B304B504B704B904BB04BD04BF04C204C404C604C804CA04CC04CE04CF04D104D304D504D704D904DB04DD04DF04E104E304E504E704E904EB04ED04EF04F104F304F504F704F904FB04FD04FF05010503050505070509050B050D050F05110513051505170519051B051D051F0521052305250561-05871D00-1D2B1D62-1D771D79-1D9A1E011E031E051E071E091E0B1E0D1E0F1E111E131E151E171E191E1B1E1D1E1F1E211E231E251E271E291E2B1E2D1E2F1E311E331E351E371E391E3B1E3D1E3F1E411E431E451E471E491E4B1E4D1E4F1E511E531E551E571E591E5B1E5D1E5F1E611E631E651E671E691E6B1E6D1E6F1E711E731E751E771E791E7B1E7D1E7F1E811E831E851E871E891E8B1E8D1E8F1E911E931E95-1E9D1E9F1EA11EA31EA51EA71EA91EAB1EAD1EAF1EB11EB31EB51EB71EB91EBB1EBD1EBF1EC11EC31EC51EC71EC91ECB1ECD1ECF1ED11ED31ED51ED71ED91EDB1EDD1EDF1EE11EE31EE51EE71EE91EEB1EED1EEF1EF11EF31EF51EF71EF91EFB1EFD1EFF-1F071F10-1F151F20-1F271F30-1F371F40-1F451F50-1F571F60-1F671F70-1F7D1F80-1F871F90-1F971FA0-1FA71FB0-1FB41FB61FB71FBE1FC2-1FC41FC61FC71FD0-1FD31FD61FD71FE0-1FE71FF2-1FF41FF61FF7210A210E210F2113212F21342139213C213D2146-2149214E21842C30-2C5E2C612C652C662C682C6A2C6C2C712C732C742C76-2C7C2C812C832C852C872C892C8B2C8D2C8F2C912C932C952C972C992C9B2C9D2C9F2CA12CA32CA52CA72CA92CAB2CAD2CAF2CB12CB32CB52CB72CB92CBB2CBD2CBF2CC12CC32CC52CC72CC92CCB2CCD2CCF2CD12CD32CD52CD72CD92CDB2CDD2CDF2CE12CE32CE42CEC2CEE2D00-2D25A641A643A645A647A649A64BA64DA64FA651A653A655A657A659A65BA65DA65FA663A665A667A669A66BA66DA681A683A685A687A689A68BA68DA68FA691A693A695A697A723A725A727A729A72BA72DA72F-A731A733A735A737A739A73BA73DA73FA741A743A745A747A749A74BA74DA74FA751A753A755A757A759A75BA75DA75FA761A763A765A767A769A76BA76DA76FA771-A778A77AA77CA77FA781A783A785A787A78CFB00-FB06FB13-FB17FF41-FF5A\",Lu:\"0041-005A00C0-00D600D8-00DE01000102010401060108010A010C010E01100112011401160118011A011C011E01200122012401260128012A012C012E01300132013401360139013B013D013F0141014301450147014A014C014E01500152015401560158015A015C015E01600162016401660168016A016C016E017001720174017601780179017B017D018101820184018601870189-018B018E-0191019301940196-0198019C019D019F01A001A201A401A601A701A901AC01AE01AF01B1-01B301B501B701B801BC01C401C701CA01CD01CF01D101D301D501D701D901DB01DE01E001E201E401E601E801EA01EC01EE01F101F401F6-01F801FA01FC01FE02000202020402060208020A020C020E02100212021402160218021A021C021E02200222022402260228022A022C022E02300232023A023B023D023E02410243-02460248024A024C024E03700372037603860388-038A038C038E038F0391-03A103A3-03AB03CF03D2-03D403D803DA03DC03DE03E003E203E403E603E803EA03EC03EE03F403F703F903FA03FD-042F04600462046404660468046A046C046E04700472047404760478047A047C047E0480048A048C048E04900492049404960498049A049C049E04A004A204A404A604A804AA04AC04AE04B004B204B404B604B804BA04BC04BE04C004C104C304C504C704C904CB04CD04D004D204D404D604D804DA04DC04DE04E004E204E404E604E804EA04EC04EE04F004F204F404F604F804FA04FC04FE05000502050405060508050A050C050E05100512051405160518051A051C051E0520052205240531-055610A0-10C51E001E021E041E061E081E0A1E0C1E0E1E101E121E141E161E181E1A1E1C1E1E1E201E221E241E261E281E2A1E2C1E2E1E301E321E341E361E381E3A1E3C1E3E1E401E421E441E461E481E4A1E4C1E4E1E501E521E541E561E581E5A1E5C1E5E1E601E621E641E661E681E6A1E6C1E6E1E701E721E741E761E781E7A1E7C1E7E1E801E821E841E861E881E8A1E8C1E8E1E901E921E941E9E1EA01EA21EA41EA61EA81EAA1EAC1EAE1EB01EB21EB41EB61EB81EBA1EBC1EBE1EC01EC21EC41EC61EC81ECA1ECC1ECE1ED01ED21ED41ED61ED81EDA1EDC1EDE1EE01EE21EE41EE61EE81EEA1EEC1EEE1EF01EF21EF41EF61EF81EFA1EFC1EFE1F08-1F0F1F18-1F1D1F28-1F2F1F38-1F3F1F48-1F4D1F591F5B1F5D1F5F1F68-1F6F1FB8-1FBB1FC8-1FCB1FD8-1FDB1FE8-1FEC1FF8-1FFB21022107210B-210D2110-211221152119-211D212421262128212A-212D2130-2133213E213F214521832C00-2C2E2C602C62-2C642C672C692C6B2C6D-2C702C722C752C7E-2C802C822C842C862C882C8A2C8C2C8E2C902C922C942C962C982C9A2C9C2C9E2CA02CA22CA42CA62CA82CAA2CAC2CAE2CB02CB22CB42CB62CB82CBA2CBC2CBE2CC02CC22CC42CC62CC82CCA2CCC2CCE2CD02CD22CD42CD62CD82CDA2CDC2CDE2CE02CE22CEB2CEDA640A642A644A646A648A64AA64CA64EA650A652A654A656A658A65AA65CA65EA662A664A666A668A66AA66CA680A682A684A686A688A68AA68CA68EA690A692A694A696A722A724A726A728A72AA72CA72EA732A734A736A738A73AA73CA73EA740A742A744A746A748A74AA74CA74EA750A752A754A756A758A75AA75CA75EA760A762A764A766A768A76AA76CA76EA779A77BA77DA77EA780A782A784A786A78BFF21-FF3A\",Lt:\"01C501C801CB01F21F88-1F8F1F98-1F9F1FA8-1FAF1FBC1FCC1FFC\",Lm:\"02B0-02C102C6-02D102E0-02E402EC02EE0374037A0559064006E506E607F407F507FA081A0824082809710E460EC610FC17D718431AA71C78-1C7D1D2C-1D611D781D9B-1DBF2071207F2090-20942C7D2D6F2E2F30053031-3035303B309D309E30FC-30FEA015A4F8-A4FDA60CA67FA717-A71FA770A788A9CFAA70AADDFF70FF9EFF9F\",Lo:\"01BB01C0-01C3029405D0-05EA05F0-05F20621-063F0641-064A066E066F0671-06D306D506EE06EF06FA-06FC06FF07100712-072F074D-07A507B107CA-07EA0800-08150904-0939093D09500958-096109720979-097F0985-098C098F09900993-09A809AA-09B009B209B6-09B909BD09CE09DC09DD09DF-09E109F009F10A05-0A0A0A0F0A100A13-0A280A2A-0A300A320A330A350A360A380A390A59-0A5C0A5E0A72-0A740A85-0A8D0A8F-0A910A93-0AA80AAA-0AB00AB20AB30AB5-0AB90ABD0AD00AE00AE10B05-0B0C0B0F0B100B13-0B280B2A-0B300B320B330B35-0B390B3D0B5C0B5D0B5F-0B610B710B830B85-0B8A0B8E-0B900B92-0B950B990B9A0B9C0B9E0B9F0BA30BA40BA8-0BAA0BAE-0BB90BD00C05-0C0C0C0E-0C100C12-0C280C2A-0C330C35-0C390C3D0C580C590C600C610C85-0C8C0C8E-0C900C92-0CA80CAA-0CB30CB5-0CB90CBD0CDE0CE00CE10D05-0D0C0D0E-0D100D12-0D280D2A-0D390D3D0D600D610D7A-0D7F0D85-0D960D9A-0DB10DB3-0DBB0DBD0DC0-0DC60E01-0E300E320E330E40-0E450E810E820E840E870E880E8A0E8D0E94-0E970E99-0E9F0EA1-0EA30EA50EA70EAA0EAB0EAD-0EB00EB20EB30EBD0EC0-0EC40EDC0EDD0F000F40-0F470F49-0F6C0F88-0F8B1000-102A103F1050-1055105A-105D106110651066106E-10701075-1081108E10D0-10FA1100-1248124A-124D1250-12561258125A-125D1260-1288128A-128D1290-12B012B2-12B512B8-12BE12C012C2-12C512C8-12D612D8-13101312-13151318-135A1380-138F13A0-13F41401-166C166F-167F1681-169A16A0-16EA1700-170C170E-17111720-17311740-17511760-176C176E-17701780-17B317DC1820-18421844-18771880-18A818AA18B0-18F51900-191C1950-196D1970-19741980-19AB19C1-19C71A00-1A161A20-1A541B05-1B331B45-1B4B1B83-1BA01BAE1BAF1C00-1C231C4D-1C4F1C5A-1C771CE9-1CEC1CEE-1CF12135-21382D30-2D652D80-2D962DA0-2DA62DA8-2DAE2DB0-2DB62DB8-2DBE2DC0-2DC62DC8-2DCE2DD0-2DD62DD8-2DDE3006303C3041-3096309F30A1-30FA30FF3105-312D3131-318E31A0-31B731F0-31FF3400-4DB54E00-9FCBA000-A014A016-A48CA4D0-A4F7A500-A60BA610-A61FA62AA62BA66EA6A0-A6E5A7FB-A801A803-A805A807-A80AA80C-A822A840-A873A882-A8B3A8F2-A8F7A8FBA90A-A925A930-A946A960-A97CA984-A9B2AA00-AA28AA40-AA42AA44-AA4BAA60-AA6FAA71-AA76AA7AAA80-AAAFAAB1AAB5AAB6AAB9-AABDAAC0AAC2AADBAADCABC0-ABE2AC00-D7A3D7B0-D7C6D7CB-D7FBF900-FA2DFA30-FA6DFA70-FAD9FB1DFB1F-FB28FB2A-FB36FB38-FB3CFB3EFB40FB41FB43FB44FB46-FBB1FBD3-FD3DFD50-FD8FFD92-FDC7FDF0-FDFBFE70-FE74FE76-FEFCFF66-FF6FFF71-FF9DFFA0-FFBEFFC2-FFC7FFCA-FFCFFFD2-FFD7FFDA-FFDC\",M:\"0300-036F0483-04890591-05BD05BF05C105C205C405C505C70610-061A064B-065E067006D6-06DC06DE-06E406E706E806EA-06ED07110730-074A07A6-07B007EB-07F30816-0819081B-08230825-08270829-082D0900-0903093C093E-094E0951-0955096209630981-098309BC09BE-09C409C709C809CB-09CD09D709E209E30A01-0A030A3C0A3E-0A420A470A480A4B-0A4D0A510A700A710A750A81-0A830ABC0ABE-0AC50AC7-0AC90ACB-0ACD0AE20AE30B01-0B030B3C0B3E-0B440B470B480B4B-0B4D0B560B570B620B630B820BBE-0BC20BC6-0BC80BCA-0BCD0BD70C01-0C030C3E-0C440C46-0C480C4A-0C4D0C550C560C620C630C820C830CBC0CBE-0CC40CC6-0CC80CCA-0CCD0CD50CD60CE20CE30D020D030D3E-0D440D46-0D480D4A-0D4D0D570D620D630D820D830DCA0DCF-0DD40DD60DD8-0DDF0DF20DF30E310E34-0E3A0E47-0E4E0EB10EB4-0EB90EBB0EBC0EC8-0ECD0F180F190F350F370F390F3E0F3F0F71-0F840F860F870F90-0F970F99-0FBC0FC6102B-103E1056-1059105E-10601062-10641067-106D1071-10741082-108D108F109A-109D135F1712-17141732-1734175217531772177317B6-17D317DD180B-180D18A91920-192B1930-193B19B0-19C019C819C91A17-1A1B1A55-1A5E1A60-1A7C1A7F1B00-1B041B34-1B441B6B-1B731B80-1B821BA1-1BAA1C24-1C371CD0-1CD21CD4-1CE81CED1CF21DC0-1DE61DFD-1DFF20D0-20F02CEF-2CF12DE0-2DFF302A-302F3099309AA66F-A672A67CA67DA6F0A6F1A802A806A80BA823-A827A880A881A8B4-A8C4A8E0-A8F1A926-A92DA947-A953A980-A983A9B3-A9C0AA29-AA36AA43AA4CAA4DAA7BAAB0AAB2-AAB4AAB7AAB8AABEAABFAAC1ABE3-ABEAABECABEDFB1EFE00-FE0FFE20-FE26\",Mn:\"0300-036F0483-04870591-05BD05BF05C105C205C405C505C70610-061A064B-065E067006D6-06DC06DF-06E406E706E806EA-06ED07110730-074A07A6-07B007EB-07F30816-0819081B-08230825-08270829-082D0900-0902093C0941-0948094D0951-095509620963098109BC09C1-09C409CD09E209E30A010A020A3C0A410A420A470A480A4B-0A4D0A510A700A710A750A810A820ABC0AC1-0AC50AC70AC80ACD0AE20AE30B010B3C0B3F0B41-0B440B4D0B560B620B630B820BC00BCD0C3E-0C400C46-0C480C4A-0C4D0C550C560C620C630CBC0CBF0CC60CCC0CCD0CE20CE30D41-0D440D4D0D620D630DCA0DD2-0DD40DD60E310E34-0E3A0E47-0E4E0EB10EB4-0EB90EBB0EBC0EC8-0ECD0F180F190F350F370F390F71-0F7E0F80-0F840F860F870F90-0F970F99-0FBC0FC6102D-10301032-10371039103A103D103E10581059105E-10601071-1074108210851086108D109D135F1712-17141732-1734175217531772177317B7-17BD17C617C9-17D317DD180B-180D18A91920-19221927192819321939-193B1A171A181A561A58-1A5E1A601A621A65-1A6C1A73-1A7C1A7F1B00-1B031B341B36-1B3A1B3C1B421B6B-1B731B801B811BA2-1BA51BA81BA91C2C-1C331C361C371CD0-1CD21CD4-1CE01CE2-1CE81CED1DC0-1DE61DFD-1DFF20D0-20DC20E120E5-20F02CEF-2CF12DE0-2DFF302A-302F3099309AA66FA67CA67DA6F0A6F1A802A806A80BA825A826A8C4A8E0-A8F1A926-A92DA947-A951A980-A982A9B3A9B6-A9B9A9BCAA29-AA2EAA31AA32AA35AA36AA43AA4CAAB0AAB2-AAB4AAB7AAB8AABEAABFAAC1ABE5ABE8ABEDFB1EFE00-FE0FFE20-FE26\",Mc:\"0903093E-09400949-094C094E0982098309BE-09C009C709C809CB09CC09D70A030A3E-0A400A830ABE-0AC00AC90ACB0ACC0B020B030B3E0B400B470B480B4B0B4C0B570BBE0BBF0BC10BC20BC6-0BC80BCA-0BCC0BD70C01-0C030C41-0C440C820C830CBE0CC0-0CC40CC70CC80CCA0CCB0CD50CD60D020D030D3E-0D400D46-0D480D4A-0D4C0D570D820D830DCF-0DD10DD8-0DDF0DF20DF30F3E0F3F0F7F102B102C10311038103B103C105610571062-10641067-106D108310841087-108C108F109A-109C17B617BE-17C517C717C81923-19261929-192B193019311933-193819B0-19C019C819C91A19-1A1B1A551A571A611A631A641A6D-1A721B041B351B3B1B3D-1B411B431B441B821BA11BA61BA71BAA1C24-1C2B1C341C351CE11CF2A823A824A827A880A881A8B4-A8C3A952A953A983A9B4A9B5A9BAA9BBA9BD-A9C0AA2FAA30AA33AA34AA4DAA7BABE3ABE4ABE6ABE7ABE9ABEAABEC\",Me:\"0488048906DE20DD-20E020E2-20E4A670-A672\",N:\"0030-003900B200B300B900BC-00BE0660-066906F0-06F907C0-07C90966-096F09E6-09EF09F4-09F90A66-0A6F0AE6-0AEF0B66-0B6F0BE6-0BF20C66-0C6F0C78-0C7E0CE6-0CEF0D66-0D750E50-0E590ED0-0ED90F20-0F331040-10491090-10991369-137C16EE-16F017E0-17E917F0-17F91810-18191946-194F19D0-19DA1A80-1A891A90-1A991B50-1B591BB0-1BB91C40-1C491C50-1C5920702074-20792080-20892150-21822185-21892460-249B24EA-24FF2776-27932CFD30073021-30293038-303A3192-31953220-32293251-325F3280-328932B1-32BFA620-A629A6E6-A6EFA830-A835A8D0-A8D9A900-A909A9D0-A9D9AA50-AA59ABF0-ABF9FF10-FF19\",Nd:\"0030-00390660-066906F0-06F907C0-07C90966-096F09E6-09EF0A66-0A6F0AE6-0AEF0B66-0B6F0BE6-0BEF0C66-0C6F0CE6-0CEF0D66-0D6F0E50-0E590ED0-0ED90F20-0F291040-10491090-109917E0-17E91810-18191946-194F19D0-19DA1A80-1A891A90-1A991B50-1B591BB0-1BB91C40-1C491C50-1C59A620-A629A8D0-A8D9A900-A909A9D0-A9D9AA50-AA59ABF0-ABF9FF10-FF19\",Nl:\"16EE-16F02160-21822185-218830073021-30293038-303AA6E6-A6EF\",No:\"00B200B300B900BC-00BE09F4-09F90BF0-0BF20C78-0C7E0D70-0D750F2A-0F331369-137C17F0-17F920702074-20792080-20892150-215F21892460-249B24EA-24FF2776-27932CFD3192-31953220-32293251-325F3280-328932B1-32BFA830-A835\",P:\"0021-00230025-002A002C-002F003A003B003F0040005B-005D005F007B007D00A100AB00B700BB00BF037E0387055A-055F0589058A05BE05C005C305C605F305F40609060A060C060D061B061E061F066A-066D06D40700-070D07F7-07F90830-083E0964096509700DF40E4F0E5A0E5B0F04-0F120F3A-0F3D0F850FD0-0FD4104A-104F10FB1361-13681400166D166E169B169C16EB-16ED1735173617D4-17D617D8-17DA1800-180A1944194519DE19DF1A1E1A1F1AA0-1AA61AA8-1AAD1B5A-1B601C3B-1C3F1C7E1C7F1CD32010-20272030-20432045-20512053-205E207D207E208D208E2329232A2768-277527C527C627E6-27EF2983-299829D8-29DB29FC29FD2CF9-2CFC2CFE2CFF2E00-2E2E2E302E313001-30033008-30113014-301F3030303D30A030FBA4FEA4FFA60D-A60FA673A67EA6F2-A6F7A874-A877A8CEA8CFA8F8-A8FAA92EA92FA95FA9C1-A9CDA9DEA9DFAA5C-AA5FAADEAADFABEBFD3EFD3FFE10-FE19FE30-FE52FE54-FE61FE63FE68FE6AFE6BFF01-FF03FF05-FF0AFF0C-FF0FFF1AFF1BFF1FFF20FF3B-FF3DFF3FFF5BFF5DFF5F-FF65\",Pd:\"002D058A05BE140018062010-20152E172E1A301C303030A0FE31FE32FE58FE63FF0D\",Ps:\"0028005B007B0F3A0F3C169B201A201E2045207D208D23292768276A276C276E27702772277427C527E627E827EA27EC27EE2983298529872989298B298D298F299129932995299729D829DA29FC2E222E242E262E283008300A300C300E3010301430163018301A301DFD3EFE17FE35FE37FE39FE3BFE3DFE3FFE41FE43FE47FE59FE5BFE5DFF08FF3BFF5BFF5FFF62\",Pe:\"0029005D007D0F3B0F3D169C2046207E208E232A2769276B276D276F27712773277527C627E727E927EB27ED27EF298429862988298A298C298E2990299229942996299829D929DB29FD2E232E252E272E293009300B300D300F3011301530173019301B301E301FFD3FFE18FE36FE38FE3AFE3CFE3EFE40FE42FE44FE48FE5AFE5CFE5EFF09FF3DFF5DFF60FF63\",Pi:\"00AB2018201B201C201F20392E022E042E092E0C2E1C2E20\",Pf:\"00BB2019201D203A2E032E052E0A2E0D2E1D2E21\",Pc:\"005F203F20402054FE33FE34FE4D-FE4FFF3F\",Po:\"0021-00230025-0027002A002C002E002F003A003B003F0040005C00A100B700BF037E0387055A-055F058905C005C305C605F305F40609060A060C060D061B061E061F066A-066D06D40700-070D07F7-07F90830-083E0964096509700DF40E4F0E5A0E5B0F04-0F120F850FD0-0FD4104A-104F10FB1361-1368166D166E16EB-16ED1735173617D4-17D617D8-17DA1800-18051807-180A1944194519DE19DF1A1E1A1F1AA0-1AA61AA8-1AAD1B5A-1B601C3B-1C3F1C7E1C7F1CD3201620172020-20272030-2038203B-203E2041-20432047-205120532055-205E2CF9-2CFC2CFE2CFF2E002E012E06-2E082E0B2E0E-2E162E182E192E1B2E1E2E1F2E2A-2E2E2E302E313001-3003303D30FBA4FEA4FFA60D-A60FA673A67EA6F2-A6F7A874-A877A8CEA8CFA8F8-A8FAA92EA92FA95FA9C1-A9CDA9DEA9DFAA5C-AA5FAADEAADFABEBFE10-FE16FE19FE30FE45FE46FE49-FE4CFE50-FE52FE54-FE57FE5F-FE61FE68FE6AFE6BFF01-FF03FF05-FF07FF0AFF0CFF0EFF0FFF1AFF1BFF1FFF20FF3CFF61FF64FF65\",S:\"0024002B003C-003E005E0060007C007E00A2-00A900AC00AE-00B100B400B600B800D700F702C2-02C502D2-02DF02E5-02EB02ED02EF-02FF03750384038503F604820606-0608060B060E060F06E906FD06FE07F609F209F309FA09FB0AF10B700BF3-0BFA0C7F0CF10CF20D790E3F0F01-0F030F13-0F170F1A-0F1F0F340F360F380FBE-0FC50FC7-0FCC0FCE0FCF0FD5-0FD8109E109F13601390-139917DB194019E0-19FF1B61-1B6A1B74-1B7C1FBD1FBF-1FC11FCD-1FCF1FDD-1FDF1FED-1FEF1FFD1FFE20442052207A-207C208A-208C20A0-20B8210021012103-21062108210921142116-2118211E-2123212521272129212E213A213B2140-2144214A-214D214F2190-2328232B-23E82400-24262440-244A249C-24E92500-26CD26CF-26E126E326E8-26FF2701-27042706-2709270C-27272729-274B274D274F-27522756-275E2761-276727942798-27AF27B1-27BE27C0-27C427C7-27CA27CC27D0-27E527F0-29822999-29D729DC-29FB29FE-2B4C2B50-2B592CE5-2CEA2E80-2E992E9B-2EF32F00-2FD52FF0-2FFB300430123013302030363037303E303F309B309C319031913196-319F31C0-31E33200-321E322A-32503260-327F328A-32B032C0-32FE3300-33FF4DC0-4DFFA490-A4C6A700-A716A720A721A789A78AA828-A82BA836-A839AA77-AA79FB29FDFCFDFDFE62FE64-FE66FE69FF04FF0BFF1C-FF1EFF3EFF40FF5CFF5EFFE0-FFE6FFE8-FFEEFFFCFFFD\",Sm:\"002B003C-003E007C007E00AC00B100D700F703F60606-060820442052207A-207C208A-208C2140-2144214B2190-2194219A219B21A021A321A621AE21CE21CF21D221D421F4-22FF2308-230B23202321237C239B-23B323DC-23E125B725C125F8-25FF266F27C0-27C427C7-27CA27CC27D0-27E527F0-27FF2900-29822999-29D729DC-29FB29FE-2AFF2B30-2B442B47-2B4CFB29FE62FE64-FE66FF0BFF1C-FF1EFF5CFF5EFFE2FFE9-FFEC\",Sc:\"002400A2-00A5060B09F209F309FB0AF10BF90E3F17DB20A0-20B8A838FDFCFE69FF04FFE0FFE1FFE5FFE6\",Sk:\"005E006000A800AF00B400B802C2-02C502D2-02DF02E5-02EB02ED02EF-02FF0375038403851FBD1FBF-1FC11FCD-1FCF1FDD-1FDF1FED-1FEF1FFD1FFE309B309CA700-A716A720A721A789A78AFF3EFF40FFE3\",So:\"00A600A700A900AE00B000B60482060E060F06E906FD06FE07F609FA0B700BF3-0BF80BFA0C7F0CF10CF20D790F01-0F030F13-0F170F1A-0F1F0F340F360F380FBE-0FC50FC7-0FCC0FCE0FCF0FD5-0FD8109E109F13601390-1399194019E0-19FF1B61-1B6A1B74-1B7C210021012103-21062108210921142116-2118211E-2123212521272129212E213A213B214A214C214D214F2195-2199219C-219F21A121A221A421A521A7-21AD21AF-21CD21D021D121D321D5-21F32300-2307230C-231F2322-2328232B-237B237D-239A23B4-23DB23E2-23E82400-24262440-244A249C-24E92500-25B625B8-25C025C2-25F72600-266E2670-26CD26CF-26E126E326E8-26FF2701-27042706-2709270C-27272729-274B274D274F-27522756-275E2761-276727942798-27AF27B1-27BE2800-28FF2B00-2B2F2B452B462B50-2B592CE5-2CEA2E80-2E992E9B-2EF32F00-2FD52FF0-2FFB300430123013302030363037303E303F319031913196-319F31C0-31E33200-321E322A-32503260-327F328A-32B032C0-32FE3300-33FF4DC0-4DFFA490-A4C6A828-A82BA836A837A839AA77-AA79FDFDFFE4FFE8FFEDFFEEFFFCFFFD\",Z:\"002000A01680180E2000-200A20282029202F205F3000\",Zs:\"002000A01680180E2000-200A202F205F3000\",Zl:\"2028\",Zp:\"2029\",C:\"0000-001F007F-009F00AD03780379037F-0383038B038D03A20526-05300557055805600588058B-059005C8-05CF05EB-05EF05F5-0605061C061D0620065F06DD070E070F074B074C07B2-07BF07FB-07FF082E082F083F-08FF093A093B094F095609570973-097809800984098D098E0991099209A909B109B3-09B509BA09BB09C509C609C909CA09CF-09D609D8-09DB09DE09E409E509FC-0A000A040A0B-0A0E0A110A120A290A310A340A370A3A0A3B0A3D0A43-0A460A490A4A0A4E-0A500A52-0A580A5D0A5F-0A650A76-0A800A840A8E0A920AA90AB10AB40ABA0ABB0AC60ACA0ACE0ACF0AD1-0ADF0AE40AE50AF00AF2-0B000B040B0D0B0E0B110B120B290B310B340B3A0B3B0B450B460B490B4A0B4E-0B550B58-0B5B0B5E0B640B650B72-0B810B840B8B-0B8D0B910B96-0B980B9B0B9D0BA0-0BA20BA5-0BA70BAB-0BAD0BBA-0BBD0BC3-0BC50BC90BCE0BCF0BD1-0BD60BD8-0BE50BFB-0C000C040C0D0C110C290C340C3A-0C3C0C450C490C4E-0C540C570C5A-0C5F0C640C650C70-0C770C800C810C840C8D0C910CA90CB40CBA0CBB0CC50CC90CCE-0CD40CD7-0CDD0CDF0CE40CE50CF00CF3-0D010D040D0D0D110D290D3A-0D3C0D450D490D4E-0D560D58-0D5F0D640D650D76-0D780D800D810D840D97-0D990DB20DBC0DBE0DBF0DC7-0DC90DCB-0DCE0DD50DD70DE0-0DF10DF5-0E000E3B-0E3E0E5C-0E800E830E850E860E890E8B0E8C0E8E-0E930E980EA00EA40EA60EA80EA90EAC0EBA0EBE0EBF0EC50EC70ECE0ECF0EDA0EDB0EDE-0EFF0F480F6D-0F700F8C-0F8F0F980FBD0FCD0FD9-0FFF10C6-10CF10FD-10FF1249124E124F12571259125E125F1289128E128F12B112B612B712BF12C112C612C712D7131113161317135B-135E137D-137F139A-139F13F5-13FF169D-169F16F1-16FF170D1715-171F1737-173F1754-175F176D17711774-177F17B417B517DE17DF17EA-17EF17FA-17FF180F181A-181F1878-187F18AB-18AF18F6-18FF191D-191F192C-192F193C-193F1941-1943196E196F1975-197F19AC-19AF19CA-19CF19DB-19DD1A1C1A1D1A5F1A7D1A7E1A8A-1A8F1A9A-1A9F1AAE-1AFF1B4C-1B4F1B7D-1B7F1BAB-1BAD1BBA-1BFF1C38-1C3A1C4A-1C4C1C80-1CCF1CF3-1CFF1DE7-1DFC1F161F171F1E1F1F1F461F471F4E1F4F1F581F5A1F5C1F5E1F7E1F7F1FB51FC51FD41FD51FDC1FF01FF11FF51FFF200B-200F202A-202E2060-206F20722073208F2095-209F20B9-20CF20F1-20FF218A-218F23E9-23FF2427-243F244B-245F26CE26E226E4-26E727002705270A270B2728274C274E2753-2755275F27602795-279727B027BF27CB27CD-27CF2B4D-2B4F2B5A-2BFF2C2F2C5F2CF2-2CF82D26-2D2F2D66-2D6E2D70-2D7F2D97-2D9F2DA72DAF2DB72DBF2DC72DCF2DD72DDF2E32-2E7F2E9A2EF4-2EFF2FD6-2FEF2FFC-2FFF3040309730983100-3104312E-3130318F31B8-31BF31E4-31EF321F32FF4DB6-4DBF9FCC-9FFFA48D-A48FA4C7-A4CFA62C-A63FA660A661A674-A67BA698-A69FA6F8-A6FFA78D-A7FAA82C-A82FA83A-A83FA878-A87FA8C5-A8CDA8DA-A8DFA8FC-A8FFA954-A95EA97D-A97FA9CEA9DA-A9DDA9E0-A9FFAA37-AA3FAA4EAA4FAA5AAA5BAA7C-AA7FAAC3-AADAAAE0-ABBFABEEABEFABFA-ABFFD7A4-D7AFD7C7-D7CAD7FC-F8FFFA2EFA2FFA6EFA6FFADA-FAFFFB07-FB12FB18-FB1CFB37FB3DFB3FFB42FB45FBB2-FBD2FD40-FD4FFD90FD91FDC8-FDEFFDFEFDFFFE1A-FE1FFE27-FE2FFE53FE67FE6C-FE6FFE75FEFD-FF00FFBF-FFC1FFC8FFC9FFD0FFD1FFD8FFD9FFDD-FFDFFFE7FFEF-FFFBFFFEFFFF\",Cc:\"0000-001F007F-009F\",Cf:\"00AD0600-060306DD070F17B417B5200B-200F202A-202E2060-2064206A-206FFEFFFFF9-FFFB\",Co:\"E000-F8FF\",Cs:\"D800-DFFF\",Cn:\"03780379037F-0383038B038D03A20526-05300557055805600588058B-059005C8-05CF05EB-05EF05F5-05FF06040605061C061D0620065F070E074B074C07B2-07BF07FB-07FF082E082F083F-08FF093A093B094F095609570973-097809800984098D098E0991099209A909B109B3-09B509BA09BB09C509C609C909CA09CF-09D609D8-09DB09DE09E409E509FC-0A000A040A0B-0A0E0A110A120A290A310A340A370A3A0A3B0A3D0A43-0A460A490A4A0A4E-0A500A52-0A580A5D0A5F-0A650A76-0A800A840A8E0A920AA90AB10AB40ABA0ABB0AC60ACA0ACE0ACF0AD1-0ADF0AE40AE50AF00AF2-0B000B040B0D0B0E0B110B120B290B310B340B3A0B3B0B450B460B490B4A0B4E-0B550B58-0B5B0B5E0B640B650B72-0B810B840B8B-0B8D0B910B96-0B980B9B0B9D0BA0-0BA20BA5-0BA70BAB-0BAD0BBA-0BBD0BC3-0BC50BC90BCE0BCF0BD1-0BD60BD8-0BE50BFB-0C000C040C0D0C110C290C340C3A-0C3C0C450C490C4E-0C540C570C5A-0C5F0C640C650C70-0C770C800C810C840C8D0C910CA90CB40CBA0CBB0CC50CC90CCE-0CD40CD7-0CDD0CDF0CE40CE50CF00CF3-0D010D040D0D0D110D290D3A-0D3C0D450D490D4E-0D560D58-0D5F0D640D650D76-0D780D800D810D840D97-0D990DB20DBC0DBE0DBF0DC7-0DC90DCB-0DCE0DD50DD70DE0-0DF10DF5-0E000E3B-0E3E0E5C-0E800E830E850E860E890E8B0E8C0E8E-0E930E980EA00EA40EA60EA80EA90EAC0EBA0EBE0EBF0EC50EC70ECE0ECF0EDA0EDB0EDE-0EFF0F480F6D-0F700F8C-0F8F0F980FBD0FCD0FD9-0FFF10C6-10CF10FD-10FF1249124E124F12571259125E125F1289128E128F12B112B612B712BF12C112C612C712D7131113161317135B-135E137D-137F139A-139F13F5-13FF169D-169F16F1-16FF170D1715-171F1737-173F1754-175F176D17711774-177F17DE17DF17EA-17EF17FA-17FF180F181A-181F1878-187F18AB-18AF18F6-18FF191D-191F192C-192F193C-193F1941-1943196E196F1975-197F19AC-19AF19CA-19CF19DB-19DD1A1C1A1D1A5F1A7D1A7E1A8A-1A8F1A9A-1A9F1AAE-1AFF1B4C-1B4F1B7D-1B7F1BAB-1BAD1BBA-1BFF1C38-1C3A1C4A-1C4C1C80-1CCF1CF3-1CFF1DE7-1DFC1F161F171F1E1F1F1F461F471F4E1F4F1F581F5A1F5C1F5E1F7E1F7F1FB51FC51FD41FD51FDC1FF01FF11FF51FFF2065-206920722073208F2095-209F20B9-20CF20F1-20FF218A-218F23E9-23FF2427-243F244B-245F26CE26E226E4-26E727002705270A270B2728274C274E2753-2755275F27602795-279727B027BF27CB27CD-27CF2B4D-2B4F2B5A-2BFF2C2F2C5F2CF2-2CF82D26-2D2F2D66-2D6E2D70-2D7F2D97-2D9F2DA72DAF2DB72DBF2DC72DCF2DD72DDF2E32-2E7F2E9A2EF4-2EFF2FD6-2FEF2FFC-2FFF3040309730983100-3104312E-3130318F31B8-31BF31E4-31EF321F32FF4DB6-4DBF9FCC-9FFFA48D-A48FA4C7-A4CFA62C-A63FA660A661A674-A67BA698-A69FA6F8-A6FFA78D-A7FAA82C-A82FA83A-A83FA878-A87FA8C5-A8CDA8DA-A8DFA8FC-A8FFA954-A95EA97D-A97FA9CEA9DA-A9DDA9E0-A9FFAA37-AA3FAA4EAA4FAA5AAA5BAA7C-AA7FAAC3-AADAAAE0-ABBFABEEABEFABFA-ABFFD7A4-D7AFD7C7-D7CAD7FC-D7FFFA2EFA2FFA6EFA6FFADA-FAFFFB07-FB12FB18-FB1CFB37FB3DFB3FFB42FB45FBB2-FBD2FD40-FD4FFD90FD91FDC8-FDEFFDFEFDFFFE1A-FE1FFE27-FE2FFE53FE67FE6C-FE6FFE75FEFDFEFEFF00FFBF-FFC1FFC8FFC9FFD0FFD1FFD8FFD9FFDD-FFDFFFE7FFEF-FFF8FFFEFFFF\"})}),define(\"ace/mode/text\",[\"require\",\"exports\",\"module\",\"ace/tokenizer\",\"ace/mode/text_highlight_rules\",\"ace/mode/behaviour/cstyle\",\"ace/unicode\",\"ace/lib/lang\",\"ace/token_iterator\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../tokenizer\").Tokenizer,i=e(\"./text_highlight_rules\").TextHighlightRules,s=e(\"./behaviour/cstyle\").CstyleBehaviour,o=e(\"../unicode\"),u=e(\"../lib/lang\"),a=e(\"../token_iterator\").TokenIterator,f=e(\"../range\").Range,l=function(){this.HighlightRules=i};(function(){this.$defaultBehaviour=new s,this.tokenRe=new RegExp(\"^[\"+o.packages.L+o.packages.Mn+o.packages.Mc+o.packages.Nd+o.packages.Pc+\"\\\\$_]+\",\"g\"),this.nonTokenRe=new RegExp(\"^(?:[^\"+o.packages.L+o.packages.Mn+o.packages.Mc+o.packages.Nd+o.packages.Pc+\"\\\\$_]|\\\\s])+\",\"g\"),this.getTokenizer=function(){return this.$tokenizer||(this.$highlightRules=this.$highlightRules||new this.HighlightRules(this.$highlightRuleConfig),this.$tokenizer=new r(this.$highlightRules.getRules())),this.$tokenizer},this.lineCommentStart=\"\",this.blockComment=\"\",this.toggleCommentLines=function(e,t,n,r){function w(e){for(var t=n;t<=r;t++)e(i.getLine(t),t)}var i=t.doc,s=!0,o=!0,a=Infinity,f=t.getTabSize(),l=!1;if(!this.lineCommentStart){if(!this.blockComment)return!1;var c=this.blockComment.start,h=this.blockComment.end,p=new RegExp(\"^(\\\\s*)(?:\"+u.escapeRegExp(c)+\")\"),d=new RegExp(\"(?:\"+u.escapeRegExp(h)+\")\\\\s*$\"),v=function(e,t){if(g(e,t))return;if(!s||/\\S/.test(e))i.insertInLine({row:t,column:e.length},h),i.insertInLine({row:t,column:a},c)},m=function(e,t){var n;(n=e.match(d))&&i.removeInLine(t,e.length-n[0].length,e.length),(n=e.match(p))&&i.removeInLine(t,n[1].length,n[0].length)},g=function(e,n){if(p.test(e))return!0;var r=t.getTokens(n);for(var i=0;i<r.length;i++)if(r[i].type===\"comment\")return!0}}else{if(Array.isArray(this.lineCommentStart))var p=this.lineCommentStart.map(u.escapeRegExp).join(\"|\"),c=this.lineCommentStart[0];else var p=u.escapeRegExp(this.lineCommentStart),c=this.lineCommentStart;p=new RegExp(\"^(\\\\s*)(?:\"+p+\") ?\"),l=t.getUseSoftTabs();var m=function(e,t){var n=e.match(p);if(!n)return;var r=n[1].length,s=n[0].length;!b(e,r,s)&&n[0][s-1]==\" \"&&s--,i.removeInLine(t,r,s)},y=c+\" \",v=function(e,t){if(!s||/\\S/.test(e))b(e,a,a)?i.insertInLine({row:t,column:a},y):i.insertInLine({row:t,column:a},c)},g=function(e,t){return p.test(e)},b=function(e,t,n){var r=0;while(t--&&e.charAt(t)==\" \")r++;if(r%f!=0)return!1;var r=0;while(e.charAt(n++)==\" \")r++;return f>2?r%f!=f-1:r%f==0}}var E=Infinity;w(function(e,t){var n=e.search(/\\S/);n!==-1?(n<a&&(a=n),o&&!g(e,t)&&(o=!1)):E>e.length&&(E=e.length)}),a==Infinity&&(a=E,s=!1,o=!1),l&&a%f!=0&&(a=Math.floor(a/f)*f),w(o?m:v)},this.toggleBlockComment=function(e,t,n,r){var i=this.blockComment;if(!i)return;!i.start&&i[0]&&(i=i[0]);var s=new a(t,r.row,r.column),o=s.getCurrentToken(),u=t.selection,l=t.selection.toOrientedRange(),c,h;if(o&&/comment/.test(o.type)){var p,d;while(o&&/comment/.test(o.type)){var v=o.value.indexOf(i.start);if(v!=-1){var m=s.getCurrentTokenRow(),g=s.getCurrentTokenColumn()+v;p=new f(m,g,m,g+i.start.length);break}o=s.stepBackward()}var s=new a(t,r.row,r.column),o=s.getCurrentToken();while(o&&/comment/.test(o.type)){var v=o.value.indexOf(i.end);if(v!=-1){var m=s.getCurrentTokenRow(),g=s.getCurrentTokenColumn()+v;d=new f(m,g,m,g+i.end.length);break}o=s.stepForward()}d&&t.remove(d),p&&(t.remove(p),c=p.start.row,h=-i.start.length)}else h=i.start.length,c=n.start.row,t.insert(n.end,i.end),t.insert(n.start,i.start);l.start.row==c&&(l.start.column+=h),l.end.row==c&&(l.end.column+=h),t.selection.fromOrientedRange(l)},this.getNextLineIndent=function(e,t,n){return this.$getIndent(t)},this.checkOutdent=function(e,t,n){return!1},this.autoOutdent=function(e,t,n){},this.$getIndent=function(e){return e.match(/^\\s*/)[0]},this.createWorker=function(e){return null},this.createModeDelegates=function(e){this.$embeds=[],this.$modes={};for(var t in e)e[t]&&(this.$embeds.push(t),this.$modes[t]=new e[t]);var n=[\"toggleBlockComment\",\"toggleCommentLines\",\"getNextLineIndent\",\"checkOutdent\",\"autoOutdent\",\"transformAction\",\"getCompletions\"];for(var t=0;t<n.length;t++)(function(e){var r=n[t],i=e[r];e[n[t]]=function(){return this.$delegator(r,arguments,i)}})(this)},this.$delegator=function(e,t,n){var r=t[0];typeof r!=\"string\"&&(r=r[0]);for(var i=0;i<this.$embeds.length;i++){if(!this.$modes[this.$embeds[i]])continue;var s=r.split(this.$embeds[i]);if(!s[0]&&s[1]){t[0]=s[1];var o=this.$modes[this.$embeds[i]];return o[e].apply(o,t)}}var u=n.apply(this,t);return n?u:undefined},this.transformAction=function(e,t,n,r,i){if(this.$behaviour){var s=this.$behaviour.getBehaviours();for(var o in s)if(s[o][t]){var u=s[o][t].apply(this,arguments);if(u)return u}}},this.getKeywords=function(e){if(!this.completionKeywords){var t=this.$tokenizer.rules,n=[];for(var r in t){var i=t[r];for(var s=0,o=i.length;s<o;s++)if(typeof i[s].token==\"string\")/keyword|support|storage/.test(i[s].token)&&n.push(i[s].regex);else if(typeof i[s].token==\"object\")for(var u=0,a=i[s].token.length;u<a;u++)if(/keyword|support|storage/.test(i[s].token[u])){var r=i[s].regex.match(/\\(.+?\\)/g)[u];n.push(r.substr(1,r.length-2))}}this.completionKeywords=n}return e?n.concat(this.$keywordList||[]):this.$keywordList},this.$createKeywordList=function(){return this.$highlightRules||this.getTokenizer(),this.$keywordList=this.$highlightRules.$keywordList||[]},this.getCompletions=function(e,t,n,r){var i=this.$keywordList||this.$createKeywordList();return i.map(function(e){return{name:e,value:e,score:0,meta:\"keyword\"}})},this.$id=\"ace/mode/text\"}).call(l.prototype),t.Mode=l}),define(\"ace/apply_delta\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function r(e,t){throw console.log(\"Invalid Delta:\",e),\"Invalid Delta: \"+t}function i(e,t){return t.row>=0&&t.row<e.length&&t.column>=0&&t.column<=e[t.row].length}function s(e,t){t.action!=\"insert\"&&t.action!=\"remove\"&&r(t,\"delta.action must be 'insert' or 'remove'\"),t.lines instanceof Array||r(t,\"delta.lines must be an Array\"),(!t.start||!t.end)&&r(t,\"delta.start/end must be an present\");var n=t.start;i(e,t.start)||r(t,\"delta.start must be contained in document\");var s=t.end;t.action==\"remove\"&&!i(e,s)&&r(t,\"delta.end must contained in document for 'remove' actions\");var o=s.row-n.row,u=s.column-(o==0?n.column:0);(o!=t.lines.length-1||t.lines[o].length!=u)&&r(t,\"delta.range must match delta lines\")}t.applyDelta=function(e,t,n){var r=t.start.row,i=t.start.column,s=e[r]||\"\";switch(t.action){case\"insert\":var o=t.lines;if(o.length===1)e[r]=s.substring(0,i)+t.lines[0]+s.substring(i);else{var u=[r,1].concat(t.lines);e.splice.apply(e,u),e[r]=s.substring(0,i)+e[r],e[r+t.lines.length-1]+=s.substring(i)}break;case\"remove\":var a=t.end.column,f=t.end.row;r===f?e[r]=s.substring(0,i)+s.substring(a):e.splice(r,f-r+1,s.substring(0,i)+e[f].substring(a))}}}),define(\"ace/anchor\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/event_emitter\").EventEmitter,s=t.Anchor=function(e,t,n){this.$onChange=this.onChange.bind(this),this.attach(e),typeof n==\"undefined\"?this.setPosition(t.row,t.column):this.setPosition(t,n)};(function(){function e(e,t,n){var r=n?e.column<=t.column:e.column<t.column;return e.row<t.row||e.row==t.row&&r}function t(t,n,r){var i=t.action==\"insert\",s=(i?1:-1)*(t.end.row-t.start.row),o=(i?1:-1)*(t.end.column-t.start.column),u=t.start,a=i?u:t.end;return e(n,u,r)?{row:n.row,column:n.column}:e(a,n,!r)?{row:n.row+s,column:n.column+(n.row==a.row?o:0)}:{row:u.row,column:u.column}}r.implement(this,i),this.getPosition=function(){return this.$clipPositionToDocument(this.row,this.column)},this.getDocument=function(){return this.document},this.$insertRight=!1,this.onChange=function(e){if(e.start.row==e.end.row&&e.start.row!=this.row)return;if(e.start.row>this.row)return;var n=t(e,{row:this.row,column:this.column},this.$insertRight);this.setPosition(n.row,n.column,!0)},this.setPosition=function(e,t,n){var r;n?r={row:e,column:t}:r=this.$clipPositionToDocument(e,t);if(this.row==r.row&&this.column==r.column)return;var i={row:this.row,column:this.column};this.row=r.row,this.column=r.column,this._signal(\"change\",{old:i,value:r})},this.detach=function(){this.document.removeEventListener(\"change\",this.$onChange)},this.attach=function(e){this.document=e||this.document,this.document.on(\"change\",this.$onChange)},this.$clipPositionToDocument=function(e,t){var n={};return e>=this.document.getLength()?(n.row=Math.max(0,this.document.getLength()-1),n.column=this.document.getLine(n.row).length):e<0?(n.row=0,n.column=0):(n.row=e,n.column=Math.min(this.document.getLine(n.row).length,Math.max(0,t))),t<0&&(n.column=0),n}}).call(s.prototype)}),define(\"ace/document\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/apply_delta\",\"ace/lib/event_emitter\",\"ace/range\",\"ace/anchor\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./apply_delta\").applyDelta,s=e(\"./lib/event_emitter\").EventEmitter,o=e(\"./range\").Range,u=e(\"./anchor\").Anchor,a=function(e){this.$lines=[\"\"],e.length===0?this.$lines=[\"\"]:Array.isArray(e)?this.insertMergedLines({row:0,column:0},e):this.insert({row:0,column:0},e)};(function(){r.implement(this,s),this.setValue=function(e){var t=this.getLength()-1;this.remove(new o(0,0,t,this.getLine(t).length)),this.insert({row:0,column:0},e)},this.getValue=function(){return this.getAllLines().join(this.getNewLineCharacter())},this.createAnchor=function(e,t){return new u(this,e,t)},\"aaa\".split(/a/).length===0?this.$split=function(e){return e.replace(/\\r\\n|\\r/g,\"\\n\").split(\"\\n\")}:this.$split=function(e){return e.split(/\\r\\n|\\r|\\n/)},this.$detectNewLine=function(e){var t=e.match(/^.*?(\\r\\n|\\r|\\n)/m);this.$autoNewLine=t?t[1]:\"\\n\",this._signal(\"changeNewLineMode\")},this.getNewLineCharacter=function(){switch(this.$newLineMode){case\"windows\":return\"\\r\\n\";case\"unix\":return\"\\n\";default:return this.$autoNewLine||\"\\n\"}},this.$autoNewLine=\"\",this.$newLineMode=\"auto\",this.setNewLineMode=function(e){if(this.$newLineMode===e)return;this.$newLineMode=e,this._signal(\"changeNewLineMode\")},this.getNewLineMode=function(){return this.$newLineMode},this.isNewLine=function(e){return e==\"\\r\\n\"||e==\"\\r\"||e==\"\\n\"},this.getLine=function(e){return this.$lines[e]||\"\"},this.getLines=function(e,t){return this.$lines.slice(e,t+1)},this.getAllLines=function(){return this.getLines(0,this.getLength())},this.getLength=function(){return this.$lines.length},this.getTextRange=function(e){return this.getLinesForRange(e).join(this.getNewLineCharacter())},this.getLinesForRange=function(e){var t;if(e.start.row===e.end.row)t=[this.getLine(e.start.row).substring(e.start.column,e.end.column)];else{t=this.getLines(e.start.row,e.end.row),t[0]=(t[0]||\"\").substring(e.start.column);var n=t.length-1;e.end.row-e.start.row==n&&(t[n]=t[n].substring(0,e.end.column))}return t},this.insertLines=function(e,t){return console.warn(\"Use of document.insertLines is deprecated. Use the insertFullLines method instead.\"),this.insertFullLines(e,t)},this.removeLines=function(e,t){return console.warn(\"Use of document.removeLines is deprecated. Use the removeFullLines method instead.\"),this.removeFullLines(e,t)},this.insertNewLine=function(e){return console.warn(\"Use of document.insertNewLine is deprecated. Use insertMergedLines(position, ['', '']) instead.\"),this.insertMergedLines(e,[\"\",\"\"])},this.insert=function(e,t){return this.getLength()<=1&&this.$detectNewLine(t),this.insertMergedLines(e,this.$split(t))},this.insertInLine=function(e,t){var n=this.clippedPos(e.row,e.column),r=this.pos(e.row,e.column+t.length);return this.applyDelta({start:n,end:r,action:\"insert\",lines:[t]},!0),this.clonePos(r)},this.clippedPos=function(e,t){var n=this.getLength();e===undefined?e=n:e<0?e=0:e>=n&&(e=n-1,t=undefined);var r=this.getLine(e);return t==undefined&&(t=r.length),t=Math.min(Math.max(t,0),r.length),{row:e,column:t}},this.clonePos=function(e){return{row:e.row,column:e.column}},this.pos=function(e,t){return{row:e,column:t}},this.$clipPosition=function(e){var t=this.getLength();return e.row>=t?(e.row=Math.max(0,t-1),e.column=this.getLine(t-1).length):(e.row=Math.max(0,e.row),e.column=Math.min(Math.max(e.column,0),this.getLine(e.row).length)),e},this.insertFullLines=function(e,t){e=Math.min(Math.max(e,0),this.getLength());var n=0;e<this.getLength()?(t=t.concat([\"\"]),n=0):(t=[\"\"].concat(t),e--,n=this.$lines[e].length),this.insertMergedLines({row:e,column:n},t)},this.insertMergedLines=function(e,t){var n=this.clippedPos(e.row,e.column),r={row:n.row+t.length-1,column:(t.length==1?n.column:0)+t[t.length-1].length};return this.applyDelta({start:n,end:r,action:\"insert\",lines:t}),this.clonePos(r)},this.remove=function(e){var t=this.clippedPos(e.start.row,e.start.column),n=this.clippedPos(e.end.row,e.end.column);return this.applyDelta({start:t,end:n,action:\"remove\",lines:this.getLinesForRange({start:t,end:n})}),this.clonePos(t)},this.removeInLine=function(e,t,n){var r=this.clippedPos(e,t),i=this.clippedPos(e,n);return this.applyDelta({start:r,end:i,action:\"remove\",lines:this.getLinesForRange({start:r,end:i})},!0),this.clonePos(r)},this.removeFullLines=function(e,t){e=Math.min(Math.max(0,e),this.getLength()-1),t=Math.min(Math.max(0,t),this.getLength()-1);var n=t==this.getLength()-1&&e>0,r=t<this.getLength()-1,i=n?e-1:e,s=n?this.getLine(i).length:0,u=r?t+1:t,a=r?0:this.getLine(u).length,f=new o(i,s,u,a),l=this.$lines.slice(e,t+1);return this.applyDelta({start:f.start,end:f.end,action:\"remove\",lines:this.getLinesForRange(f)}),l},this.removeNewLine=function(e){e<this.getLength()-1&&e>=0&&this.applyDelta({start:this.pos(e,this.getLine(e).length),end:this.pos(e+1,0),action:\"remove\",lines:[\"\",\"\"]})},this.replace=function(e,t){e instanceof o||(e=o.fromPoints(e.start,e.end));if(t.length===0&&e.isEmpty())return e.start;if(t==this.getTextRange(e))return e.end;this.remove(e);var n;return t?n=this.insert(e.start,t):n=e.start,n},this.applyDeltas=function(e){for(var t=0;t<e.length;t++)this.applyDelta(e[t])},this.revertDeltas=function(e){for(var t=e.length-1;t>=0;t--)this.revertDelta(e[t])},this.applyDelta=function(e,t){var n=e.action==\"insert\";if(n?e.lines.length<=1&&!e.lines[0]:!o.comparePoints(e.start,e.end))return;n&&e.lines.length>2e4&&this.$splitAndapplyLargeDelta(e,2e4),i(this.$lines,e,t),this._signal(\"change\",e)},this.$splitAndapplyLargeDelta=function(e,t){var n=e.lines,r=n.length,i=e.start.row,s=e.start.column,o=0,u=0;do{o=u,u+=t-1;var a=n.slice(o,u);if(u>r){e.lines=a,e.start.row=i+o,e.start.column=s;break}a.push(\"\"),this.applyDelta({start:this.pos(i+o,s),end:this.pos(i+u,s=0),action:e.action,lines:a},!0)}while(!0)},this.revertDelta=function(e){this.applyDelta({start:this.clonePos(e.start),end:this.clonePos(e.end),action:e.action==\"insert\"?\"remove\":\"insert\",lines:e.lines.slice()})},this.indexToPosition=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length;for(var i=t||0,s=n.length;i<s;i++){e-=n[i].length+r;if(e<0)return{row:i,column:e+n[i].length+r}}return{row:s-1,column:n[s-1].length}},this.positionToIndex=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length,i=0,s=Math.min(e.row,n.length);for(var o=t||0;o<s;++o)i+=n[o].length+r;return i+e.column}}).call(a.prototype),t.Document=a}),define(\"ace/background_tokenizer\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/event_emitter\").EventEmitter,s=function(e,t){this.running=!1,this.lines=[],this.states=[],this.currentLine=0,this.tokenizer=e;var n=this;this.$worker=function(){if(!n.running)return;var e=new Date,t=n.currentLine,r=-1,i=n.doc,s=t;while(n.lines[t])t++;var o=i.getLength(),u=0;n.running=!1;while(t<o){n.$tokenizeRow(t),r=t;do t++;while(n.lines[t]);u++;if(u%5===0&&new Date-e>20){n.running=setTimeout(n.$worker,20);break}}n.currentLine=t,s<=r&&n.fireUpdateEvent(s,r)}};(function(){r.implement(this,i),this.setTokenizer=function(e){this.tokenizer=e,this.lines=[],this.states=[],this.start(0)},this.setDocument=function(e){this.doc=e,this.lines=[],this.states=[],this.stop()},this.fireUpdateEvent=function(e,t){var n={first:e,last:t};this._signal(\"update\",{data:n})},this.start=function(e){this.currentLine=Math.min(e||0,this.currentLine,this.doc.getLength()),this.lines.splice(this.currentLine,this.lines.length),this.states.splice(this.currentLine,this.states.length),this.stop(),this.running=setTimeout(this.$worker,700)},this.scheduleStart=function(){this.running||(this.running=setTimeout(this.$worker,700))},this.$updateOnChange=function(e){var t=e.start.row,n=e.end.row-t;if(n===0)this.lines[t]=null;else if(e.action==\"remove\")this.lines.splice(t,n+1,null),this.states.splice(t,n+1,null);else{var r=Array(n+1);r.unshift(t,1),this.lines.splice.apply(this.lines,r),this.states.splice.apply(this.states,r)}this.currentLine=Math.min(t,this.currentLine,this.doc.getLength()),this.stop()},this.stop=function(){this.running&&clearTimeout(this.running),this.running=!1},this.getTokens=function(e){return this.lines[e]||this.$tokenizeRow(e)},this.getState=function(e){return this.currentLine==e&&this.$tokenizeRow(e),this.states[e]||\"start\"},this.$tokenizeRow=function(e){var t=this.doc.getLine(e),n=this.states[e-1],r=this.tokenizer.getLineTokens(t,n,e);return this.states[e]+\"\"!=r.state+\"\"?(this.states[e]=r.state,this.lines[e+1]=null,this.currentLine>e+1&&(this.currentLine=e+1)):this.currentLine==e&&(this.currentLine=e+1),this.lines[e]=r.tokens}}).call(s.prototype),t.BackgroundTokenizer=s}),define(\"ace/search_highlight\",[\"require\",\"exports\",\"module\",\"ace/lib/lang\",\"ace/lib/oop\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"./lib/lang\"),i=e(\"./lib/oop\"),s=e(\"./range\").Range,o=function(e,t,n){this.setRegexp(e),this.clazz=t,this.type=n||\"text\"};(function(){this.MAX_RANGES=500,this.setRegexp=function(e){if(this.regExp+\"\"==e+\"\")return;this.regExp=e,this.cache=[]},this.update=function(e,t,n,i){if(!this.regExp)return;var o=i.firstRow,u=i.lastRow;for(var a=o;a<=u;a++){var f=this.cache[a];f==null&&(f=r.getMatchOffsets(n.getLine(a),this.regExp),f.length>this.MAX_RANGES&&(f=f.slice(0,this.MAX_RANGES)),f=f.map(function(e){return new s(a,e.offset,a,e.offset+e.length)}),this.cache[a]=f.length?f:\"\");for(var l=f.length;l--;)t.drawSingleLineMarker(e,f[l].toScreenRange(n),this.clazz,i)}}}).call(o.prototype),t.SearchHighlight=o}),define(\"ace/edit_session/fold_line\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";function i(e,t){this.foldData=e,Array.isArray(t)?this.folds=t:t=this.folds=[t];var n=t[t.length-1];this.range=new r(t[0].start.row,t[0].start.column,n.end.row,n.end.column),this.start=this.range.start,this.end=this.range.end,this.folds.forEach(function(e){e.setFoldLine(this)},this)}var r=e(\"../range\").Range;(function(){this.shiftRow=function(e){this.start.row+=e,this.end.row+=e,this.folds.forEach(function(t){t.start.row+=e,t.end.row+=e})},this.addFold=function(e){if(e.sameRow){if(e.start.row<this.startRow||e.endRow>this.endRow)throw new Error(\"Can't add a fold to this FoldLine as it has no connection\");this.folds.push(e),this.folds.sort(function(e,t){return-e.range.compareEnd(t.start.row,t.start.column)}),this.range.compareEnd(e.start.row,e.start.column)>0?(this.end.row=e.end.row,this.end.column=e.end.column):this.range.compareStart(e.end.row,e.end.column)<0&&(this.start.row=e.start.row,this.start.column=e.start.column)}else if(e.start.row==this.end.row)this.folds.push(e),this.end.row=e.end.row,this.end.column=e.end.column;else{if(e.end.row!=this.start.row)throw new Error(\"Trying to add fold to FoldRow that doesn't have a matching row\");this.folds.unshift(e),this.start.row=e.start.row,this.start.column=e.start.column}e.foldLine=this},this.containsRow=function(e){return e>=this.start.row&&e<=this.end.row},this.walk=function(e,t,n){var r=0,i=this.folds,s,o,u,a=!0;t==null&&(t=this.end.row,n=this.end.column);for(var f=0;f<i.length;f++){s=i[f],o=s.range.compareStart(t,n);if(o==-1){e(null,t,n,r,a);return}u=e(null,s.start.row,s.start.column,r,a),u=!u&&e(s.placeholder,s.start.row,s.start.column,r);if(u||o===0)return;a=!s.sameRow,r=s.end.column}e(null,t,n,r,a)},this.getNextFoldTo=function(e,t){var n,r;for(var i=0;i<this.folds.length;i++){n=this.folds[i],r=n.range.compareEnd(e,t);if(r==-1)return{fold:n,kind:\"after\"};if(r===0)return{fold:n,kind:\"inside\"}}return null},this.addRemoveChars=function(e,t,n){var r=this.getNextFoldTo(e,t),i,s;if(r){i=r.fold;if(r.kind==\"inside\"&&i.start.column!=t&&i.start.row!=e)window.console&&window.console.log(e,t,i);else if(i.start.row==e){s=this.folds;var o=s.indexOf(i);o===0&&(this.start.column+=n);for(o;o<s.length;o++){i=s[o],i.start.column+=n;if(!i.sameRow)return;i.end.column+=n}this.end.column+=n}}},this.split=function(e,t){var n=this.getNextFoldTo(e,t);if(!n||n.kind==\"inside\")return null;var r=n.fold,s=this.folds,o=this.foldData,u=s.indexOf(r),a=s[u-1];this.end.row=a.end.row,this.end.column=a.end.column,s=s.splice(u,s.length-u);var f=new i(o,s);return o.splice(o.indexOf(this)+1,0,f),f},this.merge=function(e){var t=e.folds;for(var n=0;n<t.length;n++)this.addFold(t[n]);var r=this.foldData;r.splice(r.indexOf(e),1)},this.toString=function(){var e=[this.range.toString()+\": [\"];return this.folds.forEach(function(t){e.push(\"  \"+t.toString())}),e.push(\"]\"),e.join(\"\\n\")},this.idxToPosition=function(e){var t=0;for(var n=0;n<this.folds.length;n++){var r=this.folds[n];e-=r.start.column-t;if(e<0)return{row:r.start.row,column:r.start.column+e};e-=r.placeholder.length;if(e<0)return r.start;t=r.end.column}return{row:this.end.row,column:this.end.column+e}}}).call(i.prototype),t.FoldLine=i}),define(\"ace/range_list\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"./range\").Range,i=r.comparePoints,s=function(){this.ranges=[]};(function(){this.comparePoints=i,this.pointIndex=function(e,t,n){var r=this.ranges;for(var s=n||0;s<r.length;s++){var o=r[s],u=i(e,o.end);if(u>0)continue;var a=i(e,o.start);return u===0?t&&a!==0?-s-2:s:a>0||a===0&&!t?s:-s-1}return-s-1},this.add=function(e){var t=!e.isEmpty(),n=this.pointIndex(e.start,t);n<0&&(n=-n-1);var r=this.pointIndex(e.end,t,n);return r<0?r=-r-1:r++,this.ranges.splice(n,r-n,e)},this.addList=function(e){var t=[];for(var n=e.length;n--;)t.push.apply(t,this.add(e[n]));return t},this.substractPoint=function(e){var t=this.pointIndex(e);if(t>=0)return this.ranges.splice(t,1)},this.merge=function(){var e=[],t=this.ranges;t=t.sort(function(e,t){return i(e.start,t.start)});var n=t[0],r;for(var s=1;s<t.length;s++){r=n,n=t[s];var o=i(r.end,n.start);if(o<0)continue;if(o==0&&!r.isEmpty()&&!n.isEmpty())continue;i(r.end,n.end)<0&&(r.end.row=n.end.row,r.end.column=n.end.column),t.splice(s,1),e.push(n),n=r,s--}return this.ranges=t,e},this.contains=function(e,t){return this.pointIndex({row:e,column:t})>=0},this.containsPoint=function(e){return this.pointIndex(e)>=0},this.rangeAtPoint=function(e){var t=this.pointIndex(e);if(t>=0)return this.ranges[t]},this.clipRows=function(e,t){var n=this.ranges;if(n[0].start.row>t||n[n.length-1].start.row<e)return[];var r=this.pointIndex({row:e,column:0});r<0&&(r=-r-1);var i=this.pointIndex({row:t,column:0},r);i<0&&(i=-i-1);var s=[];for(var o=r;o<i;o++)s.push(n[o]);return s},this.removeAll=function(){return this.ranges.splice(0,this.ranges.length)},this.attach=function(e){this.session&&this.detach(),this.session=e,this.onChange=this.$onChange.bind(this),this.session.on(\"change\",this.onChange)},this.detach=function(){if(!this.session)return;this.session.removeListener(\"change\",this.onChange),this.session=null},this.$onChange=function(e){if(e.action==\"insert\")var t=e.start,n=e.end;else var n=e.start,t=e.end;var r=t.row,i=n.row,s=i-r,o=-t.column+n.column,u=this.ranges;for(var a=0,f=u.length;a<f;a++){var l=u[a];if(l.end.row<r)continue;if(l.start.row>r)break;l.start.row==r&&l.start.column>=t.column&&(l.start.column!=t.column||!this.$insertRight)&&(l.start.column+=o,l.start.row+=s);if(l.end.row==r&&l.end.column>=t.column){if(l.end.column==t.column&&this.$insertRight)continue;l.end.column==t.column&&o>0&&a<f-1&&l.end.column>l.start.column&&l.end.column==u[a+1].start.column&&(l.end.column-=o),l.end.column+=o,l.end.row+=s}}if(s!=0&&a<f)for(;a<f;a++){var l=u[a];l.start.row+=s,l.end.row+=s}}}).call(s.prototype),t.RangeList=s}),define(\"ace/edit_session/fold\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/range_list\",\"ace/lib/oop\"],function(e,t,n){\"use strict\";function u(e,t){e.row-=t.row,e.row==0&&(e.column-=t.column)}function a(e,t){u(e.start,t),u(e.end,t)}function f(e,t){e.row==0&&(e.column+=t.column),e.row+=t.row}function l(e,t){f(e.start,t),f(e.end,t)}var r=e(\"../range\").Range,i=e(\"../range_list\").RangeList,s=e(\"../lib/oop\"),o=t.Fold=function(e,t){this.foldLine=null,this.placeholder=t,this.range=e,this.start=e.start,this.end=e.end,this.sameRow=e.start.row==e.end.row,this.subFolds=this.ranges=[]};s.inherits(o,i),function(){this.toString=function(){return'\"'+this.placeholder+'\" '+this.range.toString()},this.setFoldLine=function(e){this.foldLine=e,this.subFolds.forEach(function(t){t.setFoldLine(e)})},this.clone=function(){var e=this.range.clone(),t=new o(e,this.placeholder);return this.subFolds.forEach(function(e){t.subFolds.push(e.clone())}),t.collapseChildren=this.collapseChildren,t},this.addSubFold=function(e){if(this.range.isEqual(e))return;if(!this.range.containsRange(e))throw new Error(\"A fold can't intersect already existing fold\"+e.range+this.range);a(e,this.start);var t=e.start.row,n=e.start.column;for(var r=0,i=-1;r<this.subFolds.length;r++){i=this.subFolds[r].range.compare(t,n);if(i!=1)break}var s=this.subFolds[r];if(i==0)return s.addSubFold(e);var t=e.range.end.row,n=e.range.end.column;for(var o=r,i=-1;o<this.subFolds.length;o++){i=this.subFolds[o].range.compare(t,n);if(i!=1)break}var u=this.subFolds[o];if(i==0)throw new Error(\"A fold can't intersect already existing fold\"+e.range+this.range);var f=this.subFolds.splice(r,o-r,e);return e.setFoldLine(this.foldLine),e},this.restoreRange=function(e){return l(e,this.start)}}.call(o.prototype)}),define(\"ace/edit_session/folding\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/edit_session/fold_line\",\"ace/edit_session/fold\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";function u(){this.getFoldAt=function(e,t,n){var r=this.getFoldLine(e);if(!r)return null;var i=r.folds;for(var s=0;s<i.length;s++){var o=i[s];if(o.range.contains(e,t)){if(n==1&&o.range.isEnd(e,t))continue;if(n==-1&&o.range.isStart(e,t))continue;return o}}},this.getFoldsInRange=function(e){var t=e.start,n=e.end,r=this.$foldData,i=[];t.column+=1,n.column-=1;for(var s=0;s<r.length;s++){var o=r[s].range.compareRange(e);if(o==2)continue;if(o==-2)break;var u=r[s].folds;for(var a=0;a<u.length;a++){var f=u[a];o=f.range.compareRange(e);if(o==-2)break;if(o==2)continue;if(o==42)break;i.push(f)}}return t.column-=1,n.column+=1,i},this.getFoldsInRangeList=function(e){if(Array.isArray(e)){var t=[];e.forEach(function(e){t=t.concat(this.getFoldsInRange(e))},this)}else var t=this.getFoldsInRange(e);return t},this.getAllFolds=function(){var e=[],t=this.$foldData;for(var n=0;n<t.length;n++)for(var r=0;r<t[n].folds.length;r++)e.push(t[n].folds[r]);return e},this.getFoldStringAt=function(e,t,n,r){r=r||this.getFoldLine(e);if(!r)return null;var i={end:{column:0}},s,o;for(var u=0;u<r.folds.length;u++){o=r.folds[u];var a=o.range.compareEnd(e,t);if(a==-1){s=this.getLine(o.start.row).substring(i.end.column,o.start.column);break}if(a===0)return null;i=o}return s||(s=this.getLine(o.start.row).substring(i.end.column)),n==-1?s.substring(0,t-i.end.column):n==1?s.substring(t-i.end.column):s},this.getFoldLine=function(e,t){var n=this.$foldData,r=0;t&&(r=n.indexOf(t)),r==-1&&(r=0);for(r;r<n.length;r++){var i=n[r];if(i.start.row<=e&&i.end.row>=e)return i;if(i.end.row>e)return null}return null},this.getNextFoldLine=function(e,t){var n=this.$foldData,r=0;t&&(r=n.indexOf(t)),r==-1&&(r=0);for(r;r<n.length;r++){var i=n[r];if(i.end.row>=e)return i}return null},this.getFoldedRowCount=function(e,t){var n=this.$foldData,r=t-e+1;for(var i=0;i<n.length;i++){var s=n[i],o=s.end.row,u=s.start.row;if(o>=t){u<t&&(u>=e?r-=t-u:r=0);break}o>=e&&(u>=e?r-=o-u:r-=o-e+1)}return r},this.$addFoldLine=function(e){return this.$foldData.push(e),this.$foldData.sort(function(e,t){return e.start.row-t.start.row}),e},this.addFold=function(e,t){var n=this.$foldData,r=!1,o;e instanceof s?o=e:(o=new s(t,e),o.collapseChildren=t.collapseChildren),this.$clipRangeToDocument(o.range);var u=o.start.row,a=o.start.column,f=o.end.row,l=o.end.column;if(u<f||u==f&&a<=l-2){var c=this.getFoldAt(u,a,1),h=this.getFoldAt(f,l,-1);if(c&&h==c)return c.addSubFold(o);c&&!c.range.isStart(u,a)&&this.removeFold(c),h&&!h.range.isEnd(f,l)&&this.removeFold(h);var p=this.getFoldsInRange(o.range);p.length>0&&(this.removeFolds(p),p.forEach(function(e){o.addSubFold(e)}));for(var d=0;d<n.length;d++){var v=n[d];if(f==v.start.row){v.addFold(o),r=!0;break}if(u==v.end.row){v.addFold(o),r=!0;if(!o.sameRow){var m=n[d+1];if(m&&m.start.row==f){v.merge(m);break}}break}if(f<=v.start.row)break}return r||(v=this.$addFoldLine(new i(this.$foldData,o))),this.$useWrapMode?this.$updateWrapData(v.start.row,v.start.row):this.$updateRowLengthCache(v.start.row,v.start.row),this.$modified=!0,this._signal(\"changeFold\",{data:o,action:\"add\"}),o}throw new Error(\"The range has to be at least 2 characters width\")},this.addFolds=function(e){e.forEach(function(e){this.addFold(e)},this)},this.removeFold=function(e){var t=e.foldLine,n=t.start.row,r=t.end.row,i=this.$foldData,s=t.folds;if(s.length==1)i.splice(i.indexOf(t),1);else if(t.range.isEnd(e.end.row,e.end.column))s.pop(),t.end.row=s[s.length-1].end.row,t.end.column=s[s.length-1].end.column;else if(t.range.isStart(e.start.row,e.start.column))s.shift(),t.start.row=s[0].start.row,t.start.column=s[0].start.column;else if(e.sameRow)s.splice(s.indexOf(e),1);else{var o=t.split(e.start.row,e.start.column);s=o.folds,s.shift(),o.start.row=s[0].start.row,o.start.column=s[0].start.column}this.$updating||(this.$useWrapMode?this.$updateWrapData(n,r):this.$updateRowLengthCache(n,r)),this.$modified=!0,this._signal(\"changeFold\",{data:e,action:\"remove\"})},this.removeFolds=function(e){var t=[];for(var n=0;n<e.length;n++)t.push(e[n]);t.forEach(function(e){this.removeFold(e)},this),this.$modified=!0},this.expandFold=function(e){this.removeFold(e),e.subFolds.forEach(function(t){e.restoreRange(t),this.addFold(t)},this),e.collapseChildren>0&&this.foldAll(e.start.row+1,e.end.row,e.collapseChildren-1),e.subFolds=[]},this.expandFolds=function(e){e.forEach(function(e){this.expandFold(e)},this)},this.unfold=function(e,t){var n,i;e==null?(n=new r(0,0,this.getLength(),0),t=!0):typeof e==\"number\"?n=new r(e,0,e,this.getLine(e).length):\"row\"in e?n=r.fromPoints(e,e):n=e,i=this.getFoldsInRangeList(n);if(t)this.removeFolds(i);else{var s=i;while(s.length)this.expandFolds(s),s=this.getFoldsInRangeList(n)}if(i.length)return i},this.isRowFolded=function(e,t){return!!this.getFoldLine(e,t)},this.getRowFoldEnd=function(e,t){var n=this.getFoldLine(e,t);return n?n.end.row:e},this.getRowFoldStart=function(e,t){var n=this.getFoldLine(e,t);return n?n.start.row:e},this.getFoldDisplayLine=function(e,t,n,r,i){r==null&&(r=e.start.row),i==null&&(i=0),t==null&&(t=e.end.row),n==null&&(n=this.getLine(t).length);var s=this.doc,o=\"\";return e.walk(function(e,t,n,u){if(t<r)return;if(t==r){if(n<i)return;u=Math.max(i,u)}e!=null?o+=e:o+=s.getLine(t).substring(u,n)},t,n),o},this.getDisplayLine=function(e,t,n,r){var i=this.getFoldLine(e);if(!i){var s;return s=this.doc.getLine(e),s.substring(r||0,t||s.length)}return this.getFoldDisplayLine(i,e,t,n,r)},this.$cloneFoldData=function(){var e=[];return e=this.$foldData.map(function(t){var n=t.folds.map(function(e){return e.clone()});return new i(e,n)}),e},this.toggleFold=function(e){var t=this.selection,n=t.getRange(),r,i;if(n.isEmpty()){var s=n.start;r=this.getFoldAt(s.row,s.column);if(r){this.expandFold(r);return}(i=this.findMatchingBracket(s))?n.comparePoint(i)==1?n.end=i:(n.start=i,n.start.column++,n.end.column--):(i=this.findMatchingBracket({row:s.row,column:s.column+1}))?(n.comparePoint(i)==1?n.end=i:n.start=i,n.start.column++):n=this.getCommentFoldRange(s.row,s.column)||n}else{var o=this.getFoldsInRange(n);if(e&&o.length){this.expandFolds(o);return}o.length==1&&(r=o[0])}r||(r=this.getFoldAt(n.start.row,n.start.column));if(r&&r.range.toString()==n.toString()){this.expandFold(r);return}var u=\"...\";if(!n.isMultiLine()){u=this.getTextRange(n);if(u.length<4)return;u=u.trim().substring(0,2)+\"..\"}this.addFold(u,n)},this.getCommentFoldRange=function(e,t,n){var i=new o(this,e,t),s=i.getCurrentToken();if(s&&/^comment|string/.test(s.type)){var u=new r,a=new RegExp(s.type.replace(/\\..*/,\"\\\\.\"));if(n!=1){do s=i.stepBackward();while(s&&a.test(s.type));i.stepForward()}u.start.row=i.getCurrentTokenRow(),u.start.column=i.getCurrentTokenColumn()+2,i=new o(this,e,t);if(n!=-1){do s=i.stepForward();while(s&&a.test(s.type));s=i.stepBackward()}else s=i.getCurrentToken();return u.end.row=i.getCurrentTokenRow(),u.end.column=i.getCurrentTokenColumn()+s.value.length-2,u}},this.foldAll=function(e,t,n){n==undefined&&(n=1e5);var r=this.foldWidgets;if(!r)return;t=t||this.getLength(),e=e||0;for(var i=e;i<t;i++){r[i]==null&&(r[i]=this.getFoldWidget(i));if(r[i]!=\"start\")continue;var s=this.getFoldWidgetRange(i);if(s&&s.isMultiLine()&&s.end.row<=t&&s.start.row>=e){i=s.end.row;try{var o=this.addFold(\"...\",s);o&&(o.collapseChildren=n)}catch(u){}}}},this.$foldStyles={manual:1,markbegin:1,markbeginend:1},this.$foldStyle=\"markbegin\",this.setFoldStyle=function(e){if(!this.$foldStyles[e])throw new Error(\"invalid fold style: \"+e+\"[\"+Object.keys(this.$foldStyles).join(\", \")+\"]\");if(this.$foldStyle==e)return;this.$foldStyle=e,e==\"manual\"&&this.unfold();var t=this.$foldMode;this.$setFolding(null),this.$setFolding(t)},this.$setFolding=function(e){if(this.$foldMode==e)return;this.$foldMode=e,this.off(\"change\",this.$updateFoldWidgets),this.off(\"tokenizerUpdate\",this.$tokenizerUpdateFoldWidgets),this._signal(\"changeAnnotation\");if(!e||this.$foldStyle==\"manual\"){this.foldWidgets=null;return}this.foldWidgets=[],this.getFoldWidget=e.getFoldWidget.bind(e,this,this.$foldStyle),this.getFoldWidgetRange=e.getFoldWidgetRange.bind(e,this,this.$foldStyle),this.$updateFoldWidgets=this.updateFoldWidgets.bind(this),this.$tokenizerUpdateFoldWidgets=this.tokenizerUpdateFoldWidgets.bind(this),this.on(\"change\",this.$updateFoldWidgets),this.on(\"tokenizerUpdate\",this.$tokenizerUpdateFoldWidgets)},this.getParentFoldRangeData=function(e,t){var n=this.foldWidgets;if(!n||t&&n[e])return{};var r=e-1,i;while(r>=0){var s=n[r];s==null&&(s=n[r]=this.getFoldWidget(r));if(s==\"start\"){var o=this.getFoldWidgetRange(r);i||(i=o);if(o&&o.end.row>=e)break}r--}return{range:r!==-1&&o,firstRange:i}},this.onFoldWidgetClick=function(e,t){t=t.domEvent;var n={children:t.shiftKey,all:t.ctrlKey||t.metaKey,siblings:t.altKey},r=this.$toggleFoldWidget(e,n);if(!r){var i=t.target||t.srcElement;i&&/ace_fold-widget/.test(i.className)&&(i.className+=\" ace_invalid\")}},this.$toggleFoldWidget=function(e,t){if(!this.getFoldWidget)return;var n=this.getFoldWidget(e),r=this.getLine(e),i=n===\"end\"?-1:1,s=this.getFoldAt(e,i===-1?0:r.length,i);if(s)return t.children||t.all?this.removeFold(s):this.expandFold(s),s;var o=this.getFoldWidgetRange(e,!0);if(o&&!o.isMultiLine()){s=this.getFoldAt(o.start.row,o.start.column,1);if(s&&o.isEqual(s.range))return this.removeFold(s),s}if(t.siblings){var u=this.getParentFoldRangeData(e);if(u.range)var a=u.range.start.row+1,f=u.range.end.row;this.foldAll(a,f,t.all?1e4:0)}else t.children?(f=o?o.end.row:this.getLength(),this.foldAll(e+1,f,t.all?1e4:0)):o&&(t.all&&(o.collapseChildren=1e4),this.addFold(\"...\",o));return o},this.toggleFoldWidget=function(e){var t=this.selection.getCursor().row;t=this.getRowFoldStart(t);var n=this.$toggleFoldWidget(t,{});if(n)return;var r=this.getParentFoldRangeData(t,!0);n=r.range||r.firstRange;if(n){t=n.start.row;var i=this.getFoldAt(t,this.getLine(t).length,1);i?this.removeFold(i):this.addFold(\"...\",n)}},this.updateFoldWidgets=function(e){var t=e.start.row,n=e.end.row-t;if(n===0)this.foldWidgets[t]=null;else if(e.action==\"remove\")this.foldWidgets.splice(t,n+1,null);else{var r=Array(n+1);r.unshift(t,1),this.foldWidgets.splice.apply(this.foldWidgets,r)}},this.tokenizerUpdateFoldWidgets=function(e){var t=e.data;t.first!=t.last&&this.foldWidgets.length>t.first&&this.foldWidgets.splice(t.first,this.foldWidgets.length)}}var r=e(\"../range\").Range,i=e(\"./fold_line\").FoldLine,s=e(\"./fold\").Fold,o=e(\"../token_iterator\").TokenIterator;t.Folding=u}),define(\"ace/edit_session/bracket_match\",[\"require\",\"exports\",\"module\",\"ace/token_iterator\",\"ace/range\"],function(e,t,n){\"use strict\";function s(){this.findMatchingBracket=function(e,t){if(e.column==0)return null;var n=t||this.getLine(e.row).charAt(e.column-1);if(n==\"\")return null;var r=n.match(/([\\(\\[\\{])|([\\)\\]\\}])/);return r?r[1]?this.$findClosingBracket(r[1],e):this.$findOpeningBracket(r[2],e):null},this.getBracketRange=function(e){var t=this.getLine(e.row),n=!0,r,s=t.charAt(e.column-1),o=s&&s.match(/([\\(\\[\\{])|([\\)\\]\\}])/);o||(s=t.charAt(e.column),e={row:e.row,column:e.column+1},o=s&&s.match(/([\\(\\[\\{])|([\\)\\]\\}])/),n=!1);if(!o)return null;if(o[1]){var u=this.$findClosingBracket(o[1],e);if(!u)return null;r=i.fromPoints(e,u),n||(r.end.column++,r.start.column--),r.cursor=r.end}else{var u=this.$findOpeningBracket(o[2],e);if(!u)return null;r=i.fromPoints(u,e),n||(r.start.column++,r.end.column--),r.cursor=r.start}return r},this.$brackets={\")\":\"(\",\"(\":\")\",\"]\":\"[\",\"[\":\"]\",\"{\":\"}\",\"}\":\"{\"},this.$findOpeningBracket=function(e,t,n){var i=this.$brackets[e],s=1,o=new r(this,t.row,t.column),u=o.getCurrentToken();u||(u=o.stepForward());if(!u)return;n||(n=new RegExp(\"(\\\\.?\"+u.type.replace(\".\",\"\\\\.\").replace(\"rparen\",\".paren\").replace(/\\b(?:end)\\b/,\"(?:start|begin|end)\")+\")+\"));var a=t.column-o.getCurrentTokenColumn()-2,f=u.value;for(;;){while(a>=0){var l=f.charAt(a);if(l==i){s-=1;if(s==0)return{row:o.getCurrentTokenRow(),column:a+o.getCurrentTokenColumn()}}else l==e&&(s+=1);a-=1}do u=o.stepBackward();while(u&&!n.test(u.type));if(u==null)break;f=u.value,a=f.length-1}return null},this.$findClosingBracket=function(e,t,n){var i=this.$brackets[e],s=1,o=new r(this,t.row,t.column),u=o.getCurrentToken();u||(u=o.stepForward());if(!u)return;n||(n=new RegExp(\"(\\\\.?\"+u.type.replace(\".\",\"\\\\.\").replace(\"lparen\",\".paren\").replace(/\\b(?:start|begin)\\b/,\"(?:start|begin|end)\")+\")+\"));var a=t.column-o.getCurrentTokenColumn();for(;;){var f=u.value,l=f.length;while(a<l){var c=f.charAt(a);if(c==i){s-=1;if(s==0)return{row:o.getCurrentTokenRow(),column:a+o.getCurrentTokenColumn()}}else c==e&&(s+=1);a+=1}do u=o.stepForward();while(u&&!n.test(u.type));if(u==null)break;a=0}return null}}var r=e(\"../token_iterator\").TokenIterator,i=e(\"../range\").Range;t.BracketMatch=s}),define(\"ace/edit_session\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/config\",\"ace/lib/event_emitter\",\"ace/selection\",\"ace/mode/text\",\"ace/range\",\"ace/document\",\"ace/background_tokenizer\",\"ace/search_highlight\",\"ace/edit_session/folding\",\"ace/edit_session/bracket_match\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/lang\"),s=e(\"./config\"),o=e(\"./lib/event_emitter\").EventEmitter,u=e(\"./selection\").Selection,a=e(\"./mode/text\").Mode,f=e(\"./range\").Range,l=e(\"./document\").Document,c=e(\"./background_tokenizer\").BackgroundTokenizer,h=e(\"./search_highlight\").SearchHighlight,p=function(e,t){this.$breakpoints=[],this.$decorations=[],this.$frontMarkers={},this.$backMarkers={},this.$markerId=1,this.$undoSelect=!0,this.$foldData=[],this.id=\"session\"+ ++p.$uid,this.$foldData.toString=function(){return this.join(\"\\n\")},this.on(\"changeFold\",this.onChangeFold.bind(this)),this.$onChange=this.onChange.bind(this);if(typeof e!=\"object\"||!e.getLine)e=new l(e);this.setDocument(e),this.selection=new u(this),s.resetOptions(this),this.setMode(t),s._signal(\"session\",this)};(function(){function m(e){return e<4352?!1:e>=4352&&e<=4447||e>=4515&&e<=4519||e>=4602&&e<=4607||e>=9001&&e<=9002||e>=11904&&e<=11929||e>=11931&&e<=12019||e>=12032&&e<=12245||e>=12272&&e<=12283||e>=12288&&e<=12350||e>=12353&&e<=12438||e>=12441&&e<=12543||e>=12549&&e<=12589||e>=12593&&e<=12686||e>=12688&&e<=12730||e>=12736&&e<=12771||e>=12784&&e<=12830||e>=12832&&e<=12871||e>=12880&&e<=13054||e>=13056&&e<=19903||e>=19968&&e<=42124||e>=42128&&e<=42182||e>=43360&&e<=43388||e>=44032&&e<=55203||e>=55216&&e<=55238||e>=55243&&e<=55291||e>=63744&&e<=64255||e>=65040&&e<=65049||e>=65072&&e<=65106||e>=65108&&e<=65126||e>=65128&&e<=65131||e>=65281&&e<=65376||e>=65504&&e<=65510}r.implement(this,o),this.setDocument=function(e){this.doc&&this.doc.removeListener(\"change\",this.$onChange),this.doc=e,e.on(\"change\",this.$onChange),this.bgTokenizer&&this.bgTokenizer.setDocument(this.getDocument()),this.resetCaches()},this.getDocument=function(){return this.doc},this.$resetRowCache=function(e){if(!e){this.$docRowCache=[],this.$screenRowCache=[];return}var t=this.$docRowCache.length,n=this.$getRowCacheIndex(this.$docRowCache,e)+1;t>n&&(this.$docRowCache.splice(n,t),this.$screenRowCache.splice(n,t))},this.$getRowCacheIndex=function(e,t){var n=0,r=e.length-1;while(n<=r){var i=n+r>>1,s=e[i];if(t>s)n=i+1;else{if(!(t<s))return i;r=i-1}}return n-1},this.resetCaches=function(){this.$modified=!0,this.$wrapData=[],this.$rowLengthCache=[],this.$resetRowCache(0),this.bgTokenizer&&this.bgTokenizer.start(0)},this.onChangeFold=function(e){var t=e.data;this.$resetRowCache(t.start.row)},this.onChange=function(e){this.$modified=!0,this.$resetRowCache(e.start.row);var t=this.$updateInternalDataOnChange(e);!this.$fromUndo&&this.$undoManager&&!e.ignore&&(this.$deltasDoc.push(e),t&&t.length!=0&&this.$deltasFold.push({action:\"removeFolds\",folds:t}),this.$informUndoManager.schedule()),this.bgTokenizer&&this.bgTokenizer.$updateOnChange(e),this._signal(\"change\",e)},this.setValue=function(e){this.doc.setValue(e),this.selection.moveTo(0,0),this.$resetRowCache(0),this.$deltas=[],this.$deltasDoc=[],this.$deltasFold=[],this.setUndoManager(this.$undoManager),this.getUndoManager().reset()},this.getValue=this.toString=function(){return this.doc.getValue()},this.getSelection=function(){return this.selection},this.getState=function(e){return this.bgTokenizer.getState(e)},this.getTokens=function(e){return this.bgTokenizer.getTokens(e)},this.getTokenAt=function(e,t){var n=this.bgTokenizer.getTokens(e),r,i=0;if(t==null)s=n.length-1,i=this.getLine(e).length;else for(var s=0;s<n.length;s++){i+=n[s].value.length;if(i>=t)break}return r=n[s],r?(r.index=s,r.start=i-r.value.length,r):null},this.setUndoManager=function(e){this.$undoManager=e,this.$deltas=[],this.$deltasDoc=[],this.$deltasFold=[],this.$informUndoManager&&this.$informUndoManager.cancel();if(e){var t=this;this.$syncInformUndoManager=function(){t.$informUndoManager.cancel(),t.$deltasFold.length&&(t.$deltas.push({group:\"fold\",deltas:t.$deltasFold}),t.$deltasFold=[]),t.$deltasDoc.length&&(t.$deltas.push({group:\"doc\",deltas:t.$deltasDoc}),t.$deltasDoc=[]),t.$deltas.length>0&&e.execute({action:\"aceupdate\",args:[t.$deltas,t],merge:t.mergeUndoDeltas}),t.mergeUndoDeltas=!1,t.$deltas=[]},this.$informUndoManager=i.delayedCall(this.$syncInformUndoManager)}},this.markUndoGroup=function(){this.$syncInformUndoManager&&this.$syncInformUndoManager()},this.$defaultUndoManager={undo:function(){},redo:function(){},reset:function(){}},this.getUndoManager=function(){return this.$undoManager||this.$defaultUndoManager},this.getTabString=function(){return this.getUseSoftTabs()?i.stringRepeat(\" \",this.getTabSize()):\"\t\"},this.setUseSoftTabs=function(e){this.setOption(\"useSoftTabs\",e)},this.getUseSoftTabs=function(){return this.$useSoftTabs&&!this.$mode.$indentWithTabs},this.setTabSize=function(e){this.setOption(\"tabSize\",e)},this.getTabSize=function(){return this.$tabSize},this.isTabStop=function(e){return this.$useSoftTabs&&e.column%this.$tabSize===0},this.$overwrite=!1,this.setOverwrite=function(e){this.setOption(\"overwrite\",e)},this.getOverwrite=function(){return this.$overwrite},this.toggleOverwrite=function(){this.setOverwrite(!this.$overwrite)},this.addGutterDecoration=function(e,t){this.$decorations[e]||(this.$decorations[e]=\"\"),this.$decorations[e]+=\" \"+t,this._signal(\"changeBreakpoint\",{})},this.removeGutterDecoration=function(e,t){this.$decorations[e]=(this.$decorations[e]||\"\").replace(\" \"+t,\"\"),this._signal(\"changeBreakpoint\",{})},this.getBreakpoints=function(){return this.$breakpoints},this.setBreakpoints=function(e){this.$breakpoints=[];for(var t=0;t<e.length;t++)this.$breakpoints[e[t]]=\"ace_breakpoint\";this._signal(\"changeBreakpoint\",{})},this.clearBreakpoints=function(){this.$breakpoints=[],this._signal(\"changeBreakpoint\",{})},this.setBreakpoint=function(e,t){t===undefined&&(t=\"ace_breakpoint\"),t?this.$breakpoints[e]=t:delete this.$breakpoints[e],this._signal(\"changeBreakpoint\",{})},this.clearBreakpoint=function(e){delete this.$breakpoints[e],this._signal(\"changeBreakpoint\",{})},this.addMarker=function(e,t,n,r){var i=this.$markerId++,s={range:e,type:n||\"line\",renderer:typeof n==\"function\"?n:null,clazz:t,inFront:!!r,id:i};return r?(this.$frontMarkers[i]=s,this._signal(\"changeFrontMarker\")):(this.$backMarkers[i]=s,this._signal(\"changeBackMarker\")),i},this.addDynamicMarker=function(e,t){if(!e.update)return;var n=this.$markerId++;return e.id=n,e.inFront=!!t,t?(this.$frontMarkers[n]=e,this._signal(\"changeFrontMarker\")):(this.$backMarkers[n]=e,this._signal(\"changeBackMarker\")),e},this.removeMarker=function(e){var t=this.$frontMarkers[e]||this.$backMarkers[e];if(!t)return;var n=t.inFront?this.$frontMarkers:this.$backMarkers;t&&(delete n[e],this._signal(t.inFront?\"changeFrontMarker\":\"changeBackMarker\"))},this.getMarkers=function(e){return e?this.$frontMarkers:this.$backMarkers},this.highlight=function(e){if(!this.$searchHighlight){var t=new h(null,\"ace_selected-word\",\"text\");this.$searchHighlight=this.addDynamicMarker(t)}this.$searchHighlight.setRegexp(e)},this.highlightLines=function(e,t,n,r){typeof t!=\"number\"&&(n=t,t=e),n||(n=\"ace_step\");var i=new f(e,0,t,Infinity);return i.id=this.addMarker(i,n,\"fullLine\",r),i},this.setAnnotations=function(e){this.$annotations=e,this._signal(\"changeAnnotation\",{})},this.getAnnotations=function(){return this.$annotations||[]},this.clearAnnotations=function(){this.setAnnotations([])},this.$detectNewLine=function(e){var t=e.match(/^.*?(\\r?\\n)/m);t?this.$autoNewLine=t[1]:this.$autoNewLine=\"\\n\"},this.getWordRange=function(e,t){var n=this.getLine(e),r=!1;t>0&&(r=!!n.charAt(t-1).match(this.tokenRe)),r||(r=!!n.charAt(t).match(this.tokenRe));if(r)var i=this.tokenRe;else if(/^\\s+$/.test(n.slice(t-1,t+1)))var i=/\\s/;else var i=this.nonTokenRe;var s=t;if(s>0){do s--;while(s>=0&&n.charAt(s).match(i));s++}var o=t;while(o<n.length&&n.charAt(o).match(i))o++;return new f(e,s,e,o)},this.getAWordRange=function(e,t){var n=this.getWordRange(e,t),r=this.getLine(n.end.row);while(r.charAt(n.end.column).match(/[ \\t]/))n.end.column+=1;return n},this.setNewLineMode=function(e){this.doc.setNewLineMode(e)},this.getNewLineMode=function(){return this.doc.getNewLineMode()},this.setUseWorker=function(e){this.setOption(\"useWorker\",e)},this.getUseWorker=function(){return this.$useWorker},this.onReloadTokenizer=function(e){var t=e.data;this.bgTokenizer.start(t.first),this._signal(\"tokenizerUpdate\",e)},this.$modes={},this.$mode=null,this.$modeId=null,this.setMode=function(e,t){if(e&&typeof e==\"object\"){if(e.getTokenizer)return this.$onChangeMode(e);var n=e,r=n.path}else r=e||\"ace/mode/text\";this.$modes[\"ace/mode/text\"]||(this.$modes[\"ace/mode/text\"]=new a);if(this.$modes[r]&&!n){this.$onChangeMode(this.$modes[r]),t&&t();return}this.$modeId=r,s.loadModule([\"mode\",r],function(e){if(this.$modeId!==r)return t&&t();this.$modes[r]&&!n?this.$onChangeMode(this.$modes[r]):e&&e.Mode&&(e=new e.Mode(n),n||(this.$modes[r]=e,e.$id=r),this.$onChangeMode(e)),t&&t()}.bind(this)),this.$mode||this.$onChangeMode(this.$modes[\"ace/mode/text\"],!0)},this.$onChangeMode=function(e,t){t||(this.$modeId=e.$id);if(this.$mode===e)return;this.$mode=e,this.$stopWorker(),this.$useWorker&&this.$startWorker();var n=e.getTokenizer();if(n.addEventListener!==undefined){var r=this.onReloadTokenizer.bind(this);n.addEventListener(\"update\",r)}if(!this.bgTokenizer){this.bgTokenizer=new c(n);var i=this;this.bgTokenizer.addEventListener(\"update\",function(e){i._signal(\"tokenizerUpdate\",e)})}else this.bgTokenizer.setTokenizer(n);this.bgTokenizer.setDocument(this.getDocument()),this.tokenRe=e.tokenRe,this.nonTokenRe=e.nonTokenRe,t||(e.attachToSession&&e.attachToSession(this),this.$options.wrapMethod.set.call(this,this.$wrapMethod),this.$setFolding(e.foldingRules),this.bgTokenizer.start(0),this._emit(\"changeMode\"))},this.$stopWorker=function(){this.$worker&&(this.$worker.terminate(),this.$worker=null)},this.$startWorker=function(){try{this.$worker=this.$mode.createWorker(this)}catch(e){s.warn(\"Could not load worker\",e),this.$worker=null}},this.getMode=function(){return this.$mode},this.$scrollTop=0,this.setScrollTop=function(e){if(this.$scrollTop===e||isNaN(e))return;this.$scrollTop=e,this._signal(\"changeScrollTop\",e)},this.getScrollTop=function(){return this.$scrollTop},this.$scrollLeft=0,this.setScrollLeft=function(e){if(this.$scrollLeft===e||isNaN(e))return;this.$scrollLeft=e,this._signal(\"changeScrollLeft\",e)},this.getScrollLeft=function(){return this.$scrollLeft},this.getScreenWidth=function(){return this.$computeWidth(),this.lineWidgets?Math.max(this.getLineWidgetMaxWidth(),this.screenWidth):this.screenWidth},this.getLineWidgetMaxWidth=function(){if(this.lineWidgetsWidth!=null)return this.lineWidgetsWidth;var e=0;return this.lineWidgets.forEach(function(t){t&&t.screenWidth>e&&(e=t.screenWidth)}),this.lineWidgetWidth=e},this.$computeWidth=function(e){if(this.$modified||e){this.$modified=!1;if(this.$useWrapMode)return this.screenWidth=this.$wrapLimit;var t=this.doc.getAllLines(),n=this.$rowLengthCache,r=0,i=0,s=this.$foldData[i],o=s?s.start.row:Infinity,u=t.length;for(var a=0;a<u;a++){if(a>o){a=s.end.row+1;if(a>=u)break;s=this.$foldData[i++],o=s?s.start.row:Infinity}n[a]==null&&(n[a]=this.$getStringScreenWidth(t[a])[0]),n[a]>r&&(r=n[a])}this.screenWidth=r}},this.getLine=function(e){return this.doc.getLine(e)},this.getLines=function(e,t){return this.doc.getLines(e,t)},this.getLength=function(){return this.doc.getLength()},this.getTextRange=function(e){return this.doc.getTextRange(e||this.selection.getRange())},this.insert=function(e,t){return this.doc.insert(e,t)},this.remove=function(e){return this.doc.remove(e)},this.removeFullLines=function(e,t){return this.doc.removeFullLines(e,t)},this.undoChanges=function(e,t){if(!e.length)return;this.$fromUndo=!0;var n=null;for(var r=e.length-1;r!=-1;r--){var i=e[r];i.group==\"doc\"?(this.doc.revertDeltas(i.deltas),n=this.$getUndoSelection(i.deltas,!0,n)):i.deltas.forEach(function(e){this.addFolds(e.folds)},this)}return this.$fromUndo=!1,n&&this.$undoSelect&&!t&&this.selection.setSelectionRange(n),n},this.redoChanges=function(e,t){if(!e.length)return;this.$fromUndo=!0;var n=null;for(var r=0;r<e.length;r++){var i=e[r];i.group==\"doc\"&&(this.doc.applyDeltas(i.deltas),n=this.$getUndoSelection(i.deltas,!1,n))}return this.$fromUndo=!1,n&&this.$undoSelect&&!t&&this.selection.setSelectionRange(n),n},this.setUndoSelect=function(e){this.$undoSelect=e},this.$getUndoSelection=function(e,t,n){function r(e){return t?e.action!==\"insert\":e.action===\"insert\"}var i=e[0],s,o,u=!1;r(i)?(s=f.fromPoints(i.start,i.end),u=!0):(s=f.fromPoints(i.start,i.start),u=!1);for(var a=1;a<e.length;a++)i=e[a],r(i)?(o=i.start,s.compare(o.row,o.column)==-1&&s.setStart(o),o=i.end,s.compare(o.row,o.column)==1&&s.setEnd(o),u=!0):(o=i.start,s.compare(o.row,o.column)==-1&&(s=f.fromPoints(i.start,i.start)),u=!1);if(n!=null){f.comparePoints(n.start,s.start)===0&&(n.start.column+=s.end.column-s.start.column,n.end.column+=s.end.column-s.start.column);var l=n.compareRange(s);l==1?s.setStart(n.start):l==-1&&s.setEnd(n.end)}return s},this.replace=function(e,t){return this.doc.replace(e,t)},this.moveText=function(e,t,n){var r=this.getTextRange(e),i=this.getFoldsInRange(e),s=f.fromPoints(t,t);if(!n){this.remove(e);var o=e.start.row-e.end.row,u=o?-e.end.column:e.start.column-e.end.column;u&&(s.start.row==e.end.row&&s.start.column>e.end.column&&(s.start.column+=u),s.end.row==e.end.row&&s.end.column>e.end.column&&(s.end.column+=u)),o&&s.start.row>=e.end.row&&(s.start.row+=o,s.end.row+=o)}s.end=this.insert(s.start,r);if(i.length){var a=e.start,l=s.start,o=l.row-a.row,u=l.column-a.column;this.addFolds(i.map(function(e){return e=e.clone(),e.start.row==a.row&&(e.start.column+=u),e.end.row==a.row&&(e.end.column+=u),e.start.row+=o,e.end.row+=o,e}))}return s},this.indentRows=function(e,t,n){n=n.replace(/\\t/g,this.getTabString());for(var r=e;r<=t;r++)this.doc.insertInLine({row:r,column:0},n)},this.outdentRows=function(e){var t=e.collapseRows(),n=new f(0,0,0,0),r=this.getTabSize();for(var i=t.start.row;i<=t.end.row;++i){var s=this.getLine(i);n.start.row=i,n.end.row=i;for(var o=0;o<r;++o)if(s.charAt(o)!=\" \")break;o<r&&s.charAt(o)==\"\t\"?(n.start.column=o,n.end.column=o+1):(n.start.column=0,n.end.column=o),this.remove(n)}},this.$moveLines=function(e,t,n){e=this.getRowFoldStart(e),t=this.getRowFoldEnd(t);if(n<0){var r=this.getRowFoldStart(e+n);if(r<0)return 0;var i=r-e}else if(n>0){var r=this.getRowFoldEnd(t+n);if(r>this.doc.getLength()-1)return 0;var i=r-t}else{e=this.$clipRowToDocument(e),t=this.$clipRowToDocument(t);var i=t-e+1}var s=new f(e,0,t,Number.MAX_VALUE),o=this.getFoldsInRange(s).map(function(e){return e=e.clone(),e.start.row+=i,e.end.row+=i,e}),u=n==0?this.doc.getLines(e,t):this.doc.removeFullLines(e,t);return this.doc.insertFullLines(e+i,u),o.length&&this.addFolds(o),i},this.moveLinesUp=function(e,t){return this.$moveLines(e,t,-1)},this.moveLinesDown=function(e,t){return this.$moveLines(e,t,1)},this.duplicateLines=function(e,t){return this.$moveLines(e,t,0)},this.$clipRowToDocument=function(e){return Math.max(0,Math.min(e,this.doc.getLength()-1))},this.$clipColumnToRow=function(e,t){return t<0?0:Math.min(this.doc.getLine(e).length,t)},this.$clipPositionToDocument=function(e,t){t=Math.max(0,t);if(e<0)e=0,t=0;else{var n=this.doc.getLength();e>=n?(e=n-1,t=this.doc.getLine(n-1).length):t=Math.min(this.doc.getLine(e).length,t)}return{row:e,column:t}},this.$clipRangeToDocument=function(e){e.start.row<0?(e.start.row=0,e.start.column=0):e.start.column=this.$clipColumnToRow(e.start.row,e.start.column);var t=this.doc.getLength()-1;return e.end.row>t?(e.end.row=t,e.end.column=this.doc.getLine(t).length):e.end.column=this.$clipColumnToRow(e.end.row,e.end.column),e},this.$wrapLimit=80,this.$useWrapMode=!1,this.$wrapLimitRange={min:null,max:null},this.setUseWrapMode=function(e){if(e!=this.$useWrapMode){this.$useWrapMode=e,this.$modified=!0,this.$resetRowCache(0);if(e){var t=this.getLength();this.$wrapData=Array(t),this.$updateWrapData(0,t-1)}this._signal(\"changeWrapMode\")}},this.getUseWrapMode=function(){return this.$useWrapMode},this.setWrapLimitRange=function(e,t){if(this.$wrapLimitRange.min!==e||this.$wrapLimitRange.max!==t)this.$wrapLimitRange={min:e,max:t},this.$modified=!0,this.$useWrapMode&&this._signal(\"changeWrapMode\")},this.adjustWrapLimit=function(e,t){var n=this.$wrapLimitRange;n.max<0&&(n={min:t,max:t});var r=this.$constrainWrapLimit(e,n.min,n.max);return r!=this.$wrapLimit&&r>1?(this.$wrapLimit=r,this.$modified=!0,this.$useWrapMode&&(this.$updateWrapData(0,this.getLength()-1),this.$resetRowCache(0),this._signal(\"changeWrapLimit\")),!0):!1},this.$constrainWrapLimit=function(e,t,n){return t&&(e=Math.max(t,e)),n&&(e=Math.min(n,e)),e},this.getWrapLimit=function(){return this.$wrapLimit},this.setWrapLimit=function(e){this.setWrapLimitRange(e,e)},this.getWrapLimitRange=function(){return{min:this.$wrapLimitRange.min,max:this.$wrapLimitRange.max}},this.$updateInternalDataOnChange=function(e){var t=this.$useWrapMode,n=e.action,r=e.start,i=e.end,s=r.row,o=i.row,u=o-s,a=null;this.$updating=!0;if(u!=0)if(n===\"remove\"){this[t?\"$wrapData\":\"$rowLengthCache\"].splice(s,u);var f=this.$foldData;a=this.getFoldsInRange(e),this.removeFolds(a);var l=this.getFoldLine(i.row),c=0;if(l){l.addRemoveChars(i.row,i.column,r.column-i.column),l.shiftRow(-u);var h=this.getFoldLine(s);h&&h!==l&&(h.merge(l),l=h),c=f.indexOf(l)+1}for(c;c<f.length;c++){var l=f[c];l.start.row>=i.row&&l.shiftRow(-u)}o=s}else{var p=Array(u);p.unshift(s,0);var d=t?this.$wrapData:this.$rowLengthCache;d.splice.apply(d,p);var f=this.$foldData,l=this.getFoldLine(s),c=0;if(l){var v=l.range.compareInside(r.row,r.column);v==0?(l=l.split(r.row,r.column),l&&(l.shiftRow(u),l.addRemoveChars(o,0,i.column-r.column))):v==-1&&(l.addRemoveChars(s,0,i.column-r.column),l.shiftRow(u)),c=f.indexOf(l)+1}for(c;c<f.length;c++){var l=f[c];l.start.row>=s&&l.shiftRow(u)}}else{u=Math.abs(e.start.column-e.end.column),n===\"remove\"&&(a=this.getFoldsInRange(e),this.removeFolds(a),u=-u);var l=this.getFoldLine(s);l&&l.addRemoveChars(s,r.column,u)}return t&&this.$wrapData.length!=this.doc.getLength()&&console.error(\"doc.getLength() and $wrapData.length have to be the same!\"),this.$updating=!1,t?this.$updateWrapData(s,o):this.$updateRowLengthCache(s,o),a},this.$updateRowLengthCache=function(e,t,n){this.$rowLengthCache[e]=null,this.$rowLengthCache[t]=null},this.$updateWrapData=function(e,t){var r=this.doc.getAllLines(),i=this.getTabSize(),s=this.$wrapData,o=this.$wrapLimit,a,f,l=e;t=Math.min(t,r.length-1);while(l<=t)f=this.getFoldLine(l,f),f?(a=[],f.walk(function(e,t,i,s){var o;if(e!=null){o=this.$getDisplayTokens(e,a.length),o[0]=n;for(var f=1;f<o.length;f++)o[f]=u}else o=this.$getDisplayTokens(r[t].substring(s,i),a.length);a=a.concat(o)}.bind(this),f.end.row,r[f.end.row].length+1),s[f.start.row]=this.$computeWrapSplits(a,o,i),l=f.end.row+1):(a=this.$getDisplayTokens(r[l]),s[l]=this.$computeWrapSplits(a,o,i),l++)};var e=1,t=2,n=3,u=4,l=9,p=10,d=11,v=12;this.$computeWrapSplits=function(e,r,i){function g(){var t=0;if(m===0)return t;if(h)for(var n=0;n<e.length;n++){var r=e[n];if(r==p)t+=1;else{if(r!=d){if(r==v)continue;break}t+=i}}return c&&h!==!1&&(t+=i),Math.min(t,m)}function y(t){var n=e.slice(a,t),r=n.length;n.join(\"\").replace(/12/g,function(){r-=1}).replace(/2/g,function(){r-=1}),s.length||(b=g(),s.indent=b),f+=r,s.push(f),a=t}if(e.length==0)return[];var s=[],o=e.length,a=0,f=0,c=this.$wrapAsCode,h=this.$indentedSoftWrap,m=r<=Math.max(2*i,8)||h===!1?0:Math.floor(r/2),b=0;while(o-a>r-b){var w=a+r-b;if(e[w-1]>=p&&e[w]>=p){y(w);continue}if(e[w]==n||e[w]==u){for(w;w!=a-1;w--)if(e[w]==n)break;if(w>a){y(w);continue}w=a+r;for(w;w<e.length;w++)if(e[w]!=u)break;if(w==e.length)break;y(w);continue}var E=Math.max(w-(r-(r>>2)),a-1);while(w>E&&e[w]<n)w--;if(c){while(w>E&&e[w]<n)w--;while(w>E&&e[w]==l)w--}else while(w>E&&e[w]<p)w--;if(w>E){y(++w);continue}w=a+r,e[w]==t&&w--,y(w-b)}return s},this.$getDisplayTokens=function(n,r){var i=[],s;r=r||0;for(var o=0;o<n.length;o++){var u=n.charCodeAt(o);if(u==9){s=this.getScreenTabSize(i.length+r),i.push(d);for(var a=1;a<s;a++)i.push(v)}else u==32?i.push(p):u>39&&u<48||u>57&&u<64?i.push(l):u>=4352&&m(u)?i.push(e,t):i.push(e)}return i},this.$getStringScreenWidth=function(e,t,n){if(t==0)return[0,0];t==null&&(t=Infinity),n=n||0;var r,i;for(i=0;i<e.length;i++){r=e.charCodeAt(i),r==9?n+=this.getScreenTabSize(n):r>=4352&&m(r)?n+=2:n+=1;if(n>t)break}return[n,i]},this.lineWidgets=null,this.getRowLength=function(e){if(this.lineWidgets)var t=this.lineWidgets[e]&&this.lineWidgets[e].rowCount||0;else t=0;return!this.$useWrapMode||!this.$wrapData[e]?1+t:this.$wrapData[e].length+1+t},this.getRowLineCount=function(e){return!this.$useWrapMode||!this.$wrapData[e]?1:this.$wrapData[e].length+1},this.getRowWrapIndent=function(e){if(this.$useWrapMode){var t=this.screenToDocumentPosition(e,Number.MAX_VALUE),n=this.$wrapData[t.row];return n.length&&n[0]<t.column?n.indent:0}return 0},this.getScreenLastRowColumn=function(e){var t=this.screenToDocumentPosition(e,Number.MAX_VALUE);return this.documentToScreenColumn(t.row,t.column)},this.getDocumentLastRowColumn=function(e,t){var n=this.documentToScreenRow(e,t);return this.getScreenLastRowColumn(n)},this.getDocumentLastRowColumnPosition=function(e,t){var n=this.documentToScreenRow(e,t);return this.screenToDocumentPosition(n,Number.MAX_VALUE/10)},this.getRowSplitData=function(e){return this.$useWrapMode?this.$wrapData[e]:undefined},this.getScreenTabSize=function(e){return this.$tabSize-e%this.$tabSize},this.screenToDocumentRow=function(e,t){return this.screenToDocumentPosition(e,t).row},this.screenToDocumentColumn=function(e,t){return this.screenToDocumentPosition(e,t).column},this.screenToDocumentPosition=function(e,t){if(e<0)return{row:0,column:0};var n,r=0,i=0,s,o=0,u=0,a=this.$screenRowCache,f=this.$getRowCacheIndex(a,e),l=a.length;if(l&&f>=0)var o=a[f],r=this.$docRowCache[f],c=e>a[l-1];else var c=!l;var h=this.getLength()-1,p=this.getNextFoldLine(r),d=p?p.start.row:Infinity;while(o<=e){u=this.getRowLength(r);if(o+u>e||r>=h)break;o+=u,r++,r>d&&(r=p.end.row+1,p=this.getNextFoldLine(r,p),d=p?p.start.row:Infinity),c&&(this.$docRowCache.push(r),this.$screenRowCache.push(o))}if(p&&p.start.row<=r)n=this.getFoldDisplayLine(p),r=p.start.row;else{if(o+u<=e||r>h)return{row:h,column:this.getLine(h).length};n=this.getLine(r),p=null}var v=0;if(this.$useWrapMode){var m=this.$wrapData[r];if(m){var g=Math.floor(e-o);s=m[g],g>0&&m.length&&(v=m.indent,i=m[g-1]||m[m.length-1],n=n.substring(i))}}return i+=this.$getStringScreenWidth(n,t-v)[1],this.$useWrapMode&&i>=s&&(i=s-1),p?p.idxToPosition(i):{row:r,column:i}},this.documentToScreenPosition=function(e,t){if(typeof t==\"undefined\")var n=this.$clipPositionToDocument(e.row,e.column);else n=this.$clipPositionToDocument(e,t);e=n.row,t=n.column;var r=0,i=null,s=null;s=this.getFoldAt(e,t,1),s&&(e=s.start.row,t=s.start.column);var o,u=0,a=this.$docRowCache,f=this.$getRowCacheIndex(a,e),l=a.length;if(l&&f>=0)var u=a[f],r=this.$screenRowCache[f],c=e>a[l-1];else var c=!l;var h=this.getNextFoldLine(u),p=h?h.start.row:Infinity;while(u<e){if(u>=p){o=h.end.row+1;if(o>e)break;h=this.getNextFoldLine(o,h),p=h?h.start.row:Infinity}else o=u+1;r+=this.getRowLength(u),u=o,c&&(this.$docRowCache.push(u),this.$screenRowCache.push(r))}var d=\"\";h&&u>=p?(d=this.getFoldDisplayLine(h,e,t),i=h.start.row):(d=this.getLine(e).substring(0,t),i=e);var v=0;if(this.$useWrapMode){var m=this.$wrapData[i];if(m){var g=0;while(d.length>=m[g])r++,g++;d=d.substring(m[g-1]||0,d.length),v=g>0?m.indent:0}}return{row:r,column:v+this.$getStringScreenWidth(d)[0]}},this.documentToScreenColumn=function(e,t){return this.documentToScreenPosition(e,t).column},this.documentToScreenRow=function(e,t){return this.documentToScreenPosition(e,t).row},this.getScreenLength=function(){var e=0,t=null;if(!this.$useWrapMode){e=this.getLength();var n=this.$foldData;for(var r=0;r<n.length;r++)t=n[r],e-=t.end.row-t.start.row}else{var i=this.$wrapData.length,s=0,r=0,t=this.$foldData[r++],o=t?t.start.row:Infinity;while(s<i){var u=this.$wrapData[s];e+=u?u.length+1:1,s++,s>o&&(s=t.end.row+1,t=this.$foldData[r++],o=t?t.start.row:Infinity)}}return this.lineWidgets&&(e+=this.$getWidgetScreenLength()),e},this.$setFontMetrics=function(e){if(!this.$enableVarChar)return;this.$getStringScreenWidth=function(t,n,r){if(n===0)return[0,0];n||(n=Infinity),r=r||0;var i,s;for(s=0;s<t.length;s++){i=t.charAt(s),i===\"\t\"?r+=this.getScreenTabSize(r):r+=e.getCharacterWidth(i);if(r>n)break}return[r,s]}},this.destroy=function(){this.bgTokenizer&&(this.bgTokenizer.setDocument(null),this.bgTokenizer=null),this.$stopWorker()}}).call(p.prototype),e(\"./edit_session/folding\").Folding.call(p.prototype),e(\"./edit_session/bracket_match\").BracketMatch.call(p.prototype),s.defineOptions(p.prototype,\"session\",{wrap:{set:function(e){!e||e==\"off\"?e=!1:e==\"free\"?e=!0:e==\"printMargin\"?e=-1:typeof e==\"string\"&&(e=parseInt(e,10)||!1);if(this.$wrap==e)return;this.$wrap=e;if(!e)this.setUseWrapMode(!1);else{var t=typeof e==\"number\"?e:null;this.setWrapLimitRange(t,t),this.setUseWrapMode(!0)}},get:function(){return this.getUseWrapMode()?this.$wrap==-1?\"printMargin\":this.getWrapLimitRange().min?this.$wrap:\"free\":\"off\"},handlesSet:!0},wrapMethod:{set:function(e){e=e==\"auto\"?this.$mode.type!=\"text\":e!=\"text\",e!=this.$wrapAsCode&&(this.$wrapAsCode=e,this.$useWrapMode&&(this.$modified=!0,this.$resetRowCache(0),this.$updateWrapData(0,this.getLength()-1)))},initialValue:\"auto\"},indentedSoftWrap:{initialValue:!0},firstLineNumber:{set:function(){this._signal(\"changeBreakpoint\")},initialValue:1},useWorker:{set:function(e){this.$useWorker=e,this.$stopWorker(),e&&this.$startWorker()},initialValue:!0},useSoftTabs:{initialValue:!0},tabSize:{set:function(e){if(isNaN(e)||this.$tabSize===e)return;this.$modified=!0,this.$rowLengthCache=[],this.$tabSize=e,this._signal(\"changeTabSize\")},initialValue:4,handlesSet:!0},overwrite:{set:function(e){this._signal(\"changeOverwrite\")},initialValue:!1},newLineMode:{set:function(e){this.doc.setNewLineMode(e)},get:function(){return this.doc.getNewLineMode()},handlesSet:!0},mode:{set:function(e){this.setMode(e)},get:function(){return this.$modeId}}}),t.EditSession=p}),define(\"ace/search\",[\"require\",\"exports\",\"module\",\"ace/lib/lang\",\"ace/lib/oop\",\"ace/range\"],function(e,t,n){\"use strict\";function u(e,t){function n(e){return/\\w/.test(e)||t.regExp?\"\\\\b\":\"\"}return n(e[0])+e+n(e[e.length-1])}var r=e(\"./lib/lang\"),i=e(\"./lib/oop\"),s=e(\"./range\").Range,o=function(){this.$options={}};(function(){this.set=function(e){return i.mixin(this.$options,e),this},this.getOptions=function(){return r.copyObject(this.$options)},this.setOptions=function(e){this.$options=e},this.find=function(e){var t=this.$options,n=this.$matchIterator(e,t);if(!n)return!1;var r=null;return n.forEach(function(e,n,i){if(!e.start){var o=e.offset+(i||0);r=new s(n,o,n,o+e.length);if(!e.length&&t.start&&t.start.start&&t.skipCurrent!=0&&r.isEqual(t.start))return r=null,!1}else r=e;return!0}),r},this.findAll=function(e){var t=this.$options;if(!t.needle)return[];this.$assembleRegExp(t);var n=t.range,i=n?e.getLines(n.start.row,n.end.row):e.doc.getAllLines(),o=[],u=t.re;if(t.$isMultiLine){var a=u.length,f=i.length-a,l;e:for(var c=u.offset||0;c<=f;c++){for(var h=0;h<a;h++)if(i[c+h].search(u[h])==-1)continue e;var p=i[c],d=i[c+a-1],v=p.length-p.match(u[0])[0].length,m=d.match(u[a-1])[0].length;if(l&&l.end.row===c&&l.end.column>v)continue;o.push(l=new s(c,v,c+a-1,m)),a>2&&(c=c+a-2)}}else for(var g=0;g<i.length;g++){var y=r.getMatchOffsets(i[g],u);for(var h=0;h<y.length;h++){var b=y[h];o.push(new s(g,b.offset,g,b.offset+b.length))}}if(n){var w=n.start.column,E=n.start.column,g=0,h=o.length-1;while(g<h&&o[g].start.column<w&&o[g].start.row==n.start.row)g++;while(g<h&&o[h].end.column>E&&o[h].end.row==n.end.row)h--;o=o.slice(g,h+1);for(g=0,h=o.length;g<h;g++)o[g].start.row+=n.start.row,o[g].end.row+=n.start.row}return o},this.replace=function(e,t){var n=this.$options,r=this.$assembleRegExp(n);if(n.$isMultiLine)return t;if(!r)return;var i=r.exec(e);if(!i||i[0].length!=e.length)return null;t=e.replace(r,t);if(n.preserveCase){t=t.split(\"\");for(var s=Math.min(e.length,e.length);s--;){var o=e[s];o&&o.toLowerCase()!=o?t[s]=t[s].toUpperCase():t[s]=t[s].toLowerCase()}t=t.join(\"\")}return t},this.$matchIterator=function(e,t){var n=this.$assembleRegExp(t);if(!n)return!1;var i;if(t.$isMultiLine)var o=n.length,u=function(t,r,u){var a=t.search(n[0]);if(a==-1)return;for(var f=1;f<o;f++){t=e.getLine(r+f);if(t.search(n[f])==-1)return}var l=t.match(n[o-1])[0].length,c=new s(r,a,r+o-1,l);n.offset==1?(c.start.row--,c.start.column=Number.MAX_VALUE):u&&(c.start.column+=u);if(i(c))return!0};else if(t.backwards)var u=function(e,t,s){var o=r.getMatchOffsets(e,n);for(var u=o.length-1;u>=0;u--)if(i(o[u],t,s))return!0};else var u=function(e,t,s){var o=r.getMatchOffsets(e,n);for(var u=0;u<o.length;u++)if(i(o[u],t,s))return!0};var a=this.$lineIterator(e,t);return{forEach:function(e){i=e,a.forEach(u)}}},this.$assembleRegExp=function(e,t){if(e.needle instanceof RegExp)return e.re=e.needle;var n=e.needle;if(!e.needle)return e.re=!1;e.regExp||(n=r.escapeRegExp(n)),e.wholeWord&&(n=u(n,e));var i=e.caseSensitive?\"gm\":\"gmi\";e.$isMultiLine=!t&&/[\\n\\r]/.test(n);if(e.$isMultiLine)return e.re=this.$assembleMultilineRegExp(n,i);try{var s=new RegExp(n,i)}catch(o){s=!1}return e.re=s},this.$assembleMultilineRegExp=function(e,t){var n=e.replace(/\\r\\n|\\r|\\n/g,\"$\\n^\").split(\"\\n\"),r=[];for(var i=0;i<n.length;i++)try{r.push(new RegExp(n[i],t))}catch(s){return!1}return n[0]==\"\"?(r.shift(),r.offset=1):r.offset=0,r},this.$lineIterator=function(e,t){var n=t.backwards==1,r=t.skipCurrent!=0,i=t.range,s=t.start;s||(s=i?i[n?\"end\":\"start\"]:e.selection.getRange()),s.start&&(s=s[r!=n?\"end\":\"start\"]);var o=i?i.start.row:0,u=i?i.end.row:e.getLength()-1,a=n?function(n){var r=s.row,i=e.getLine(r).substring(0,s.column);if(n(i,r))return;for(r--;r>=o;r--)if(n(e.getLine(r),r))return;if(t.wrap==0)return;for(r=u,o=s.row;r>=o;r--)if(n(e.getLine(r),r))return}:function(n){var r=s.row,i=e.getLine(r).substr(s.column);if(n(i,r,s.column))return;for(r+=1;r<=u;r++)if(n(e.getLine(r),r))return;if(t.wrap==0)return;for(r=o,u=s.row;r<=u;r++)if(n(e.getLine(r),r))return};return{forEach:a}}}).call(o.prototype),t.Search=o}),define(\"ace/keyboard/hash_handler\",[\"require\",\"exports\",\"module\",\"ace/lib/keys\",\"ace/lib/useragent\"],function(e,t,n){\"use strict\";function o(e,t){this.platform=t||(i.isMac?\"mac\":\"win\"),this.commands={},this.commandKeyBinding={},this.addCommands(e),this.$singleCommand=!0}function u(e,t){o.call(this,e,t),this.$singleCommand=!1}var r=e(\"../lib/keys\"),i=e(\"../lib/useragent\"),s=r.KEY_MODS;u.prototype=o.prototype,function(){function e(e){return typeof e==\"object\"&&e.bindKey&&e.bindKey.position||0}this.addCommand=function(e){this.commands[e.name]&&this.removeCommand(e),this.commands[e.name]=e,e.bindKey&&this._buildKeyHash(e)},this.removeCommand=function(e,t){var n=e&&(typeof e==\"string\"?e:e.name);e=this.commands[n],t||delete this.commands[n];var r=this.commandKeyBinding;for(var i in r){var s=r[i];if(s==e)delete r[i];else if(Array.isArray(s)){var o=s.indexOf(e);o!=-1&&(s.splice(o,1),s.length==1&&(r[i]=s[0]))}}},this.bindKey=function(e,t,n){typeof e==\"object\"&&e&&(n==undefined&&(n=e.position),e=e[this.platform]);if(!e)return;if(typeof t==\"function\")return this.addCommand({exec:t,bindKey:e,name:t.name||e});e.split(\"|\").forEach(function(e){var r=\"\";if(e.indexOf(\" \")!=-1){var i=e.split(/\\s+/);e=i.pop(),i.forEach(function(e){var t=this.parseKeys(e),n=s[t.hashId]+t.key;r+=(r?\" \":\"\")+n,this._addCommandToBinding(r,\"chainKeys\")},this),r+=\" \"}var o=this.parseKeys(e),u=s[o.hashId]+o.key;this._addCommandToBinding(r+u,t,n)},this)},this._addCommandToBinding=function(t,n,r){var i=this.commandKeyBinding,s;if(!n)delete i[t];else if(!i[t]||this.$singleCommand)i[t]=n;else{Array.isArray(i[t])?(s=i[t].indexOf(n))!=-1&&i[t].splice(s,1):i[t]=[i[t]],typeof r!=\"number\"&&(r||n.isDefault?r=-100:r=e(n));var o=i[t];for(s=0;s<o.length;s++){var u=o[s],a=e(u);if(a>r)break}o.splice(s,0,n)}},this.addCommands=function(e){e&&Object.keys(e).forEach(function(t){var n=e[t];if(!n)return;if(typeof n==\"string\")return this.bindKey(n,t);typeof n==\"function\"&&(n={exec:n});if(typeof n!=\"object\")return;n.name||(n.name=t),this.addCommand(n)},this)},this.removeCommands=function(e){Object.keys(e).forEach(function(t){this.removeCommand(e[t])},this)},this.bindKeys=function(e){Object.keys(e).forEach(function(t){this.bindKey(t,e[t])},this)},this._buildKeyHash=function(e){this.bindKey(e.bindKey,e)},this.parseKeys=function(e){var t=e.toLowerCase().split(/[\\-\\+]([\\-\\+])?/).filter(function(e){return e}),n=t.pop(),i=r[n];if(r.FUNCTION_KEYS[i])n=r.FUNCTION_KEYS[i].toLowerCase();else{if(!t.length)return{key:n,hashId:-1};if(t.length==1&&t[0]==\"shift\")return{key:n.toUpperCase(),hashId:-1}}var s=0;for(var o=t.length;o--;){var u=r.KEY_MODS[t[o]];if(u==null)return typeof console!=\"undefined\"&&console.error(\"invalid modifier \"+t[o]+\" in \"+e),!1;s|=u}return{key:n,hashId:s}},this.findKeyCommand=function(t,n){var r=s[t]+n;return this.commandKeyBinding[r]},this.handleKeyboard=function(e,t,n,r){if(r<0)return;var i=s[t]+n,o=this.commandKeyBinding[i];e.$keyChain&&(e.$keyChain+=\" \"+i,o=this.commandKeyBinding[e.$keyChain]||o);if(o)if(o==\"chainKeys\"||o[o.length-1]==\"chainKeys\")return e.$keyChain=e.$keyChain||i,{command:\"null\"};if(e.$keyChain)if(!!t&&t!=4||n.length!=1){if(t==-1||r>0)e.$keyChain=\"\"}else e.$keyChain=e.$keyChain.slice(0,-i.length-1);return{command:o}},this.getStatusText=function(e,t){return t.$keyChain||\"\"}}.call(o.prototype),t.HashHandler=o,t.MultiHashHandler=u}),define(\"ace/commands/command_manager\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/keyboard/hash_handler\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../keyboard/hash_handler\").MultiHashHandler,s=e(\"../lib/event_emitter\").EventEmitter,o=function(e,t){i.call(this,t,e),this.byName=this.commands,this.setDefaultHandler(\"exec\",function(e){return e.command.exec(e.editor,e.args||{})})};r.inherits(o,i),function(){r.implement(this,s),this.exec=function(e,t,n){if(Array.isArray(e)){for(var r=e.length;r--;)if(this.exec(e[r],t,n))return!0;return!1}typeof e==\"string\"&&(e=this.commands[e]);if(!e)return!1;if(t&&t.$readOnly&&!e.readOnly)return!1;var i={editor:t,command:e,args:n};return i.returnValue=this._emit(\"exec\",i),this._signal(\"afterExec\",i),i.returnValue===!1?!1:!0},this.toggleRecording=function(e){if(this.$inReplay)return;return e&&e._emit(\"changeStatus\"),this.recording?(this.macro.pop(),this.removeEventListener(\"exec\",this.$addCommandToMacro),this.macro.length||(this.macro=this.oldMacro),this.recording=!1):(this.$addCommandToMacro||(this.$addCommandToMacro=function(e){this.macro.push([e.command,e.args])}.bind(this)),this.oldMacro=this.macro,this.macro=[],this.on(\"exec\",this.$addCommandToMacro),this.recording=!0)},this.replay=function(e){if(this.$inReplay||!this.macro)return;if(this.recording)return this.toggleRecording(e);try{this.$inReplay=!0,this.macro.forEach(function(t){typeof t==\"string\"?this.exec(t,e):this.exec(t[0],e,t[1])},this)}finally{this.$inReplay=!1}},this.trimMacro=function(e){return e.map(function(e){return typeof e[0]!=\"string\"&&(e[0]=e[0].name),e[1]||(e=e[0]),e})}}.call(o.prototype),t.CommandManager=o}),define(\"ace/commands/default_commands\",[\"require\",\"exports\",\"module\",\"ace/lib/lang\",\"ace/config\",\"ace/range\"],function(e,t,n){\"use strict\";function o(e,t){return{win:e,mac:t}}var r=e(\"../lib/lang\"),i=e(\"../config\"),s=e(\"../range\").Range;t.commands=[{name:\"showSettingsMenu\",bindKey:o(\"Ctrl-,\",\"Command-,\"),exec:function(e){i.loadModule(\"ace/ext/settings_menu\",function(t){t.init(e),e.showSettingsMenu()})},readOnly:!0},{name:\"goToNextError\",bindKey:o(\"Alt-E\",\"F4\"),exec:function(e){i.loadModule(\"ace/ext/error_marker\",function(t){t.showErrorMarker(e,1)})},scrollIntoView:\"animate\",readOnly:!0},{name:\"goToPreviousError\",bindKey:o(\"Alt-Shift-E\",\"Shift-F4\"),exec:function(e){i.loadModule(\"ace/ext/error_marker\",function(t){t.showErrorMarker(e,-1)})},scrollIntoView:\"animate\",readOnly:!0},{name:\"selectall\",bindKey:o(\"Ctrl-A\",\"Command-A\"),exec:function(e){e.selectAll()},readOnly:!0},{name:\"centerselection\",bindKey:o(null,\"Ctrl-L\"),exec:function(e){e.centerSelection()},readOnly:!0},{name:\"gotoline\",bindKey:o(\"Ctrl-L\",\"Command-L\"),exec:function(e){var t=parseInt(prompt(\"Enter line number:\"),10);isNaN(t)||e.gotoLine(t)},readOnly:!0},{name:\"fold\",bindKey:o(\"Alt-L|Ctrl-F1\",\"Command-Alt-L|Command-F1\"),exec:function(e){e.session.toggleFold(!1)},multiSelectAction:\"forEach\",scrollIntoView:\"center\",readOnly:!0},{name:\"unfold\",bindKey:o(\"Alt-Shift-L|Ctrl-Shift-F1\",\"Command-Alt-Shift-L|Command-Shift-F1\"),exec:function(e){e.session.toggleFold(!0)},multiSelectAction:\"forEach\",scrollIntoView:\"center\",readOnly:!0},{name:\"toggleFoldWidget\",bindKey:o(\"F2\",\"F2\"),exec:function(e){e.session.toggleFoldWidget()},multiSelectAction:\"forEach\",scrollIntoView:\"center\",readOnly:!0},{name:\"toggleParentFoldWidget\",bindKey:o(\"Alt-F2\",\"Alt-F2\"),exec:function(e){e.session.toggleFoldWidget(!0)},multiSelectAction:\"forEach\",scrollIntoView:\"center\",readOnly:!0},{name:\"foldall\",bindKey:o(null,\"Ctrl-Command-Option-0\"),exec:function(e){e.session.foldAll()},scrollIntoView:\"center\",readOnly:!0},{name:\"foldOther\",bindKey:o(\"Alt-0\",\"Command-Option-0\"),exec:function(e){e.session.foldAll(),e.session.unfold(e.selection.getAllRanges())},scrollIntoView:\"center\",readOnly:!0},{name:\"unfoldall\",bindKey:o(\"Alt-Shift-0\",\"Command-Option-Shift-0\"),exec:function(e){e.session.unfold()},scrollIntoView:\"center\",readOnly:!0},{name:\"findnext\",bindKey:o(\"Ctrl-K\",\"Command-G\"),exec:function(e){e.findNext()},multiSelectAction:\"forEach\",scrollIntoView:\"center\",readOnly:!0},{name:\"findprevious\",bindKey:o(\"Ctrl-Shift-K\",\"Command-Shift-G\"),exec:function(e){e.findPrevious()},multiSelectAction:\"forEach\",scrollIntoView:\"center\",readOnly:!0},{name:\"selectOrFindNext\",bindKey:o(\"Alt-K\",\"Ctrl-G\"),exec:function(e){e.selection.isEmpty()?e.selection.selectWord():e.findNext()},readOnly:!0},{name:\"selectOrFindPrevious\",bindKey:o(\"Alt-Shift-K\",\"Ctrl-Shift-G\"),exec:function(e){e.selection.isEmpty()?e.selection.selectWord():e.findPrevious()},readOnly:!0},{name:\"find\",bindKey:o(\"Ctrl-F\",\"Command-F\"),exec:function(e){i.loadModule(\"ace/ext/searchbox\",function(t){t.Search(e)})},readOnly:!0},{name:\"overwrite\",bindKey:\"Insert\",exec:function(e){e.toggleOverwrite()},readOnly:!0},{name:\"selecttostart\",bindKey:o(\"Ctrl-Shift-Home\",\"Command-Shift-Home|Command-Shift-Up\"),exec:function(e){e.getSelection().selectFileStart()},multiSelectAction:\"forEach\",readOnly:!0,scrollIntoView:\"animate\",aceCommandGroup:\"fileJump\"},{name:\"gotostart\",bindKey:o(\"Ctrl-Home\",\"Command-Home|Command-Up\"),exec:function(e){e.navigateFileStart()},multiSelectAction:\"forEach\",readOnly:!0,scrollIntoView:\"animate\",aceCommandGroup:\"fileJump\"},{name:\"selectup\",bindKey:o(\"Shift-Up\",\"Shift-Up|Ctrl-Shift-P\"),exec:function(e){e.getSelection().selectUp()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"golineup\",bindKey:o(\"Up\",\"Up|Ctrl-P\"),exec:function(e,t){e.navigateUp(t.times)},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"selecttoend\",bindKey:o(\"Ctrl-Shift-End\",\"Command-Shift-End|Command-Shift-Down\"),exec:function(e){e.getSelection().selectFileEnd()},multiSelectAction:\"forEach\",readOnly:!0,scrollIntoView:\"animate\",aceCommandGroup:\"fileJump\"},{name:\"gotoend\",bindKey:o(\"Ctrl-End\",\"Command-End|Command-Down\"),exec:function(e){e.navigateFileEnd()},multiSelectAction:\"forEach\",readOnly:!0,scrollIntoView:\"animate\",aceCommandGroup:\"fileJump\"},{name:\"selectdown\",bindKey:o(\"Shift-Down\",\"Shift-Down|Ctrl-Shift-N\"),exec:function(e){e.getSelection().selectDown()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"golinedown\",bindKey:o(\"Down\",\"Down|Ctrl-N\"),exec:function(e,t){e.navigateDown(t.times)},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"selectwordleft\",bindKey:o(\"Ctrl-Shift-Left\",\"Option-Shift-Left\"),exec:function(e){e.getSelection().selectWordLeft()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"gotowordleft\",bindKey:o(\"Ctrl-Left\",\"Option-Left\"),exec:function(e){e.navigateWordLeft()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"selecttolinestart\",bindKey:o(\"Alt-Shift-Left\",\"Command-Shift-Left|Ctrl-Shift-A\"),exec:function(e){e.getSelection().selectLineStart()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"gotolinestart\",bindKey:o(\"Alt-Left|Home\",\"Command-Left|Home|Ctrl-A\"),exec:function(e){e.navigateLineStart()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"selectleft\",bindKey:o(\"Shift-Left\",\"Shift-Left|Ctrl-Shift-B\"),exec:function(e){e.getSelection().selectLeft()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"gotoleft\",bindKey:o(\"Left\",\"Left|Ctrl-B\"),exec:function(e,t){e.navigateLeft(t.times)},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"selectwordright\",bindKey:o(\"Ctrl-Shift-Right\",\"Option-Shift-Right\"),exec:function(e){e.getSelection().selectWordRight()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"gotowordright\",bindKey:o(\"Ctrl-Right\",\"Option-Right\"),exec:function(e){e.navigateWordRight()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"selecttolineend\",bindKey:o(\"Alt-Shift-Right\",\"Command-Shift-Right|Shift-End|Ctrl-Shift-E\"),exec:function(e){e.getSelection().selectLineEnd()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"gotolineend\",bindKey:o(\"Alt-Right|End\",\"Command-Right|End|Ctrl-E\"),exec:function(e){e.navigateLineEnd()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"selectright\",bindKey:o(\"Shift-Right\",\"Shift-Right\"),exec:function(e){e.getSelection().selectRight()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"gotoright\",bindKey:o(\"Right\",\"Right|Ctrl-F\"),exec:function(e,t){e.navigateRight(t.times)},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"selectpagedown\",bindKey:\"Shift-PageDown\",exec:function(e){e.selectPageDown()},readOnly:!0},{name:\"pagedown\",bindKey:o(null,\"Option-PageDown\"),exec:function(e){e.scrollPageDown()},readOnly:!0},{name:\"gotopagedown\",bindKey:o(\"PageDown\",\"PageDown|Ctrl-V\"),exec:function(e){e.gotoPageDown()},readOnly:!0},{name:\"selectpageup\",bindKey:\"Shift-PageUp\",exec:function(e){e.selectPageUp()},readOnly:!0},{name:\"pageup\",bindKey:o(null,\"Option-PageUp\"),exec:function(e){e.scrollPageUp()},readOnly:!0},{name:\"gotopageup\",bindKey:\"PageUp\",exec:function(e){e.gotoPageUp()},readOnly:!0},{name:\"scrollup\",bindKey:o(\"Ctrl-Up\",null),exec:function(e){e.renderer.scrollBy(0,-2*e.renderer.layerConfig.lineHeight)},readOnly:!0},{name:\"scrolldown\",bindKey:o(\"Ctrl-Down\",null),exec:function(e){e.renderer.scrollBy(0,2*e.renderer.layerConfig.lineHeight)},readOnly:!0},{name:\"selectlinestart\",bindKey:\"Shift-Home\",exec:function(e){e.getSelection().selectLineStart()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"selectlineend\",bindKey:\"Shift-End\",exec:function(e){e.getSelection().selectLineEnd()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"togglerecording\",bindKey:o(\"Ctrl-Alt-E\",\"Command-Option-E\"),exec:function(e){e.commands.toggleRecording(e)},readOnly:!0},{name:\"replaymacro\",bindKey:o(\"Ctrl-Shift-E\",\"Command-Shift-E\"),exec:function(e){e.commands.replay(e)},readOnly:!0},{name:\"jumptomatching\",bindKey:o(\"Ctrl-P\",\"Ctrl-P\"),exec:function(e){e.jumpToMatching()},multiSelectAction:\"forEach\",scrollIntoView:\"animate\",readOnly:!0},{name:\"selecttomatching\",bindKey:o(\"Ctrl-Shift-P\",\"Ctrl-Shift-P\"),exec:function(e){e.jumpToMatching(!0)},multiSelectAction:\"forEach\",scrollIntoView:\"animate\",readOnly:!0},{name:\"expandToMatching\",bindKey:o(\"Ctrl-Shift-M\",\"Ctrl-Shift-M\"),exec:function(e){e.jumpToMatching(!0,!0)},multiSelectAction:\"forEach\",scrollIntoView:\"animate\",readOnly:!0},{name:\"passKeysToBrowser\",bindKey:o(null,null),exec:function(){},passEvent:!0,readOnly:!0},{name:\"copy\",exec:function(e){},readOnly:!0},{name:\"cut\",exec:function(e){var t=e.getSelectionRange();e._emit(\"cut\",t),e.selection.isEmpty()||(e.session.remove(t),e.clearSelection())},scrollIntoView:\"cursor\",multiSelectAction:\"forEach\"},{name:\"paste\",exec:function(e,t){e.$handlePaste(t)},scrollIntoView:\"cursor\"},{name:\"removeline\",bindKey:o(\"Ctrl-D\",\"Command-D\"),exec:function(e){e.removeLines()},scrollIntoView:\"cursor\",multiSelectAction:\"forEachLine\"},{name:\"duplicateSelection\",bindKey:o(\"Ctrl-Shift-D\",\"Command-Shift-D\"),exec:function(e){e.duplicateSelection()},scrollIntoView:\"cursor\",multiSelectAction:\"forEach\"},{name:\"sortlines\",bindKey:o(\"Ctrl-Alt-S\",\"Command-Alt-S\"),exec:function(e){e.sortLines()},scrollIntoView:\"selection\",multiSelectAction:\"forEachLine\"},{name:\"togglecomment\",bindKey:o(\"Ctrl-/\",\"Command-/\"),exec:function(e){e.toggleCommentLines()},multiSelectAction:\"forEachLine\",scrollIntoView:\"selectionPart\"},{name:\"toggleBlockComment\",bindKey:o(\"Ctrl-Shift-/\",\"Command-Shift-/\"),exec:function(e){e.toggleBlockComment()},multiSelectAction:\"forEach\",scrollIntoView:\"selectionPart\"},{name:\"modifyNumberUp\",bindKey:o(\"Ctrl-Shift-Up\",\"Alt-Shift-Up\"),exec:function(e){e.modifyNumber(1)},scrollIntoView:\"cursor\",multiSelectAction:\"forEach\"},{name:\"modifyNumberDown\",bindKey:o(\"Ctrl-Shift-Down\",\"Alt-Shift-Down\"),exec:function(e){e.modifyNumber(-1)},scrollIntoView:\"cursor\",multiSelectAction:\"forEach\"},{name:\"replace\",bindKey:o(\"Ctrl-H\",\"Command-Option-F\"),exec:function(e){i.loadModule(\"ace/ext/searchbox\",function(t){t.Search(e,!0)})}},{name:\"undo\",bindKey:o(\"Ctrl-Z\",\"Command-Z\"),exec:function(e){e.undo()}},{name:\"redo\",bindKey:o(\"Ctrl-Shift-Z|Ctrl-Y\",\"Command-Shift-Z|Command-Y\"),exec:function(e){e.redo()}},{name:\"copylinesup\",bindKey:o(\"Alt-Shift-Up\",\"Command-Option-Up\"),exec:function(e){e.copyLinesUp()},scrollIntoView:\"cursor\"},{name:\"movelinesup\",bindKey:o(\"Alt-Up\",\"Option-Up\"),exec:function(e){e.moveLinesUp()},scrollIntoView:\"cursor\"},{name:\"copylinesdown\",bindKey:o(\"Alt-Shift-Down\",\"Command-Option-Down\"),exec:function(e){e.copyLinesDown()},scrollIntoView:\"cursor\"},{name:\"movelinesdown\",bindKey:o(\"Alt-Down\",\"Option-Down\"),exec:function(e){e.moveLinesDown()},scrollIntoView:\"cursor\"},{name:\"del\",bindKey:o(\"Delete\",\"Delete|Ctrl-D|Shift-Delete\"),exec:function(e){e.remove(\"right\")},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"backspace\",bindKey:o(\"Shift-Backspace|Backspace\",\"Ctrl-Backspace|Shift-Backspace|Backspace|Ctrl-H\"),exec:function(e){e.remove(\"left\")},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"cut_or_delete\",bindKey:o(\"Shift-Delete\",null),exec:function(e){if(!e.selection.isEmpty())return!1;e.remove(\"left\")},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"removetolinestart\",bindKey:o(\"Alt-Backspace\",\"Command-Backspace\"),exec:function(e){e.removeToLineStart()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"removetolineend\",bindKey:o(\"Alt-Delete\",\"Ctrl-K\"),exec:function(e){e.removeToLineEnd()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"removewordleft\",bindKey:o(\"Ctrl-Backspace\",\"Alt-Backspace|Ctrl-Alt-Backspace\"),exec:function(e){e.removeWordLeft()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"removewordright\",bindKey:o(\"Ctrl-Delete\",\"Alt-Delete\"),exec:function(e){e.removeWordRight()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"outdent\",bindKey:o(\"Shift-Tab\",\"Shift-Tab\"),exec:function(e){e.blockOutdent()},multiSelectAction:\"forEach\",scrollIntoView:\"selectionPart\"},{name:\"indent\",bindKey:o(\"Tab\",\"Tab\"),exec:function(e){e.indent()},multiSelectAction:\"forEach\",scrollIntoView:\"selectionPart\"},{name:\"blockoutdent\",bindKey:o(\"Ctrl-[\",\"Ctrl-[\"),exec:function(e){e.blockOutdent()},multiSelectAction:\"forEachLine\",scrollIntoView:\"selectionPart\"},{name:\"blockindent\",bindKey:o(\"Ctrl-]\",\"Ctrl-]\"),exec:function(e){e.blockIndent()},multiSelectAction:\"forEachLine\",scrollIntoView:\"selectionPart\"},{name:\"insertstring\",exec:function(e,t){e.insert(t)},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"inserttext\",exec:function(e,t){e.insert(r.stringRepeat(t.text||\"\",t.times||1))},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"splitline\",bindKey:o(null,\"Ctrl-O\"),exec:function(e){e.splitLine()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"transposeletters\",bindKey:o(\"Ctrl-T\",\"Ctrl-T\"),exec:function(e){e.transposeLetters()},multiSelectAction:function(e){e.transposeSelections(1)},scrollIntoView:\"cursor\"},{name:\"touppercase\",bindKey:o(\"Ctrl-U\",\"Ctrl-U\"),exec:function(e){e.toUpperCase()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"tolowercase\",bindKey:o(\"Ctrl-Shift-U\",\"Ctrl-Shift-U\"),exec:function(e){e.toLowerCase()},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\"},{name:\"expandtoline\",bindKey:o(\"Ctrl-Shift-L\",\"Command-Shift-L\"),exec:function(e){var t=e.selection.getRange();t.start.column=t.end.column=0,t.end.row++,e.selection.setRange(t,!1)},multiSelectAction:\"forEach\",scrollIntoView:\"cursor\",readOnly:!0},{name:\"joinlines\",bindKey:o(null,null),exec:function(e){var t=e.selection.isBackwards(),n=t?e.selection.getSelectionLead():e.selection.getSelectionAnchor(),i=t?e.selection.getSelectionAnchor():e.selection.getSelectionLead(),o=e.session.doc.getLine(n.row).length,u=e.session.doc.getTextRange(e.selection.getRange()),a=u.replace(/\\n\\s*/,\" \").length,f=e.session.doc.getLine(n.row);for(var l=n.row+1;l<=i.row+1;l++){var c=r.stringTrimLeft(r.stringTrimRight(e.session.doc.getLine(l)));c.length!==0&&(c=\" \"+c),f+=c}i.row+1<e.session.doc.getLength()-1&&(f+=e.session.doc.getNewLineCharacter()),e.clearSelection(),e.session.doc.replace(new s(n.row,0,i.row+2,0),f),a>0?(e.selection.moveCursorTo(n.row,n.column),e.selection.selectTo(n.row,n.column+a)):(o=e.session.doc.getLine(n.row).length>o?o+1:o,e.selection.moveCursorTo(n.row,o))},multiSelectAction:\"forEach\",readOnly:!0},{name:\"invertSelection\",bindKey:o(null,null),exec:function(e){var t=e.session.doc.getLength()-1,n=e.session.doc.getLine(t).length,r=e.selection.rangeList.ranges,i=[];r.length<1&&(r=[e.selection.getRange()]);for(var o=0;o<r.length;o++)o==r.length-1&&(r[o].end.row!==t||r[o].end.column!==n)&&i.push(new s(r[o].end.row,r[o].end.column,t,n)),o===0?(r[o].start.row!==0||r[o].start.column!==0)&&i.push(new s(0,0,r[o].start.row,r[o].start.column)):i.push(new s(r[o-1].end.row,r[o-1].end.column,r[o].start.row,r[o].start.column));e.exitMultiSelectMode(),e.clearSelection();for(var o=0;o<i.length;o++)e.selection.addRange(i[o],!1)},readOnly:!0,scrollIntoView:\"none\"}]}),define(\"ace/editor\",[\"require\",\"exports\",\"module\",\"ace/lib/fixoldbrowsers\",\"ace/lib/oop\",\"ace/lib/dom\",\"ace/lib/lang\",\"ace/lib/useragent\",\"ace/keyboard/textinput\",\"ace/mouse/mouse_handler\",\"ace/mouse/fold_handler\",\"ace/keyboard/keybinding\",\"ace/edit_session\",\"ace/search\",\"ace/range\",\"ace/lib/event_emitter\",\"ace/commands/command_manager\",\"ace/commands/default_commands\",\"ace/config\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";e(\"./lib/fixoldbrowsers\");var r=e(\"./lib/oop\"),i=e(\"./lib/dom\"),s=e(\"./lib/lang\"),o=e(\"./lib/useragent\"),u=e(\"./keyboard/textinput\").TextInput,a=e(\"./mouse/mouse_handler\").MouseHandler,f=e(\"./mouse/fold_handler\").FoldHandler,l=e(\"./keyboard/keybinding\").KeyBinding,c=e(\"./edit_session\").EditSession,h=e(\"./search\").Search,p=e(\"./range\").Range,d=e(\"./lib/event_emitter\").EventEmitter,v=e(\"./commands/command_manager\").CommandManager,m=e(\"./commands/default_commands\").commands,g=e(\"./config\"),y=e(\"./token_iterator\").TokenIterator,b=function(e,t){var n=e.getContainerElement();this.container=n,this.renderer=e,this.commands=new v(o.isMac?\"mac\":\"win\",m),this.textInput=new u(e.getTextAreaContainer(),this),this.renderer.textarea=this.textInput.getElement(),this.keyBinding=new l(this),this.$mouseHandler=new a(this),new f(this),this.$blockScrolling=0,this.$search=(new h).set({wrap:!0}),this.$historyTracker=this.$historyTracker.bind(this),this.commands.on(\"exec\",this.$historyTracker),this.$initOperationListeners(),this._$emitInputEvent=s.delayedCall(function(){this._signal(\"input\",{}),this.session&&this.session.bgTokenizer&&this.session.bgTokenizer.scheduleStart()}.bind(this)),this.on(\"change\",function(e,t){t._$emitInputEvent.schedule(31)}),this.setSession(t||new c(\"\")),g.resetOptions(this),g._signal(\"editor\",this)};(function(){r.implement(this,d),this.$initOperationListeners=function(){function e(e){return e[e.length-1]}this.selections=[],this.commands.on(\"exec\",this.startOperation.bind(this),!0),this.commands.on(\"afterExec\",this.endOperation.bind(this),!0),this.$opResetTimer=s.delayedCall(this.endOperation.bind(this)),this.on(\"change\",function(){this.curOp||this.startOperation(),this.curOp.docChanged=!0}.bind(this),!0),this.on(\"changeSelection\",function(){this.curOp||this.startOperation(),this.curOp.selectionChanged=!0}.bind(this),!0)},this.curOp=null,this.prevOp={},this.startOperation=function(e){if(this.curOp){if(!e||this.curOp.command)return;this.prevOp=this.curOp}e||(this.previousCommand=null,e={}),this.$opResetTimer.schedule(),this.curOp={command:e.command||{},args:e.args,scrollTop:this.renderer.scrollTop},this.curOp.command.name&&this.curOp.command.scrollIntoView!==undefined&&this.$blockScrolling++},this.endOperation=function(e){if(this.curOp){if(e&&e.returnValue===!1)return this.curOp=null;this._signal(\"beforeEndOperation\");var t=this.curOp.command;t.name&&this.$blockScrolling>0&&this.$blockScrolling--;var n=t&&t.scrollIntoView;if(n){switch(n){case\"center-animate\":n=\"animate\";case\"center\":this.renderer.scrollCursorIntoView(null,.5);break;case\"animate\":case\"cursor\":this.renderer.scrollCursorIntoView();break;case\"selectionPart\":var r=this.selection.getRange(),i=this.renderer.layerConfig;(r.start.row>=i.lastRow||r.end.row<=i.firstRow)&&this.renderer.scrollSelectionIntoView(this.selection.anchor,this.selection.lead);break;default:}n==\"animate\"&&this.renderer.animateScrolling(this.curOp.scrollTop)}this.prevOp=this.curOp,this.curOp=null}},this.$mergeableCommands=[\"backspace\",\"del\",\"insertstring\"],this.$historyTracker=function(e){if(!this.$mergeUndoDeltas)return;var t=this.prevOp,n=this.$mergeableCommands,r=t.command&&e.command.name==t.command.name;if(e.command.name==\"insertstring\"){var i=e.args;this.mergeNextCommand===undefined&&(this.mergeNextCommand=!0),r=r&&this.mergeNextCommand&&(!/\\s/.test(i)||/\\s/.test(t.args)),this.mergeNextCommand=!0}else r=r&&n.indexOf(e.command.name)!==-1;this.$mergeUndoDeltas!=\"always\"&&Date.now()-this.sequenceStartTime>2e3&&(r=!1),r?this.session.mergeUndoDeltas=!0:n.indexOf(e.command.name)!==-1&&(this.sequenceStartTime=Date.now())},this.setKeyboardHandler=function(e,t){if(e&&typeof e==\"string\"){this.$keybindingId=e;var n=this;g.loadModule([\"keybinding\",e],function(r){n.$keybindingId==e&&n.keyBinding.setKeyboardHandler(r&&r.handler),t&&t()})}else this.$keybindingId=null,this.keyBinding.setKeyboardHandler(e),t&&t()},this.getKeyboardHandler=function(){return this.keyBinding.getKeyboardHandler()},this.setSession=function(e){if(this.session==e)return;this.curOp&&this.endOperation(),this.curOp={};var t=this.session;if(t){this.session.off(\"change\",this.$onDocumentChange),this.session.off(\"changeMode\",this.$onChangeMode),this.session.off(\"tokenizerUpdate\",this.$onTokenizerUpdate),this.session.off(\"changeTabSize\",this.$onChangeTabSize),this.session.off(\"changeWrapLimit\",this.$onChangeWrapLimit),this.session.off(\"changeWrapMode\",this.$onChangeWrapMode),this.session.off(\"changeFold\",this.$onChangeFold),this.session.off(\"changeFrontMarker\",this.$onChangeFrontMarker),this.session.off(\"changeBackMarker\",this.$onChangeBackMarker),this.session.off(\"changeBreakpoint\",this.$onChangeBreakpoint),this.session.off(\"changeAnnotation\",this.$onChangeAnnotation),this.session.off(\"changeOverwrite\",this.$onCursorChange),this.session.off(\"changeScrollTop\",this.$onScrollTopChange),this.session.off(\"changeScrollLeft\",this.$onScrollLeftChange);var n=this.session.getSelection();n.off(\"changeCursor\",this.$onCursorChange),n.off(\"changeSelection\",this.$onSelectionChange)}this.session=e,e?(this.$onDocumentChange=this.onDocumentChange.bind(this),e.on(\"change\",this.$onDocumentChange),this.renderer.setSession(e),this.$onChangeMode=this.onChangeMode.bind(this),e.on(\"changeMode\",this.$onChangeMode),this.$onTokenizerUpdate=this.onTokenizerUpdate.bind(this),e.on(\"tokenizerUpdate\",this.$onTokenizerUpdate),this.$onChangeTabSize=this.renderer.onChangeTabSize.bind(this.renderer),e.on(\"changeTabSize\",this.$onChangeTabSize),this.$onChangeWrapLimit=this.onChangeWrapLimit.bind(this),e.on(\"changeWrapLimit\",this.$onChangeWrapLimit),this.$onChangeWrapMode=this.onChangeWrapMode.bind(this),e.on(\"changeWrapMode\",this.$onChangeWrapMode),this.$onChangeFold=this.onChangeFold.bind(this),e.on(\"changeFold\",this.$onChangeFold),this.$onChangeFrontMarker=this.onChangeFrontMarker.bind(this),this.session.on(\"changeFrontMarker\",this.$onChangeFrontMarker),this.$onChangeBackMarker=this.onChangeBackMarker.bind(this),this.session.on(\"changeBackMarker\",this.$onChangeBackMarker),this.$onChangeBreakpoint=this.onChangeBreakpoint.bind(this),this.session.on(\"changeBreakpoint\",this.$onChangeBreakpoint),this.$onChangeAnnotation=this.onChangeAnnotation.bind(this),this.session.on(\"changeAnnotation\",this.$onChangeAnnotation),this.$onCursorChange=this.onCursorChange.bind(this),this.session.on(\"changeOverwrite\",this.$onCursorChange),this.$onScrollTopChange=this.onScrollTopChange.bind(this),this.session.on(\"changeScrollTop\",this.$onScrollTopChange),this.$onScrollLeftChange=this.onScrollLeftChange.bind(this),this.session.on(\"changeScrollLeft\",this.$onScrollLeftChange),this.selection=e.getSelection(),this.selection.on(\"changeCursor\",this.$onCursorChange),this.$onSelectionChange=this.onSelectionChange.bind(this),this.selection.on(\"changeSelection\",this.$onSelectionChange),this.onChangeMode(),this.$blockScrolling+=1,this.onCursorChange(),this.$blockScrolling-=1,this.onScrollTopChange(),this.onScrollLeftChange(),this.onSelectionChange(),this.onChangeFrontMarker(),this.onChangeBackMarker(),this.onChangeBreakpoint(),this.onChangeAnnotation(),this.session.getUseWrapMode()&&this.renderer.adjustWrapLimit(),this.renderer.updateFull()):(this.selection=null,this.renderer.setSession(e)),this._signal(\"changeSession\",{session:e,oldSession:t}),this.curOp=null,t&&t._signal(\"changeEditor\",{oldEditor:this}),e&&e._signal(\"changeEditor\",{editor:this})},this.getSession=function(){return this.session},this.setValue=function(e,t){return this.session.doc.setValue(e),t?t==1?this.navigateFileEnd():t==-1&&this.navigateFileStart():this.selectAll(),e},this.getValue=function(){return this.session.getValue()},this.getSelection=function(){return this.selection},this.resize=function(e){this.renderer.onResize(e)},this.setTheme=function(e,t){this.renderer.setTheme(e,t)},this.getTheme=function(){return this.renderer.getTheme()},this.setStyle=function(e){this.renderer.setStyle(e)},this.unsetStyle=function(e){this.renderer.unsetStyle(e)},this.getFontSize=function(){return this.getOption(\"fontSize\")||i.computedStyle(this.container,\"fontSize\")},this.setFontSize=function(e){this.setOption(\"fontSize\",e)},this.$highlightBrackets=function(){this.session.$bracketHighlight&&(this.session.removeMarker(this.session.$bracketHighlight),this.session.$bracketHighlight=null);if(this.$highlightPending)return;var e=this;this.$highlightPending=!0,setTimeout(function(){e.$highlightPending=!1;var t=e.session;if(!t||!t.bgTokenizer)return;var n=t.findMatchingBracket(e.getCursorPosition());if(n)var r=new p(n.row,n.column,n.row,n.column+1);else if(t.$mode.getMatching)var r=t.$mode.getMatching(e.session);r&&(t.$bracketHighlight=t.addMarker(r,\"ace_bracket\",\"text\"))},50)},this.$highlightTags=function(){if(this.$highlightTagPending)return;var e=this;this.$highlightTagPending=!0,setTimeout(function(){e.$highlightTagPending=!1;var t=e.session;if(!t||!t.bgTokenizer)return;var n=e.getCursorPosition(),r=new y(e.session,n.row,n.column),i=r.getCurrentToken();if(!i||!/\\b(?:tag-open|tag-name)/.test(i.type)){t.removeMarker(t.$tagHighlight),t.$tagHighlight=null;return}if(i.type.indexOf(\"tag-open\")!=-1){i=r.stepForward();if(!i)return}var s=i.value,o=0,u=r.stepBackward();if(u.value==\"<\"){do u=i,i=r.stepForward(),i&&i.value===s&&i.type.indexOf(\"tag-name\")!==-1&&(u.value===\"<\"?o++:u.value===\"</\"&&o--);while(i&&o>=0)}else{do i=u,u=r.stepBackward(),i&&i.value===s&&i.type.indexOf(\"tag-name\")!==-1&&(u.value===\"<\"?o++:u.value===\"</\"&&o--);while(u&&o<=0);r.stepForward()}if(!i){t.removeMarker(t.$tagHighlight),t.$tagHighlight=null;return}var a=r.getCurrentTokenRow(),f=r.getCurrentTokenColumn(),l=new p(a,f,a,f+i.value.length),c=t.$backMarkers[t.$tagHighlight];t.$tagHighlight&&c!=undefined&&l.compareRange(c.range)!==0&&(t.removeMarker(t.$tagHighlight),t.$tagHighlight=null),l&&!t.$tagHighlight&&(t.$tagHighlight=t.addMarker(l,\"ace_bracket\",\"text\"))},50)},this.focus=function(){var e=this;setTimeout(function(){e.textInput.focus()}),this.textInput.focus()},this.isFocused=function(){return this.textInput.isFocused()},this.blur=function(){this.textInput.blur()},this.onFocus=function(e){if(this.$isFocused)return;this.$isFocused=!0,this.renderer.showCursor(),this.renderer.visualizeFocus(),this._emit(\"focus\",e)},this.onBlur=function(e){if(!this.$isFocused)return;this.$isFocused=!1,this.renderer.hideCursor(),this.renderer.visualizeBlur(),this._emit(\"blur\",e)},this.$cursorChange=function(){this.renderer.updateCursor()},this.onDocumentChange=function(e){var t=this.session.$useWrapMode,n=e.start.row==e.end.row?e.end.row:Infinity;this.renderer.updateLines(e.start.row,n,t),this._signal(\"change\",e),this.$cursorChange(),this.$updateHighlightActiveLine()},this.onTokenizerUpdate=function(e){var t=e.data;this.renderer.updateLines(t.first,t.last)},this.onScrollTopChange=function(){this.renderer.scrollToY(this.session.getScrollTop())},this.onScrollLeftChange=function(){this.renderer.scrollToX(this.session.getScrollLeft())},this.onCursorChange=function(){this.$cursorChange(),this.$blockScrolling||(g.warn(\"Automatically scrolling cursor into view after selection change\",\"this will be disabled in the next version\",\"set editor.$blockScrolling = Infinity to disable this message\"),this.renderer.scrollCursorIntoView()),this.$highlightBrackets(),this.$highlightTags(),this.$updateHighlightActiveLine(),this._signal(\"changeSelection\")},this.$updateHighlightActiveLine=function(){var e=this.getSession(),t;if(this.$highlightActiveLine){if(this.$selectionStyle!=\"line\"||!this.selection.isMultiLine())t=this.getCursorPosition();this.renderer.$maxLines&&this.session.getLength()===1&&!(this.renderer.$minLines>1)&&(t=!1)}if(e.$highlightLineMarker&&!t)e.removeMarker(e.$highlightLineMarker.id),e.$highlightLineMarker=null;else if(!e.$highlightLineMarker&&t){var n=new p(t.row,t.column,t.row,Infinity);n.id=e.addMarker(n,\"ace_active-line\",\"screenLine\"),e.$highlightLineMarker=n}else t&&(e.$highlightLineMarker.start.row=t.row,e.$highlightLineMarker.end.row=t.row,e.$highlightLineMarker.start.column=t.column,e._signal(\"changeBackMarker\"))},this.onSelectionChange=function(e){var t=this.session;t.$selectionMarker&&t.removeMarker(t.$selectionMarker),t.$selectionMarker=null;if(!this.selection.isEmpty()){var n=this.selection.getRange(),r=this.getSelectionStyle();t.$selectionMarker=t.addMarker(n,\"ace_selection\",r)}else this.$updateHighlightActiveLine();var i=this.$highlightSelectedWord&&this.$getSelectionHighLightRegexp();this.session.highlight(i),this._signal(\"changeSelection\")},this.$getSelectionHighLightRegexp=function(){var e=this.session,t=this.getSelectionRange();if(t.isEmpty()||t.isMultiLine())return;var n=t.start.column-1,r=t.end.column+1,i=e.getLine(t.start.row),s=i.length,o=i.substring(Math.max(n,0),Math.min(r,s));if(n>=0&&/^[\\w\\d]/.test(o)||r<=s&&/[\\w\\d]$/.test(o))return;o=i.substring(t.start.column,t.end.column);if(!/^[\\w\\d]+$/.test(o))return;var u=this.$search.$assembleRegExp({wholeWord:!0,caseSensitive:!0,needle:o});return u},this.onChangeFrontMarker=function(){this.renderer.updateFrontMarkers()},this.onChangeBackMarker=function(){this.renderer.updateBackMarkers()},this.onChangeBreakpoint=function(){this.renderer.updateBreakpoints()},this.onChangeAnnotation=function(){this.renderer.setAnnotations(this.session.getAnnotations())},this.onChangeMode=function(e){this.renderer.updateText(),this._emit(\"changeMode\",e)},this.onChangeWrapLimit=function(){this.renderer.updateFull()},this.onChangeWrapMode=function(){this.renderer.onResize(!0)},this.onChangeFold=function(){this.$updateHighlightActiveLine(),this.renderer.updateFull()},this.getSelectedText=function(){return this.session.getTextRange(this.getSelectionRange())},this.getCopyText=function(){var e=this.getSelectedText();return this._signal(\"copy\",e),e},this.onCopy=function(){this.commands.exec(\"copy\",this)},this.onCut=function(){this.commands.exec(\"cut\",this)},this.onPaste=function(e,t){var n={text:e,event:t};this.commands.exec(\"paste\",this,n)},this.$handlePaste=function(e){typeof e==\"string\"&&(e={text:e}),this._signal(\"paste\",e);var t=e.text;if(!this.inMultiSelectMode||this.inVirtualSelectionMode)this.insert(t);else{var n=t.split(/\\r\\n|\\r|\\n/),r=this.selection.rangeList.ranges;if(n.length>r.length||n.length<2||!n[1])return this.commands.exec(\"insertstring\",this,t);for(var i=r.length;i--;){var s=r[i];s.isEmpty()||this.session.remove(s),this.session.insert(s.start,n[i])}}},this.execCommand=function(e,t){return this.commands.exec(e,this,t)},this.insert=function(e,t){var n=this.session,r=n.getMode(),i=this.getCursorPosition();if(this.getBehavioursEnabled()&&!t){var s=r.transformAction(n.getState(i.row),\"insertion\",this,n,e);s&&(e!==s.text&&(this.session.mergeUndoDeltas=!1,this.$mergeNextCommand=!1),e=s.text)}e==\"\t\"&&(e=this.session.getTabString());if(!this.selection.isEmpty()){var o=this.getSelectionRange();i=this.session.remove(o),this.clearSelection()}else if(this.session.getOverwrite()){var o=new p.fromPoints(i,i);o.end.column+=e.length,this.session.remove(o)}if(e==\"\\n\"||e==\"\\r\\n\"){var u=n.getLine(i.row);if(i.column>u.search(/\\S|$/)){var a=u.substr(i.column).search(/\\S|$/);n.doc.removeInLine(i.row,i.column,i.column+a)}}this.clearSelection();var f=i.column,l=n.getState(i.row),u=n.getLine(i.row),c=r.checkOutdent(l,u,e),h=n.insert(i,e);s&&s.selection&&(s.selection.length==2?this.selection.setSelectionRange(new p(i.row,f+s.selection[0],i.row,f+s.selection[1])):this.selection.setSelectionRange(new p(i.row+s.selection[0],s.selection[1],i.row+s.selection[2],s.selection[3])));if(n.getDocument().isNewLine(e)){var d=r.getNextLineIndent(l,u.slice(0,i.column),n.getTabString());n.insert({row:i.row+1,column:0},d)}c&&r.autoOutdent(l,n,i.row)},this.onTextInput=function(e){this.keyBinding.onTextInput(e)},this.onCommandKey=function(e,t,n){this.keyBinding.onCommandKey(e,t,n)},this.setOverwrite=function(e){this.session.setOverwrite(e)},this.getOverwrite=function(){return this.session.getOverwrite()},this.toggleOverwrite=function(){this.session.toggleOverwrite()},this.setScrollSpeed=function(e){this.setOption(\"scrollSpeed\",e)},this.getScrollSpeed=function(){return this.getOption(\"scrollSpeed\")},this.setDragDelay=function(e){this.setOption(\"dragDelay\",e)},this.getDragDelay=function(){return this.getOption(\"dragDelay\")},this.setSelectionStyle=function(e){this.setOption(\"selectionStyle\",e)},this.getSelectionStyle=function(){return this.getOption(\"selectionStyle\")},this.setHighlightActiveLine=function(e){this.setOption(\"highlightActiveLine\",e)},this.getHighlightActiveLine=function(){return this.getOption(\"highlightActiveLine\")},this.setHighlightGutterLine=function(e){this.setOption(\"highlightGutterLine\",e)},this.getHighlightGutterLine=function(){return this.getOption(\"highlightGutterLine\")},this.setHighlightSelectedWord=function(e){this.setOption(\"highlightSelectedWord\",e)},this.getHighlightSelectedWord=function(){return this.$highlightSelectedWord},this.setAnimatedScroll=function(e){this.renderer.setAnimatedScroll(e)},this.getAnimatedScroll=function(){return this.renderer.getAnimatedScroll()},this.setShowInvisibles=function(e){this.renderer.setShowInvisibles(e)},this.getShowInvisibles=function(){return this.renderer.getShowInvisibles()},this.setDisplayIndentGuides=function(e){this.renderer.setDisplayIndentGuides(e)},this.getDisplayIndentGuides=function(){return this.renderer.getDisplayIndentGuides()},this.setShowPrintMargin=function(e){this.renderer.setShowPrintMargin(e)},this.getShowPrintMargin=function(){return this.renderer.getShowPrintMargin()},this.setPrintMarginColumn=function(e){this.renderer.setPrintMarginColumn(e)},this.getPrintMarginColumn=function(){return this.renderer.getPrintMarginColumn()},this.setReadOnly=function(e){this.setOption(\"readOnly\",e)},this.getReadOnly=function(){return this.getOption(\"readOnly\")},this.setBehavioursEnabled=function(e){this.setOption(\"behavioursEnabled\",e)},this.getBehavioursEnabled=function(){return this.getOption(\"behavioursEnabled\")},this.setWrapBehavioursEnabled=function(e){this.setOption(\"wrapBehavioursEnabled\",e)},this.getWrapBehavioursEnabled=function(){return this.getOption(\"wrapBehavioursEnabled\")},this.setShowFoldWidgets=function(e){this.setOption(\"showFoldWidgets\",e)},this.getShowFoldWidgets=function(){return this.getOption(\"showFoldWidgets\")},this.setFadeFoldWidgets=function(e){this.setOption(\"fadeFoldWidgets\",e)},this.getFadeFoldWidgets=function(){return this.getOption(\"fadeFoldWidgets\")},this.remove=function(e){this.selection.isEmpty()&&(e==\"left\"?this.selection.selectLeft():this.selection.selectRight());var t=this.getSelectionRange();if(this.getBehavioursEnabled()){var n=this.session,r=n.getState(t.start.row),i=n.getMode().transformAction(r,\"deletion\",this,n,t);if(t.end.column===0){var s=n.getTextRange(t);if(s[s.length-1]==\"\\n\"){var o=n.getLine(t.end.row);/^\\s+$/.test(o)&&(t.end.column=o.length)}}i&&(t=i)}this.session.remove(t),this.clearSelection()},this.removeWordRight=function(){this.selection.isEmpty()&&this.selection.selectWordRight(),this.session.remove(this.getSelectionRange()),this.clearSelection()},this.removeWordLeft=function(){this.selection.isEmpty()&&this.selection.selectWordLeft(),this.session.remove(this.getSelectionRange()),this.clearSelection()},this.removeToLineStart=function(){this.selection.isEmpty()&&this.selection.selectLineStart(),this.session.remove(this.getSelectionRange()),this.clearSelection()},this.removeToLineEnd=function(){this.selection.isEmpty()&&this.selection.selectLineEnd();var e=this.getSelectionRange();e.start.column==e.end.column&&e.start.row==e.end.row&&(e.end.column=0,e.end.row++),this.session.remove(e),this.clearSelection()},this.splitLine=function(){this.selection.isEmpty()||(this.session.remove(this.getSelectionRange()),this.clearSelection());var e=this.getCursorPosition();this.insert(\"\\n\"),this.moveCursorToPosition(e)},this.transposeLetters=function(){if(!this.selection.isEmpty())return;var e=this.getCursorPosition(),t=e.column;if(t===0)return;var n=this.session.getLine(e.row),r,i;t<n.length?(r=n.charAt(t)+n.charAt(t-1),i=new p(e.row,t-1,e.row,t+1)):(r=n.charAt(t-1)+n.charAt(t-2),i=new p(e.row,t-2,e.row,t)),this.session.replace(i,r)},this.toLowerCase=function(){var e=this.getSelectionRange();this.selection.isEmpty()&&this.selection.selectWord();var t=this.getSelectionRange(),n=this.session.getTextRange(t);this.session.replace(t,n.toLowerCase()),this.selection.setSelectionRange(e)},this.toUpperCase=function(){var e=this.getSelectionRange();this.selection.isEmpty()&&this.selection.selectWord();var t=this.getSelectionRange(),n=this.session.getTextRange(t);this.session.replace(t,n.toUpperCase()),this.selection.setSelectionRange(e)},this.indent=function(){var e=this.session,t=this.getSelectionRange();if(t.start.row<t.end.row){var n=this.$getSelectedRows();e.indentRows(n.first,n.last,\"\t\");return}if(t.start.column<t.end.column){var r=e.getTextRange(t);if(!/^\\s+$/.test(r)){var n=this.$getSelectedRows();e.indentRows(n.first,n.last,\"\t\");return}}var i=e.getLine(t.start.row),o=t.start,u=e.getTabSize(),a=e.documentToScreenColumn(o.row,o.column);if(this.session.getUseSoftTabs())var f=u-a%u,l=s.stringRepeat(\" \",f);else{var f=a%u;while(i[t.start.column-1]==\" \"&&f)t.start.column--,f--;this.selection.setSelectionRange(t),l=\"\t\"}return this.insert(l)},this.blockIndent=function(){var e=this.$getSelectedRows();this.session.indentRows(e.first,e.last,\"\t\")},this.blockOutdent=function(){var e=this.session.getSelection();this.session.outdentRows(e.getRange())},this.sortLines=function(){var e=this.$getSelectedRows(),t=this.session,n=[];for(i=e.first;i<=e.last;i++)n.push(t.getLine(i));n.sort(function(e,t){return e.toLowerCase()<t.toLowerCase()?-1:e.toLowerCase()>t.toLowerCase()?1:0});var r=new p(0,0,0,0);for(var i=e.first;i<=e.last;i++){var s=t.getLine(i);r.start.row=i,r.end.row=i,r.end.column=s.length,t.replace(r,n[i-e.first])}},this.toggleCommentLines=function(){var e=this.session.getState(this.getCursorPosition().row),t=this.$getSelectedRows();this.session.getMode().toggleCommentLines(e,this.session,t.first,t.last)},this.toggleBlockComment=function(){var e=this.getCursorPosition(),t=this.session.getState(e.row),n=this.getSelectionRange();this.session.getMode().toggleBlockComment(t,this.session,n,e)},this.getNumberAt=function(e,t){var n=/[\\-]?[0-9]+(?:\\.[0-9]+)?/g;n.lastIndex=0;var r=this.session.getLine(e);while(n.lastIndex<t){var i=n.exec(r);if(i.index<=t&&i.index+i[0].length>=t){var s={value:i[0],start:i.index,end:i.index+i[0].length};return s}}return null},this.modifyNumber=function(e){var t=this.selection.getCursor().row,n=this.selection.getCursor().column,r=new p(t,n-1,t,n),i=this.session.getTextRange(r);if(!isNaN(parseFloat(i))&&isFinite(i)){var s=this.getNumberAt(t,n);if(s){var o=s.value.indexOf(\".\")>=0?s.start+s.value.indexOf(\".\")+1:s.end,u=s.start+s.value.length-o,a=parseFloat(s.value);a*=Math.pow(10,u),o!==s.end&&n<o?e*=Math.pow(10,s.end-n-1):e*=Math.pow(10,s.end-n),a+=e,a/=Math.pow(10,u);var f=a.toFixed(u),l=new p(t,s.start,t,s.end);this.session.replace(l,f),this.moveCursorTo(t,Math.max(s.start+1,n+f.length-s.value.length))}}},this.removeLines=function(){var e=this.$getSelectedRows();this.session.removeFullLines(e.first,e.last),this.clearSelection()},this.duplicateSelection=function(){var e=this.selection,t=this.session,n=e.getRange(),r=e.isBackwards();if(n.isEmpty()){var i=n.start.row;t.duplicateLines(i,i)}else{var s=r?n.start:n.end,o=t.insert(s,t.getTextRange(n),!1);n.start=s,n.end=o,e.setSelectionRange(n,r)}},this.moveLinesDown=function(){this.$moveLines(1,!1)},this.moveLinesUp=function(){this.$moveLines(-1,!1)},this.moveText=function(e,t,n){return this.session.moveText(e,t,n)},this.copyLinesUp=function(){this.$moveLines(-1,!0)},this.copyLinesDown=function(){this.$moveLines(1,!0)},this.$moveLines=function(e,t){var n,r,i=this.selection;if(!i.inMultiSelectMode||this.inVirtualSelectionMode){var s=i.toOrientedRange();n=this.$getSelectedRows(s),r=this.session.$moveLines(n.first,n.last,t?0:e),t&&e==-1&&(r=0),s.moveBy(r,0),i.fromOrientedRange(s)}else{var o=i.rangeList.ranges;i.rangeList.detach(this.session),this.inVirtualSelectionMode=!0;var u=0,a=0,f=o.length;for(var l=0;l<f;l++){var c=l;o[l].moveBy(u,0),n=this.$getSelectedRows(o[l]);var h=n.first,p=n.last;while(++l<f){a&&o[l].moveBy(a,0);var d=this.$getSelectedRows(o[l]);if(t&&d.first!=p)break;if(!t&&d.first>p+1)break;p=d.last}l--,u=this.session.$moveLines(h,p,t?0:e),t&&e==-1&&(c=l+1);while(c<=l)o[c].moveBy(u,0),c++;t||(u=0),a+=u}i.fromOrientedRange(i.ranges[0]),i.rangeList.attach(this.session),this.inVirtualSelectionMode=!1}},this.$getSelectedRows=function(e){return e=(e||this.getSelectionRange()).collapseRows(),{first:this.session.getRowFoldStart(e.start.row),last:this.session.getRowFoldEnd(e.end.row)}},this.onCompositionStart=function(e){this.renderer.showComposition(this.getCursorPosition())},this.onCompositionUpdate=function(e){this.renderer.setCompositionText(e)},this.onCompositionEnd=function(){this.renderer.hideComposition()},this.getFirstVisibleRow=function(){return this.renderer.getFirstVisibleRow()},this.getLastVisibleRow=function(){return this.renderer.getLastVisibleRow()},this.isRowVisible=function(e){return e>=this.getFirstVisibleRow()&&e<=this.getLastVisibleRow()},this.isRowFullyVisible=function(e){return e>=this.renderer.getFirstFullyVisibleRow()&&e<=this.renderer.getLastFullyVisibleRow()},this.$getVisibleRowCount=function(){return this.renderer.getScrollBottomRow()-this.renderer.getScrollTopRow()+1},this.$moveByPage=function(e,t){var n=this.renderer,r=this.renderer.layerConfig,i=e*Math.floor(r.height/r.lineHeight);this.$blockScrolling++,t===!0?this.selection.$moveSelection(function(){this.moveCursorBy(i,0)}):t===!1&&(this.selection.moveCursorBy(i,0),this.selection.clearSelection()),this.$blockScrolling--;var s=n.scrollTop;n.scrollBy(0,i*r.lineHeight),t!=null&&n.scrollCursorIntoView(null,.5),n.animateScrolling(s)},this.selectPageDown=function(){this.$moveByPage(1,!0)},this.selectPageUp=function(){this.$moveByPage(-1,!0)},this.gotoPageDown=function(){this.$moveByPage(1,!1)},this.gotoPageUp=function(){this.$moveByPage(-1,!1)},this.scrollPageDown=function(){this.$moveByPage(1)},this.scrollPageUp=function(){this.$moveByPage(-1)},this.scrollToRow=function(e){this.renderer.scrollToRow(e)},this.scrollToLine=function(e,t,n,r){this.renderer.scrollToLine(e,t,n,r)},this.centerSelection=function(){var e=this.getSelectionRange(),t={row:Math.floor(e.start.row+(e.end.row-e.start.row)/2),column:Math.floor(e.start.column+(e.end.column-e.start.column)/2)};this.renderer.alignCursor(t,.5)},this.getCursorPosition=function(){return this.selection.getCursor()},this.getCursorPositionScreen=function(){return this.session.documentToScreenPosition(this.getCursorPosition())},this.getSelectionRange=function(){return this.selection.getRange()},this.selectAll=function(){this.$blockScrolling+=1,this.selection.selectAll(),this.$blockScrolling-=1},this.clearSelection=function(){this.selection.clearSelection()},this.moveCursorTo=function(e,t){this.selection.moveCursorTo(e,t)},this.moveCursorToPosition=function(e){this.selection.moveCursorToPosition(e)},this.jumpToMatching=function(e,t){var n=this.getCursorPosition(),r=new y(this.session,n.row,n.column),i=r.getCurrentToken(),s=i||r.stepForward();if(!s)return;var o,u=!1,a={},f=n.column-s.start,l,c={\")\":\"(\",\"(\":\"(\",\"]\":\"[\",\"[\":\"[\",\"{\":\"{\",\"}\":\"{\"};do{if(s.value.match(/[{}()\\[\\]]/g))for(;f<s.value.length&&!u;f++){if(!c[s.value[f]])continue;l=c[s.value[f]]+\".\"+s.type.replace(\"rparen\",\"lparen\"),isNaN(a[l])&&(a[l]=0);switch(s.value[f]){case\"(\":case\"[\":case\"{\":a[l]++;break;case\")\":case\"]\":case\"}\":a[l]--,a[l]===-1&&(o=\"bracket\",u=!0)}}else s&&s.type.indexOf(\"tag-name\")!==-1&&(isNaN(a[s.value])&&(a[s.value]=0),i.value===\"<\"?a[s.value]++:i.value===\"</\"&&a[s.value]--,a[s.value]===-1&&(o=\"tag\",u=!0));u||(i=s,s=r.stepForward(),f=0)}while(s&&!u);if(!o)return;var h,d;if(o===\"bracket\"){h=this.session.getBracketRange(n);if(!h){h=new p(r.getCurrentTokenRow(),r.getCurrentTokenColumn()+f-1,r.getCurrentTokenRow(),r.getCurrentTokenColumn()+f-1),d=h.start;if(t||d.row===n.row&&Math.abs(d.column-n.column)<2)h=this.session.getBracketRange(d)}}else if(o===\"tag\"){if(!s||s.type.indexOf(\"tag-name\")===-1)return;var v=s.value;h=new p(r.getCurrentTokenRow(),r.getCurrentTokenColumn()-2,r.getCurrentTokenRow(),r.getCurrentTokenColumn()-2);if(h.compare(n.row,n.column)===0){u=!1;do s=i,i=r.stepBackward(),i&&(i.type.indexOf(\"tag-close\")!==-1&&h.setEnd(r.getCurrentTokenRow(),r.getCurrentTokenColumn()+1),s.value===v&&s.type.indexOf(\"tag-name\")!==-1&&(i.value===\"<\"?a[v]++:i.value===\"</\"&&a[v]--,a[v]===0&&(u=!0)));while(i&&!u)}s&&s.type.indexOf(\"tag-name\")&&(d=h.start,d.row==n.row&&Math.abs(d.column-n.column)<2&&(d=h.end))}d=h&&h.cursor||d,d&&(e?h&&t?this.selection.setRange(h):h&&h.isEqual(this.getSelectionRange())?this.clearSelection():this.selection.selectTo(d.row,d.column):this.selection.moveTo(d.row,d.column))},this.gotoLine=function(e,t,n){this.selection.clearSelection(),this.session.unfold({row:e-1,column:t||0}),this.$blockScrolling+=1,this.exitMultiSelectMode&&this.exitMultiSelectMode(),this.moveCursorTo(e-1,t||0),this.$blockScrolling-=1,this.isRowFullyVisible(e-1)||this.scrollToLine(e-1,!0,n)},this.navigateTo=function(e,t){this.selection.moveTo(e,t)},this.navigateUp=function(e){if(this.selection.isMultiLine()&&!this.selection.isBackwards()){var t=this.selection.anchor.getPosition();return this.moveCursorToPosition(t)}this.selection.clearSelection(),this.selection.moveCursorBy(-e||-1,0)},this.navigateDown=function(e){if(this.selection.isMultiLine()&&this.selection.isBackwards()){var t=this.selection.anchor.getPosition();return this.moveCursorToPosition(t)}this.selection.clearSelection(),this.selection.moveCursorBy(e||1,0)},this.navigateLeft=function(e){if(!this.selection.isEmpty()){var t=this.getSelectionRange().start;this.moveCursorToPosition(t)}else{e=e||1;while(e--)this.selection.moveCursorLeft()}this.clearSelection()},this.navigateRight=function(e){if(!this.selection.isEmpty()){var t=this.getSelectionRange().end;this.moveCursorToPosition(t)}else{e=e||1;while(e--)this.selection.moveCursorRight()}this.clearSelection()},this.navigateLineStart=function(){this.selection.moveCursorLineStart(),this.clearSelection()},this.navigateLineEnd=function(){this.selection.moveCursorLineEnd(),this.clearSelection()},this.navigateFileEnd=function(){this.selection.moveCursorFileEnd(),this.clearSelection()},this.navigateFileStart=function(){this.selection.moveCursorFileStart(),this.clearSelection()},this.navigateWordRight=function(){this.selection.moveCursorWordRight(),this.clearSelection()},this.navigateWordLeft=function(){this.selection.moveCursorWordLeft(),this.clearSelection()},this.replace=function(e,t){t&&this.$search.set(t);var n=this.$search.find(this.session),r=0;return n?(this.$tryReplace(n,e)&&(r=1),n!==null&&(this.selection.setSelectionRange(n),this.renderer.scrollSelectionIntoView(n.start,n.end)),r):r},this.replaceAll=function(e,t){t&&this.$search.set(t);var n=this.$search.findAll(this.session),r=0;if(!n.length)return r;this.$blockScrolling+=1;var i=this.getSelectionRange();this.selection.moveTo(0,0);for(var s=n.length-1;s>=0;--s)this.$tryReplace(n[s],e)&&r++;return this.selection.setSelectionRange(i),this.$blockScrolling-=1,r},this.$tryReplace=function(e,t){var n=this.session.getTextRange(e);return t=this.$search.replace(n,t),t!==null?(e.end=this.session.replace(e,t),e):null},this.getLastSearchOptions=function(){return this.$search.getOptions()},this.find=function(e,t,n){t||(t={}),typeof e==\"string\"||e instanceof RegExp?t.needle=e:typeof e==\"object\"&&r.mixin(t,e);var i=this.selection.getRange();t.needle==null&&(e=this.session.getTextRange(i)||this.$search.$options.needle,e||(i=this.session.getWordRange(i.start.row,i.start.column),e=this.session.getTextRange(i)),this.$search.set({needle:e})),this.$search.set(t),t.start||this.$search.set({start:i});var s=this.$search.find(this.session);if(t.preventScroll)return s;if(s)return this.revealRange(s,n),s;t.backwards?i.start=i.end:i.end=i.start,this.selection.setRange(i)},this.findNext=function(e,t){this.find({skipCurrent:!0,backwards:!1},e,t)},this.findPrevious=function(e,t){this.find(e,{skipCurrent:!0,backwards:!0},t)},this.revealRange=function(e,t){this.$blockScrolling+=1,this.session.unfold(e),this.selection.setSelectionRange(e),this.$blockScrolling-=1;var n=this.renderer.scrollTop;this.renderer.scrollSelectionIntoView(e.start,e.end,.5),t!==!1&&this.renderer.animateScrolling(n)},this.undo=function(){this.$blockScrolling++,this.session.getUndoManager().undo(),this.$blockScrolling--,this.renderer.scrollCursorIntoView(null,.5)},this.redo=function(){this.$blockScrolling++,this.session.getUndoManager().redo(),this.$blockScrolling--,this.renderer.scrollCursorIntoView(null,.5)},this.destroy=function(){this.renderer.destroy(),this._signal(\"destroy\",this),this.session&&this.session.destroy()},this.setAutoScrollEditorIntoView=function(e){if(!e)return;var t,n=this,r=!1;this.$scrollAnchor||(this.$scrollAnchor=document.createElement(\"div\"));var i=this.$scrollAnchor;i.style.cssText=\"position:absolute\",this.container.insertBefore(i,this.container.firstChild);var s=this.on(\"changeSelection\",function(){r=!0}),o=this.renderer.on(\"beforeRender\",function(){r&&(t=n.renderer.container.getBoundingClientRect())}),u=this.renderer.on(\"afterRender\",function(){if(r&&t&&(n.isFocused()||n.searchBox&&n.searchBox.isFocused())){var e=n.renderer,s=e.$cursorLayer.$pixelPos,o=e.layerConfig,u=s.top-o.offset;s.top>=0&&u+t.top<0?r=!0:s.top<o.height&&s.top+t.top+o.lineHeight>window.innerHeight?r=!1:r=null,r!=null&&(i.style.top=u+\"px\",i.style.left=s.left+\"px\",i.style.height=o.lineHeight+\"px\",i.scrollIntoView(r)),r=t=null}});this.setAutoScrollEditorIntoView=function(e){if(e)return;delete this.setAutoScrollEditorIntoView,this.off(\"changeSelection\",s),this.renderer.off(\"afterRender\",u),this.renderer.off(\"beforeRender\",o)}},this.$resetCursorStyle=function(){var e=this.$cursorStyle||\"ace\",t=this.renderer.$cursorLayer;if(!t)return;t.setSmoothBlinking(/smooth/.test(e)),t.isBlinking=!this.$readOnly&&e!=\"wide\",i.setCssClass(t.element,\"ace_slim-cursors\",/slim/.test(e))}}).call(b.prototype),g.defineOptions(b.prototype,\"editor\",{selectionStyle:{set:function(e){this.onSelectionChange(),this._signal(\"changeSelectionStyle\",{data:e})},initialValue:\"line\"},highlightActiveLine:{set:function(){this.$updateHighlightActiveLine()},initialValue:!0},highlightSelectedWord:{set:function(e){this.$onSelectionChange()},initialValue:!0},readOnly:{set:function(e){this.$resetCursorStyle()},initialValue:!1},cursorStyle:{set:function(e){this.$resetCursorStyle()},values:[\"ace\",\"slim\",\"smooth\",\"wide\"],initialValue:\"ace\"},mergeUndoDeltas:{values:[!1,!0,\"always\"],initialValue:!0},behavioursEnabled:{initialValue:!0},wrapBehavioursEnabled:{initialValue:!0},autoScrollEditorIntoView:{set:function(e){this.setAutoScrollEditorIntoView(e)}},keyboardHandler:{set:function(e){this.setKeyboardHandler(e)},get:function(){return this.keybindingId},handlesSet:!0},hScrollBarAlwaysVisible:\"renderer\",vScrollBarAlwaysVisible:\"renderer\",highlightGutterLine:\"renderer\",animatedScroll:\"renderer\",showInvisibles:\"renderer\",showPrintMargin:\"renderer\",printMarginColumn:\"renderer\",printMargin:\"renderer\",fadeFoldWidgets:\"renderer\",showFoldWidgets:\"renderer\",showLineNumbers:\"renderer\",showGutter:\"renderer\",displayIndentGuides:\"renderer\",fontSize:\"renderer\",fontFamily:\"renderer\",maxLines:\"renderer\",minLines:\"renderer\",scrollPastEnd:\"renderer\",fixedWidthGutter:\"renderer\",theme:\"renderer\",scrollSpeed:\"$mouseHandler\",dragDelay:\"$mouseHandler\",dragEnabled:\"$mouseHandler\",focusTimout:\"$mouseHandler\",tooltipFollowsMouse:\"$mouseHandler\",firstLineNumber:\"session\",overwrite:\"session\",newLineMode:\"session\",useWorker:\"session\",useSoftTabs:\"session\",tabSize:\"session\",wrap:\"session\",indentedSoftWrap:\"session\",foldStyle:\"session\",mode:\"session\"}),t.Editor=b}),define(\"ace/undomanager\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(){this.reset()};(function(){function e(e){return{action:e.action,start:e.start,end:e.end,lines:e.lines.length==1?null:e.lines,text:e.lines.length==1?e.lines[0]:null}}function t(e){return{action:e.action,start:e.start,end:e.end,lines:e.lines||[e.text]}}function n(e,t){var n=new Array(e.length);for(var r=0;r<e.length;r++){var i=e[r],s={group:i.group,deltas:new Array(i.length)};for(var o=0;o<i.deltas.length;o++){var u=i.deltas[o];s.deltas[o]=t(u)}n[r]=s}return n}this.execute=function(e){var t=e.args[0];this.$doc=e.args[1],e.merge&&this.hasUndo()&&(this.dirtyCounter--,t=this.$undoStack.pop().concat(t)),this.$undoStack.push(t),this.$redoStack=[],this.dirtyCounter<0&&(this.dirtyCounter=NaN),this.dirtyCounter++},this.undo=function(e){var t=this.$undoStack.pop(),n=null;return t&&(n=this.$doc.undoChanges(t,e),this.$redoStack.push(t),this.dirtyCounter--),n},this.redo=function(e){var t=this.$redoStack.pop(),n=null;return t&&(n=this.$doc.redoChanges(this.$deserializeDeltas(t),e),this.$undoStack.push(t),this.dirtyCounter++),n},this.reset=function(){this.$undoStack=[],this.$redoStack=[],this.dirtyCounter=0},this.hasUndo=function(){return this.$undoStack.length>0},this.hasRedo=function(){return this.$redoStack.length>0},this.markClean=function(){this.dirtyCounter=0},this.isClean=function(){return this.dirtyCounter===0},this.$serializeDeltas=function(t){return n(t,e)},this.$deserializeDeltas=function(e){return n(e,t)}}).call(r.prototype),t.UndoManager=r}),define(\"ace/layer/gutter\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"../lib/dom\"),i=e(\"../lib/oop\"),s=e(\"../lib/lang\"),o=e(\"../lib/event_emitter\").EventEmitter,u=function(e){this.element=r.createElement(\"div\"),this.element.className=\"ace_layer ace_gutter-layer\",e.appendChild(this.element),this.setShowFoldWidgets(this.$showFoldWidgets),this.gutterWidth=0,this.$annotations=[],this.$updateAnnotations=this.$updateAnnotations.bind(this),this.$cells=[]};(function(){i.implement(this,o),this.setSession=function(e){this.session&&this.session.removeEventListener(\"change\",this.$updateAnnotations),this.session=e,e&&e.on(\"change\",this.$updateAnnotations)},this.addGutterDecoration=function(e,t){window.console&&console.warn&&console.warn(\"deprecated use session.addGutterDecoration\"),this.session.addGutterDecoration(e,t)},this.removeGutterDecoration=function(e,t){window.console&&console.warn&&console.warn(\"deprecated use session.removeGutterDecoration\"),this.session.removeGutterDecoration(e,t)},this.setAnnotations=function(e){this.$annotations=[];for(var t=0;t<e.length;t++){var n=e[t],r=n.row,i=this.$annotations[r];i||(i=this.$annotations[r]={text:[]});var o=n.text;o=o?s.escapeHTML(o):n.html||\"\",i.text.indexOf(o)===-1&&i.text.push(o);var u=n.type;u==\"error\"?i.className=\" ace_error\":u==\"warning\"&&i.className!=\" ace_error\"?i.className=\" ace_warning\":u==\"info\"&&!i.className&&(i.className=\" ace_info\")}},this.$updateAnnotations=function(e){if(!this.$annotations.length)return;var t=e.start.row,n=e.end.row-t;if(n!==0)if(e.action==\"remove\")this.$annotations.splice(t,n+1,null);else{var r=new Array(n+1);r.unshift(t,1),this.$annotations.splice.apply(this.$annotations,r)}},this.update=function(e){var t=this.session,n=e.firstRow,i=Math.min(e.lastRow+e.gutterOffset,t.getLength()-1),s=t.getNextFoldLine(n),o=s?s.start.row:Infinity,u=this.$showFoldWidgets&&t.foldWidgets,a=t.$breakpoints,f=t.$decorations,l=t.$firstLineNumber,c=0,h=t.gutterRenderer||this.$renderer,p=null,d=-1,v=n;for(;;){v>o&&(v=s.end.row+1,s=t.getNextFoldLine(v,s),o=s?s.start.row:Infinity);if(v>i){while(this.$cells.length>d+1)p=this.$cells.pop(),this.element.removeChild(p.element);break}p=this.$cells[++d],p||(p={element:null,textNode:null,foldWidget:null},p.element=r.createElement(\"div\"),p.textNode=document.createTextNode(\"\"),p.element.appendChild(p.textNode),this.element.appendChild(p.element),this.$cells[d]=p);var m=\"ace_gutter-cell \";a[v]&&(m+=a[v]),f[v]&&(m+=f[v]),this.$annotations[v]&&(m+=this.$annotations[v].className),p.element.className!=m&&(p.element.className=m);var g=t.getRowLength(v)*e.lineHeight+\"px\";g!=p.element.style.height&&(p.element.style.height=g);if(u){var y=u[v];y==null&&(y=u[v]=t.getFoldWidget(v))}if(y){p.foldWidget||(p.foldWidget=r.createElement(\"span\"),p.element.appendChild(p.foldWidget));var m=\"ace_fold-widget ace_\"+y;y==\"start\"&&v==o&&v<s.end.row?m+=\" ace_closed\":m+=\" ace_open\",p.foldWidget.className!=m&&(p.foldWidget.className=m);var g=e.lineHeight+\"px\";p.foldWidget.style.height!=g&&(p.foldWidget.style.height=g)}else p.foldWidget&&(p.element.removeChild(p.foldWidget),p.foldWidget=null);var b=c=h?h.getText(t,v):v+l;b!=p.textNode.data&&(p.textNode.data=b),v++}this.element.style.height=e.minHeight+\"px\";if(this.$fixedWidth||t.$useWrapMode)c=t.getLength()+l;var w=h?h.getWidth(t,c,e):c.toString().length*e.characterWidth,E=this.$padding||this.$computePadding();w+=E.left+E.right,w!==this.gutterWidth&&!isNaN(w)&&(this.gutterWidth=w,this.element.style.width=Math.ceil(this.gutterWidth)+\"px\",this._emit(\"changeGutterWidth\",w))},this.$fixedWidth=!1,this.$showLineNumbers=!0,this.$renderer=\"\",this.setShowLineNumbers=function(e){this.$renderer=!e&&{getWidth:function(){return\"\"},getText:function(){return\"\"}}},this.getShowLineNumbers=function(){return this.$showLineNumbers},this.$showFoldWidgets=!0,this.setShowFoldWidgets=function(e){e?r.addCssClass(this.element,\"ace_folding-enabled\"):r.removeCssClass(this.element,\"ace_folding-enabled\"),this.$showFoldWidgets=e,this.$padding=null},this.getShowFoldWidgets=function(){return this.$showFoldWidgets},this.$computePadding=function(){if(!this.element.firstChild)return{left:0,right:0};var e=r.computedStyle(this.element.firstChild);return this.$padding={},this.$padding.left=parseInt(e.paddingLeft)+1||0,this.$padding.right=parseInt(e.paddingRight)||0,this.$padding},this.getRegion=function(e){var t=this.$padding||this.$computePadding(),n=this.element.getBoundingClientRect();if(e.x<t.left+n.left)return\"markers\";if(this.$showFoldWidgets&&e.x>n.right-t.right)return\"foldWidgets\"}}).call(u.prototype),t.Gutter=u}),define(\"ace/layer/marker\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/lib/dom\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=e(\"../lib/dom\"),s=function(e){this.element=i.createElement(\"div\"),this.element.className=\"ace_layer ace_marker-layer\",e.appendChild(this.element)};(function(){function e(e,t,n,r){return(e?1:0)|(t?2:0)|(n?4:0)|(r?8:0)}this.$padding=0,this.setPadding=function(e){this.$padding=e},this.setSession=function(e){this.session=e},this.setMarkers=function(e){this.markers=e},this.update=function(e){var e=e||this.config;if(!e)return;this.config=e;var t=[];for(var n in this.markers){var r=this.markers[n];if(!r.range){r.update(t,this,this.session,e);continue}var i=r.range.clipRows(e.firstRow,e.lastRow);if(i.isEmpty())continue;i=i.toScreenRange(this.session);if(r.renderer){var s=this.$getTop(i.start.row,e),o=this.$padding+i.start.column*e.characterWidth;r.renderer(t,i,o,s,e)}else r.type==\"fullLine\"?this.drawFullLineMarker(t,i,r.clazz,e):r.type==\"screenLine\"?this.drawScreenLineMarker(t,i,r.clazz,e):i.isMultiLine()?r.type==\"text\"?this.drawTextMarker(t,i,r.clazz,e):this.drawMultiLineMarker(t,i,r.clazz,e):this.drawSingleLineMarker(t,i,r.clazz+\" ace_start\"+\" ace_br15\",e)}this.element.innerHTML=t.join(\"\")},this.$getTop=function(e,t){return(e-t.firstRowScreen)*t.lineHeight},this.drawTextMarker=function(t,n,i,s,o){var u=this.session,a=n.start.row,f=n.end.row,l=a,c=0,h=0,p=u.getScreenLastRowColumn(l),d=new r(l,n.start.column,l,h);for(;l<=f;l++)d.start.row=d.end.row=l,d.start.column=l==a?n.start.column:u.getRowWrapIndent(l),d.end.column=p,c=h,h=p,p=l+1<f?u.getScreenLastRowColumn(l+1):l==f?0:n.end.column,this.drawSingleLineMarker(t,d,i+(l==a?\" ace_start\":\"\")+\" ace_br\"+e(l==a||l==a+1&&n.start.column,c<h,h>p,l==f),s,l==f?0:1,o)},this.drawMultiLineMarker=function(e,t,n,r,i){var s=this.$padding,o=r.lineHeight,u=this.$getTop(t.start.row,r),a=s+t.start.column*r.characterWidth;i=i||\"\",e.push(\"<div class='\",n,\" ace_br1 ace_start' style='\",\"height:\",o,\"px;\",\"right:0;\",\"top:\",u,\"px;\",\"left:\",a,\"px;\",i,\"'></div>\"),u=this.$getTop(t.end.row,r);var f=t.end.column*r.characterWidth;e.push(\"<div class='\",n,\" ace_br12' style='\",\"height:\",o,\"px;\",\"width:\",f,\"px;\",\"top:\",u,\"px;\",\"left:\",s,\"px;\",i,\"'></div>\"),o=(t.end.row-t.start.row-1)*r.lineHeight;if(o<=0)return;u=this.$getTop(t.start.row+1,r);var l=(t.start.column?1:0)|(t.end.column?0:8);e.push(\"<div class='\",n,l?\" ace_br\"+l:\"\",\"' style='\",\"height:\",o,\"px;\",\"right:0;\",\"top:\",u,\"px;\",\"left:\",s,\"px;\",i,\"'></div>\")},this.drawSingleLineMarker=function(e,t,n,r,i,s){var o=r.lineHeight,u=(t.end.column+(i||0)-t.start.column)*r.characterWidth,a=this.$getTop(t.start.row,r),f=this.$padding+t.start.column*r.characterWidth;e.push(\"<div class='\",n,\"' style='\",\"height:\",o,\"px;\",\"width:\",u,\"px;\",\"top:\",a,\"px;\",\"left:\",f,\"px;\",s||\"\",\"'></div>\")},this.drawFullLineMarker=function(e,t,n,r,i){var s=this.$getTop(t.start.row,r),o=r.lineHeight;t.start.row!=t.end.row&&(o+=this.$getTop(t.end.row,r)-s),e.push(\"<div class='\",n,\"' style='\",\"height:\",o,\"px;\",\"top:\",s,\"px;\",\"left:0;right:0;\",i||\"\",\"'></div>\")},this.drawScreenLineMarker=function(e,t,n,r,i){var s=this.$getTop(t.start.row,r),o=r.lineHeight;e.push(\"<div class='\",n,\"' style='\",\"height:\",o,\"px;\",\"top:\",s,\"px;\",\"left:0;right:0;\",i||\"\",\"'></div>\")}}).call(s.prototype),t.Marker=s}),define(\"ace/layer/text\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/dom\",\"ace/lib/lang\",\"ace/lib/useragent\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/dom\"),s=e(\"../lib/lang\"),o=e(\"../lib/useragent\"),u=e(\"../lib/event_emitter\").EventEmitter,a=function(e){this.element=i.createElement(\"div\"),this.element.className=\"ace_layer ace_text-layer\",e.appendChild(this.element),this.$updateEolChar=this.$updateEolChar.bind(this)};(function(){r.implement(this,u),this.EOF_CHAR=\"\\u00b6\",this.EOL_CHAR_LF=\"\\u00ac\",this.EOL_CHAR_CRLF=\"\\u00a4\",this.EOL_CHAR=this.EOL_CHAR_LF,this.TAB_CHAR=\"\\u2014\",this.SPACE_CHAR=\"\\u00b7\",this.$padding=0,this.$updateEolChar=function(){var e=this.session.doc.getNewLineCharacter()==\"\\n\"?this.EOL_CHAR_LF:this.EOL_CHAR_CRLF;if(this.EOL_CHAR!=e)return this.EOL_CHAR=e,!0},this.setPadding=function(e){this.$padding=e,this.element.style.padding=\"0 \"+e+\"px\"},this.getLineHeight=function(){return this.$fontMetrics.$characterSize.height||0},this.getCharacterWidth=function(){return this.$fontMetrics.$characterSize.width||0},this.$setFontMetrics=function(e){this.$fontMetrics=e,this.$fontMetrics.on(\"changeCharacterSize\",function(e){this._signal(\"changeCharacterSize\",e)}.bind(this)),this.$pollSizeChanges()},this.checkForSizeChanges=function(){this.$fontMetrics.checkForSizeChanges()},this.$pollSizeChanges=function(){return this.$pollSizeChangesTimer=this.$fontMetrics.$pollSizeChanges()},this.setSession=function(e){this.session=e,e&&this.$computeTabString()},this.showInvisibles=!1,this.setShowInvisibles=function(e){return this.showInvisibles==e?!1:(this.showInvisibles=e,this.$computeTabString(),!0)},this.displayIndentGuides=!0,this.setDisplayIndentGuides=function(e){return this.displayIndentGuides==e?!1:(this.displayIndentGuides=e,this.$computeTabString(),!0)},this.$tabStrings=[],this.onChangeTabSize=this.$computeTabString=function(){var e=this.session.getTabSize();this.tabSize=e;var t=this.$tabStrings=[0];for(var n=1;n<e+1;n++)this.showInvisibles?t.push(\"<span class='ace_invisible ace_invisible_tab'>\"+s.stringRepeat(this.TAB_CHAR,n)+\"</span>\"):t.push(s.stringRepeat(\" \",n));if(this.displayIndentGuides){this.$indentGuideRe=/\\s\\S| \\t|\\t |\\s$/;var r=\"ace_indent-guide\",i=\"\",o=\"\";if(this.showInvisibles){r+=\" ace_invisible\",i=\" ace_invisible_space\",o=\" ace_invisible_tab\";var u=s.stringRepeat(this.SPACE_CHAR,this.tabSize),a=s.stringRepeat(this.TAB_CHAR,this.tabSize)}else var u=s.stringRepeat(\" \",this.tabSize),a=u;this.$tabStrings[\" \"]=\"<span class='\"+r+i+\"'>\"+u+\"</span>\",this.$tabStrings[\"\t\"]=\"<span class='\"+r+o+\"'>\"+a+\"</span>\"}},this.updateLines=function(e,t,n){(this.config.lastRow!=e.lastRow||this.config.firstRow!=e.firstRow)&&this.scrollLines(e),this.config=e;var r=Math.max(t,e.firstRow),i=Math.min(n,e.lastRow),s=this.element.childNodes,o=0;for(var u=e.firstRow;u<r;u++){var a=this.session.getFoldLine(u);if(a){if(a.containsRow(r)){r=a.start.row;break}u=a.end.row}o++}var u=r,a=this.session.getNextFoldLine(u),f=a?a.start.row:Infinity;for(;;){u>f&&(u=a.end.row+1,a=this.session.getNextFoldLine(u,a),f=a?a.start.row:Infinity);if(u>i)break;var l=s[o++];if(l){var c=[];this.$renderLine(c,u,!this.$useLineGroups(),u==f?a:!1),l.style.height=e.lineHeight*this.session.getRowLength(u)+\"px\",l.innerHTML=c.join(\"\")}u++}},this.scrollLines=function(e){var t=this.config;this.config=e;if(!t||t.lastRow<e.firstRow)return this.update(e);if(e.lastRow<t.firstRow)return this.update(e);var n=this.element;if(t.firstRow<e.firstRow)for(var r=this.session.getFoldedRowCount(t.firstRow,e.firstRow-1);r>0;r--)n.removeChild(n.firstChild);if(t.lastRow>e.lastRow)for(var r=this.session.getFoldedRowCount(e.lastRow+1,t.lastRow);r>0;r--)n.removeChild(n.lastChild);if(e.firstRow<t.firstRow){var i=this.$renderLinesFragment(e,e.firstRow,t.firstRow-1);n.firstChild?n.insertBefore(i,n.firstChild):n.appendChild(i)}if(e.lastRow>t.lastRow){var i=this.$renderLinesFragment(e,t.lastRow+1,e.lastRow);n.appendChild(i)}},this.$renderLinesFragment=function(e,t,n){var r=this.element.ownerDocument.createDocumentFragment(),s=t,o=this.session.getNextFoldLine(s),u=o?o.start.row:Infinity;for(;;){s>u&&(s=o.end.row+1,o=this.session.getNextFoldLine(s,o),u=o?o.start.row:Infinity);if(s>n)break;var a=i.createElement(\"div\"),f=[];this.$renderLine(f,s,!1,s==u?o:!1),a.innerHTML=f.join(\"\");if(this.$useLineGroups())a.className=\"ace_line_group\",r.appendChild(a),a.style.height=e.lineHeight*this.session.getRowLength(s)+\"px\";else while(a.firstChild)r.appendChild(a.firstChild);s++}return r},this.update=function(e){this.config=e;var t=[],n=e.firstRow,r=e.lastRow,i=n,s=this.session.getNextFoldLine(i),o=s?s.start.row:Infinity;for(;;){i>o&&(i=s.end.row+1,s=this.session.getNextFoldLine(i,s),o=s?s.start.row:Infinity);if(i>r)break;this.$useLineGroups()&&t.push(\"<div class='ace_line_group' style='height:\",e.lineHeight*this.session.getRowLength(i),\"px'>\"),this.$renderLine(t,i,!1,i==o?s:!1),this.$useLineGroups()&&t.push(\"</div>\"),i++}this.element.innerHTML=t.join(\"\")},this.$textToken={text:!0,rparen:!0,lparen:!0},this.$renderToken=function(e,t,n,r){var i=this,o=/\\t|&|<|>|( +)|([\\x00-\\x1f\\x80-\\xa0\\xad\\u1680\\u180E\\u2000-\\u200f\\u2028\\u2029\\u202F\\u205F\\u3000\\uFEFF\\uFFF9-\\uFFFC])|[\\u1100-\\u115F\\u11A3-\\u11A7\\u11FA-\\u11FF\\u2329-\\u232A\\u2E80-\\u2E99\\u2E9B-\\u2EF3\\u2F00-\\u2FD5\\u2FF0-\\u2FFB\\u3000-\\u303E\\u3041-\\u3096\\u3099-\\u30FF\\u3105-\\u312D\\u3131-\\u318E\\u3190-\\u31BA\\u31C0-\\u31E3\\u31F0-\\u321E\\u3220-\\u3247\\u3250-\\u32FE\\u3300-\\u4DBF\\u4E00-\\uA48C\\uA490-\\uA4C6\\uA960-\\uA97C\\uAC00-\\uD7A3\\uD7B0-\\uD7C6\\uD7CB-\\uD7FB\\uF900-\\uFAFF\\uFE10-\\uFE19\\uFE30-\\uFE52\\uFE54-\\uFE66\\uFE68-\\uFE6B\\uFF01-\\uFF60\\uFFE0-\\uFFE6]/g,u=function(e,n,r,o,u){if(n)return i.showInvisibles?\"<span class='ace_invisible ace_invisible_space'>\"+s.stringRepeat(i.SPACE_CHAR,e.length)+\"</span>\":e;if(e==\"&\")return\"&#38;\";if(e==\"<\")return\"&#60;\";if(e==\">\")return\"&#62;\";if(e==\"\t\"){var a=i.session.getScreenTabSize(t+o);return t+=a-1,i.$tabStrings[a]}if(e==\"\\u3000\"){var f=i.showInvisibles?\"ace_cjk ace_invisible ace_invisible_space\":\"ace_cjk\",l=i.showInvisibles?i.SPACE_CHAR:\"\";return t+=1,\"<span class='\"+f+\"' style='width:\"+i.config.characterWidth*2+\"px'>\"+l+\"</span>\"}return r?\"<span class='ace_invisible ace_invisible_space ace_invalid'>\"+i.SPACE_CHAR+\"</span>\":(t+=1,\"<span class='ace_cjk' style='width:\"+i.config.characterWidth*2+\"px'>\"+e+\"</span>\")},a=r.replace(o,u);if(!this.$textToken[n.type]){var f=\"ace_\"+n.type.replace(/\\./g,\" ace_\"),l=\"\";n.type==\"fold\"&&(l=\" style='width:\"+n.value.length*this.config.characterWidth+\"px;' \"),e.push(\"<span class='\",f,\"'\",l,\">\",a,\"</span>\")}else e.push(a);return t+r.length},this.renderIndentGuide=function(e,t,n){var r=t.search(this.$indentGuideRe);return r<=0||r>=n?t:t[0]==\" \"?(r-=r%this.tabSize,e.push(s.stringRepeat(this.$tabStrings[\" \"],r/this.tabSize)),t.substr(r)):t[0]==\"\t\"?(e.push(s.stringRepeat(this.$tabStrings[\"\t\"],r)),t.substr(r)):t},this.$renderWrappedLine=function(e,t,n,r){var i=0,o=0,u=n[0],a=0;for(var f=0;f<t.length;f++){var l=t[f],c=l.value;if(f==0&&this.displayIndentGuides){i=c.length,c=this.renderIndentGuide(e,c,u);if(!c)continue;i-=c.length}if(i+c.length<u)a=this.$renderToken(e,a,l,c),i+=c.length;else{while(i+c.length>=u)a=this.$renderToken(e,a,l,c.substring(0,u-i)),c=c.substring(u-i),i=u,r||e.push(\"</div>\",\"<div class='ace_line' style='height:\",this.config.lineHeight,\"px'>\"),e.push(s.stringRepeat(\"\\u00a0\",n.indent)),o++,a=0,u=n[o]||Number.MAX_VALUE;c.length!=0&&(i+=c.length,a=this.$renderToken(e,a,l,c))}}},this.$renderSimpleLine=function(e,t){var n=0,r=t[0],i=r.value;this.displayIndentGuides&&(i=this.renderIndentGuide(e,i)),i&&(n=this.$renderToken(e,n,r,i));for(var s=1;s<t.length;s++)r=t[s],i=r.value,n=this.$renderToken(e,n,r,i)},this.$renderLine=function(e,t,n,r){!r&&r!=0&&(r=this.session.getFoldLine(t));if(r)var i=this.$getFoldLineTokens(t,r);else var i=this.session.getTokens(t);n||e.push(\"<div class='ace_line' style='height:\",this.config.lineHeight*(this.$useLineGroups()?1:this.session.getRowLength(t)),\"px'>\");if(i.length){var s=this.session.getRowSplitData(t);s&&s.length?this.$renderWrappedLine(e,i,s,n):this.$renderSimpleLine(e,i)}this.showInvisibles&&(r&&(t=r.end.row),e.push(\"<span class='ace_invisible ace_invisible_eol'>\",t==this.session.getLength()-1?this.EOF_CHAR:this.EOL_CHAR,\"</span>\")),n||e.push(\"</div>\")},this.$getFoldLineTokens=function(e,t){function i(e,t,n){var i=0,s=0;while(s+e[i].value.length<t){s+=e[i].value.length,i++;if(i==e.length)return}if(s!=t){var o=e[i].value.substring(t-s);o.length>n-t&&(o=o.substring(0,n-t)),r.push({type:e[i].type,value:o}),s=t+o.length,i+=1}while(s<n&&i<e.length){var o=e[i].value;o.length+s>n?r.push({type:e[i].type,value:o.substring(0,n-s)}):r.push(e[i]),s+=o.length,i+=1}}var n=this.session,r=[],s=n.getTokens(e);return t.walk(function(e,t,o,u,a){e!=null?r.push({type:\"fold\",value:e}):(a&&(s=n.getTokens(t)),s.length&&i(s,u,o))},t.end.row,this.session.getLine(t.end.row).length),r},this.$useLineGroups=function(){return this.session.getUseWrapMode()},this.destroy=function(){clearInterval(this.$pollSizeChangesTimer),this.$measureNode&&this.$measureNode.parentNode.removeChild(this.$measureNode),delete this.$measureNode}}).call(a.prototype),t.Text=a}),define(\"ace/layer/cursor\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\"],function(e,t,n){\"use strict\";var r=e(\"../lib/dom\"),i,s=function(e){this.element=r.createElement(\"div\"),this.element.className=\"ace_layer ace_cursor-layer\",e.appendChild(this.element),i===undefined&&(i=!(\"opacity\"in this.element.style)),this.isVisible=!1,this.isBlinking=!0,this.blinkInterval=1e3,this.smoothBlinking=!1,this.cursors=[],this.cursor=this.addCursor(),r.addCssClass(this.element,\"ace_hidden-cursors\"),this.$updateCursors=(i?this.$updateVisibility:this.$updateOpacity).bind(this)};(function(){this.$updateVisibility=function(e){var t=this.cursors;for(var n=t.length;n--;)t[n].style.visibility=e?\"\":\"hidden\"},this.$updateOpacity=function(e){var t=this.cursors;for(var n=t.length;n--;)t[n].style.opacity=e?\"\":\"0\"},this.$padding=0,this.setPadding=function(e){this.$padding=e},this.setSession=function(e){this.session=e},this.setBlinking=function(e){e!=this.isBlinking&&(this.isBlinking=e,this.restartTimer())},this.setBlinkInterval=function(e){e!=this.blinkInterval&&(this.blinkInterval=e,this.restartTimer())},this.setSmoothBlinking=function(e){e!=this.smoothBlinking&&!i&&(this.smoothBlinking=e,r.setCssClass(this.element,\"ace_smooth-blinking\",e),this.$updateCursors(!0),this.$updateCursors=this.$updateOpacity.bind(this),this.restartTimer())},this.addCursor=function(){var e=r.createElement(\"div\");return e.className=\"ace_cursor\",this.element.appendChild(e),this.cursors.push(e),e},this.removeCursor=function(){if(this.cursors.length>1){var e=this.cursors.pop();return e.parentNode.removeChild(e),e}},this.hideCursor=function(){this.isVisible=!1,r.addCssClass(this.element,\"ace_hidden-cursors\"),this.restartTimer()},this.showCursor=function(){this.isVisible=!0,r.removeCssClass(this.element,\"ace_hidden-cursors\"),this.restartTimer()},this.restartTimer=function(){var e=this.$updateCursors;clearInterval(this.intervalId),clearTimeout(this.timeoutId),this.smoothBlinking&&r.removeCssClass(this.element,\"ace_smooth-blinking\"),e(!0);if(!this.isBlinking||!this.blinkInterval||!this.isVisible)return;this.smoothBlinking&&setTimeout(function(){r.addCssClass(this.element,\"ace_smooth-blinking\")}.bind(this));var t=function(){this.timeoutId=setTimeout(function(){e(!1)},.6*this.blinkInterval)}.bind(this);this.intervalId=setInterval(function(){e(!0),t()},this.blinkInterval),t()},this.getPixelPosition=function(e,t){if(!this.config||!this.session)return{left:0,top:0};e||(e=this.session.selection.getCursor());var n=this.session.documentToScreenPosition(e),r=this.$padding+n.column*this.config.characterWidth,i=(n.row-(t?this.config.firstRowScreen:0))*this.config.lineHeight;return{left:r,top:i}},this.update=function(e){this.config=e;var t=this.session.$selectionMarkers,n=0,r=0;if(t===undefined||t.length===0)t=[{cursor:null}];for(var n=0,i=t.length;n<i;n++){var s=this.getPixelPosition(t[n].cursor,!0);if((s.top>e.height+e.offset||s.top<0)&&n>1)continue;var o=(this.cursors[r++]||this.addCursor()).style;this.drawCursor?this.drawCursor(o,s,e,t[n],this.session):(o.left=s.left+\"px\",o.top=s.top+\"px\",o.width=e.characterWidth+\"px\",o.height=e.lineHeight+\"px\")}while(this.cursors.length>r)this.removeCursor();var u=this.session.getOverwrite();this.$setOverwrite(u),this.$pixelPos=s,this.restartTimer()},this.drawCursor=null,this.$setOverwrite=function(e){e!=this.overwrite&&(this.overwrite=e,e?r.addCssClass(this.element,\"ace_overwrite-cursors\"):r.removeCssClass(this.element,\"ace_overwrite-cursors\"))},this.destroy=function(){clearInterval(this.intervalId),clearTimeout(this.timeoutId)}}).call(s.prototype),t.Cursor=s}),define(\"ace/scrollbar\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/dom\",\"ace/lib/event\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/dom\"),s=e(\"./lib/event\"),o=e(\"./lib/event_emitter\").EventEmitter,u=32768,a=function(e){this.element=i.createElement(\"div\"),this.element.className=\"ace_scrollbar ace_scrollbar\"+this.classSuffix,this.inner=i.createElement(\"div\"),this.inner.className=\"ace_scrollbar-inner\",this.element.appendChild(this.inner),e.appendChild(this.element),this.setVisible(!1),this.skipEvent=!1,s.addListener(this.element,\"scroll\",this.onScroll.bind(this)),s.addListener(this.element,\"mousedown\",s.preventDefault)};(function(){r.implement(this,o),this.setVisible=function(e){this.element.style.display=e?\"\":\"none\",this.isVisible=e,this.coeff=1}}).call(a.prototype);var f=function(e,t){a.call(this,e),this.scrollTop=0,this.scrollHeight=0,t.$scrollbarWidth=this.width=i.scrollbarWidth(e.ownerDocument),this.inner.style.width=this.element.style.width=(this.width||15)+5+\"px\"};r.inherits(f,a),function(){this.classSuffix=\"-v\",this.onScroll=function(){if(!this.skipEvent){this.scrollTop=this.element.scrollTop;if(this.coeff!=1){var e=this.element.clientHeight/this.scrollHeight;this.scrollTop=this.scrollTop*(1-e)/(this.coeff-e)}this._emit(\"scroll\",{data:this.scrollTop})}this.skipEvent=!1},this.getWidth=function(){return this.isVisible?this.width:0},this.setHeight=function(e){this.element.style.height=e+\"px\"},this.setInnerHeight=this.setScrollHeight=function(e){this.scrollHeight=e,e>u?(this.coeff=u/e,e=u):this.coeff!=1&&(this.coeff=1),this.inner.style.height=e+\"px\"},this.setScrollTop=function(e){this.scrollTop!=e&&(this.skipEvent=!0,this.scrollTop=e,this.element.scrollTop=e*this.coeff)}}.call(f.prototype);var l=function(e,t){a.call(this,e),this.scrollLeft=0,this.height=t.$scrollbarWidth,this.inner.style.height=this.element.style.height=(this.height||15)+5+\"px\"};r.inherits(l,a),function(){this.classSuffix=\"-h\",this.onScroll=function(){this.skipEvent||(this.scrollLeft=this.element.scrollLeft,this._emit(\"scroll\",{data:this.scrollLeft})),this.skipEvent=!1},this.getHeight=function(){return this.isVisible?this.height:0},this.setWidth=function(e){this.element.style.width=e+\"px\"},this.setInnerWidth=function(e){this.inner.style.width=e+\"px\"},this.setScrollWidth=function(e){this.inner.style.width=e+\"px\"},this.setScrollLeft=function(e){this.scrollLeft!=e&&(this.skipEvent=!0,this.scrollLeft=this.element.scrollLeft=e)}}.call(l.prototype),t.ScrollBar=f,t.ScrollBarV=f,t.ScrollBarH=l,t.VScrollBar=f,t.HScrollBar=l}),define(\"ace/renderloop\",[\"require\",\"exports\",\"module\",\"ace/lib/event\"],function(e,t,n){\"use strict\";var r=e(\"./lib/event\"),i=function(e,t){this.onRender=e,this.pending=!1,this.changes=0,this.window=t||window};(function(){this.schedule=function(e){this.changes=this.changes|e;if(!this.pending&&this.changes){this.pending=!0;var t=this;r.nextFrame(function(){t.pending=!1;var e;while(e=t.changes)t.changes=0,t.onRender(e)},this.window)}}}).call(i.prototype),t.RenderLoop=i}),define(\"ace/layer/font_metrics\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/dom\",\"ace/lib/lang\",\"ace/lib/useragent\",\"ace/lib/event_emitter\"],function(e,t,n){var r=e(\"../lib/oop\"),i=e(\"../lib/dom\"),s=e(\"../lib/lang\"),o=e(\"../lib/useragent\"),u=e(\"../lib/event_emitter\").EventEmitter,a=0,f=t.FontMetrics=function(e){this.el=i.createElement(\"div\"),this.$setMeasureNodeStyles(this.el.style,!0),this.$main=i.createElement(\"div\"),this.$setMeasureNodeStyles(this.$main.style),this.$measureNode=i.createElement(\"div\"),this.$setMeasureNodeStyles(this.$measureNode.style),this.el.appendChild(this.$main),this.el.appendChild(this.$measureNode),e.appendChild(this.el),a||this.$testFractionalRect(),this.$measureNode.innerHTML=s.stringRepeat(\"X\",a),this.$characterSize={width:0,height:0},this.checkForSizeChanges()};(function(){r.implement(this,u),this.$characterSize={width:0,height:0},this.$testFractionalRect=function(){var e=i.createElement(\"div\");this.$setMeasureNodeStyles(e.style),e.style.width=\"0.2px\",document.documentElement.appendChild(e);var t=e.getBoundingClientRect().width;t>0&&t<1?a=50:a=100,e.parentNode.removeChild(e)},this.$setMeasureNodeStyles=function(e,t){e.width=e.height=\"auto\",e.left=e.top=\"0px\",e.visibility=\"hidden\",e.position=\"absolute\",e.whiteSpace=\"pre\",o.isIE<8?e[\"font-family\"]=\"inherit\":e.font=\"inherit\",e.overflow=t?\"hidden\":\"visible\"},this.checkForSizeChanges=function(){var e=this.$measureSizes();if(e&&(this.$characterSize.width!==e.width||this.$characterSize.height!==e.height)){this.$measureNode.style.fontWeight=\"bold\";var t=this.$measureSizes();this.$measureNode.style.fontWeight=\"\",this.$characterSize=e,this.charSizes=Object.create(null),this.allowBoldFonts=t&&t.width===e.width&&t.height===e.height,this._emit(\"changeCharacterSize\",{data:e})}},this.$pollSizeChanges=function(){if(this.$pollSizeChangesTimer)return this.$pollSizeChangesTimer;var e=this;return this.$pollSizeChangesTimer=setInterval(function(){e.checkForSizeChanges()},500)},this.setPolling=function(e){e?this.$pollSizeChanges():this.$pollSizeChangesTimer&&(clearInterval(this.$pollSizeChangesTimer),this.$pollSizeChangesTimer=0)},this.$measureSizes=function(){if(a===50){var e=null;try{e=this.$measureNode.getBoundingClientRect()}catch(t){e={width:0,height:0}}var n={height:e.height,width:e.width/a}}else var n={height:this.$measureNode.clientHeight,width:this.$measureNode.clientWidth/a};return n.width===0||n.height===0?null:n},this.$measureCharWidth=function(e){this.$main.innerHTML=s.stringRepeat(e,a);var t=this.$main.getBoundingClientRect();return t.width/a},this.getCharacterWidth=function(e){var t=this.charSizes[e];return t===undefined&&(t=this.charSizes[e]=this.$measureCharWidth(e)/this.$characterSize.width),t},this.destroy=function(){clearInterval(this.$pollSizeChangesTimer),this.el&&this.el.parentNode&&this.el.parentNode.removeChild(this.el)}}).call(f.prototype)}),define(\"ace/virtual_renderer\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/dom\",\"ace/config\",\"ace/lib/useragent\",\"ace/layer/gutter\",\"ace/layer/marker\",\"ace/layer/text\",\"ace/layer/cursor\",\"ace/scrollbar\",\"ace/scrollbar\",\"ace/renderloop\",\"ace/layer/font_metrics\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/dom\"),s=e(\"./config\"),o=e(\"./lib/useragent\"),u=e(\"./layer/gutter\").Gutter,a=e(\"./layer/marker\").Marker,f=e(\"./layer/text\").Text,l=e(\"./layer/cursor\").Cursor,c=e(\"./scrollbar\").HScrollBar,h=e(\"./scrollbar\").VScrollBar,p=e(\"./renderloop\").RenderLoop,d=e(\"./layer/font_metrics\").FontMetrics,v=e(\"./lib/event_emitter\").EventEmitter,m='.ace_editor {position: relative;overflow: hidden;font: 12px/normal \\'Monaco\\', \\'Menlo\\', \\'Ubuntu Mono\\', \\'Consolas\\', \\'source-code-pro\\', monospace;direction: ltr;text-align: left;}.ace_scroller {position: absolute;overflow: hidden;top: 0;bottom: 0;background-color: inherit;-ms-user-select: none;-moz-user-select: none;-webkit-user-select: none;user-select: none;cursor: text;}.ace_content {position: absolute;-moz-box-sizing: border-box;-webkit-box-sizing: border-box;box-sizing: border-box;min-width: 100%;}.ace_dragging .ace_scroller:before{position: absolute;top: 0;left: 0;right: 0;bottom: 0;content: \\'\\';background: rgba(250, 250, 250, 0.01);z-index: 1000;}.ace_dragging.ace_dark .ace_scroller:before{background: rgba(0, 0, 0, 0.01);}.ace_selecting, .ace_selecting * {cursor: text !important;}.ace_gutter {position: absolute;overflow : hidden;width: auto;top: 0;bottom: 0;left: 0;cursor: default;z-index: 4;-ms-user-select: none;-moz-user-select: none;-webkit-user-select: none;user-select: none;}.ace_gutter-active-line {position: absolute;left: 0;right: 0;}.ace_scroller.ace_scroll-left {box-shadow: 17px 0 16px -16px rgba(0, 0, 0, 0.4) inset;}.ace_gutter-cell {padding-left: 19px;padding-right: 6px;background-repeat: no-repeat;}.ace_gutter-cell.ace_error {background-image: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAMAAAAoLQ9TAAABOFBMVEX/////////QRswFAb/Ui4wFAYwFAYwFAaWGAfDRymzOSH/PxswFAb/SiUwFAYwFAbUPRvjQiDllog5HhHdRybsTi3/Tyv9Tir+Syj/UC3////XurebMBIwFAb/RSHbPx/gUzfdwL3kzMivKBAwFAbbvbnhPx66NhowFAYwFAaZJg8wFAaxKBDZurf/RB6mMxb/SCMwFAYwFAbxQB3+RB4wFAb/Qhy4Oh+4QifbNRcwFAYwFAYwFAb/QRzdNhgwFAYwFAbav7v/Uy7oaE68MBK5LxLewr/r2NXewLswFAaxJw4wFAbkPRy2PyYwFAaxKhLm1tMwFAazPiQwFAaUGAb/QBrfOx3bvrv/VC/maE4wFAbRPBq6MRO8Qynew8Dp2tjfwb0wFAbx6eju5+by6uns4uH9/f36+vr/GkHjAAAAYnRSTlMAGt+64rnWu/bo8eAA4InH3+DwoN7j4eLi4xP99Nfg4+b+/u9B/eDs1MD1mO7+4PHg2MXa347g7vDizMLN4eG+Pv7i5evs/v79yu7S3/DV7/498Yv24eH+4ufQ3Ozu/v7+y13sRqwAAADLSURBVHjaZc/XDsFgGIBhtDrshlitmk2IrbHFqL2pvXf/+78DPokj7+Fz9qpU/9UXJIlhmPaTaQ6QPaz0mm+5gwkgovcV6GZzd5JtCQwgsxoHOvJO15kleRLAnMgHFIESUEPmawB9ngmelTtipwwfASilxOLyiV5UVUyVAfbG0cCPHig+GBkzAENHS0AstVF6bacZIOzgLmxsHbt2OecNgJC83JERmePUYq8ARGkJx6XtFsdddBQgZE2nPR6CICZhawjA4Fb/chv+399kfR+MMMDGOQAAAABJRU5ErkJggg==\");background-repeat: no-repeat;background-position: 2px center;}.ace_gutter-cell.ace_warning {background-image: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAMAAAAoLQ9TAAAAmVBMVEX///8AAAD///8AAAAAAABPSzb/5sAAAAB/blH/73z/ulkAAAAAAAD85pkAAAAAAAACAgP/vGz/rkDerGbGrV7/pkQICAf////e0IsAAAD/oED/qTvhrnUAAAD/yHD/njcAAADuv2r/nz//oTj/p064oGf/zHAAAAA9Nir/tFIAAAD/tlTiuWf/tkIAAACynXEAAAAAAAAtIRW7zBpBAAAAM3RSTlMAABR1m7RXO8Ln31Z36zT+neXe5OzooRDfn+TZ4p3h2hTf4t3k3ucyrN1K5+Xaks52Sfs9CXgrAAAAjklEQVR42o3PbQ+CIBQFYEwboPhSYgoYunIqqLn6/z8uYdH8Vmdnu9vz4WwXgN/xTPRD2+sgOcZjsge/whXZgUaYYvT8QnuJaUrjrHUQreGczuEafQCO/SJTufTbroWsPgsllVhq3wJEk2jUSzX3CUEDJC84707djRc5MTAQxoLgupWRwW6UB5fS++NV8AbOZgnsC7BpEAAAAABJRU5ErkJggg==\");background-position: 2px center;}.ace_gutter-cell.ace_info {background-image: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAAAAAA6mKC9AAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAAJ0Uk5TAAB2k804AAAAPklEQVQY02NgIB68QuO3tiLznjAwpKTgNyDbMegwisCHZUETUZV0ZqOquBpXj2rtnpSJT1AEnnRmL2OgGgAAIKkRQap2htgAAAAASUVORK5CYII=\");background-position: 2px center;}.ace_dark .ace_gutter-cell.ace_info {background-image: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQBAMAAADt3eJSAAAAJFBMVEUAAAChoaGAgIAqKiq+vr6tra1ZWVmUlJSbm5s8PDxubm56enrdgzg3AAAAAXRSTlMAQObYZgAAAClJREFUeNpjYMAPdsMYHegyJZFQBlsUlMFVCWUYKkAZMxZAGdxlDMQBAG+TBP4B6RyJAAAAAElFTkSuQmCC\");}.ace_scrollbar {position: absolute;right: 0;bottom: 0;z-index: 6;}.ace_scrollbar-inner {position: absolute;cursor: text;left: 0;top: 0;}.ace_scrollbar-v{overflow-x: hidden;overflow-y: scroll;top: 0;}.ace_scrollbar-h {overflow-x: scroll;overflow-y: hidden;left: 0;}.ace_print-margin {position: absolute;height: 100%;}.ace_text-input {position: absolute;z-index: 0;width: 0.5em;height: 1em;opacity: 0;background: transparent;-moz-appearance: none;appearance: none;border: none;resize: none;outline: none;overflow: hidden;font: inherit;padding: 0 1px;margin: 0 -1px;text-indent: -1em;-ms-user-select: text;-moz-user-select: text;-webkit-user-select: text;user-select: text;white-space: pre!important;}.ace_text-input.ace_composition {background: inherit;color: inherit;z-index: 1000;opacity: 1;text-indent: 0;}.ace_layer {z-index: 1;position: absolute;overflow: hidden;word-wrap: normal;white-space: pre;height: 100%;width: 100%;-moz-box-sizing: border-box;-webkit-box-sizing: border-box;box-sizing: border-box;pointer-events: none;}.ace_gutter-layer {position: relative;width: auto;text-align: right;pointer-events: auto;}.ace_text-layer {font: inherit !important;}.ace_cjk {display: inline-block;text-align: center;}.ace_cursor-layer {z-index: 4;}.ace_cursor {z-index: 4;position: absolute;-moz-box-sizing: border-box;-webkit-box-sizing: border-box;box-sizing: border-box;border-left: 2px solid;transform: translatez(0);}.ace_slim-cursors .ace_cursor {border-left-width: 1px;}.ace_overwrite-cursors .ace_cursor {border-left-width: 0;border-bottom: 1px solid;}.ace_hidden-cursors .ace_cursor {opacity: 0.2;}.ace_smooth-blinking .ace_cursor {-webkit-transition: opacity 0.18s;transition: opacity 0.18s;}.ace_editor.ace_multiselect .ace_cursor {border-left-width: 1px;}.ace_marker-layer .ace_step, .ace_marker-layer .ace_stack {position: absolute;z-index: 3;}.ace_marker-layer .ace_selection {position: absolute;z-index: 5;}.ace_marker-layer .ace_bracket {position: absolute;z-index: 6;}.ace_marker-layer .ace_active-line {position: absolute;z-index: 2;}.ace_marker-layer .ace_selected-word {position: absolute;z-index: 4;-moz-box-sizing: border-box;-webkit-box-sizing: border-box;box-sizing: border-box;}.ace_line .ace_fold {-moz-box-sizing: border-box;-webkit-box-sizing: border-box;box-sizing: border-box;display: inline-block;height: 11px;margin-top: -2px;vertical-align: middle;background-image:url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABEAAAAJCAYAAADU6McMAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAJpJREFUeNpi/P//PwOlgAXGYGRklAVSokD8GmjwY1wasKljQpYACtpCFeADcHVQfQyMQAwzwAZI3wJKvCLkfKBaMSClBlR7BOQikCFGQEErIH0VqkabiGCAqwUadAzZJRxQr/0gwiXIal8zQQPnNVTgJ1TdawL0T5gBIP1MUJNhBv2HKoQHHjqNrA4WO4zY0glyNKLT2KIfIMAAQsdgGiXvgnYAAAAASUVORK5CYII=\"),url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAA3CAYAAADNNiA5AAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAACJJREFUeNpi+P//fxgTAwPDBxDxD078RSX+YeEyDFMCIMAAI3INmXiwf2YAAAAASUVORK5CYII=\");background-repeat: no-repeat, repeat-x;background-position: center center, top left;color: transparent;border: 1px solid black;border-radius: 2px;cursor: pointer;pointer-events: auto;}.ace_dark .ace_fold {}.ace_fold:hover{background-image:url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABEAAAAJCAYAAADU6McMAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAJpJREFUeNpi/P//PwOlgAXGYGRklAVSokD8GmjwY1wasKljQpYACtpCFeADcHVQfQyMQAwzwAZI3wJKvCLkfKBaMSClBlR7BOQikCFGQEErIH0VqkabiGCAqwUadAzZJRxQr/0gwiXIal8zQQPnNVTgJ1TdawL0T5gBIP1MUJNhBv2HKoQHHjqNrA4WO4zY0glyNKLT2KIfIMAAQsdgGiXvgnYAAAAASUVORK5CYII=\"),url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAA3CAYAAADNNiA5AAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAACBJREFUeNpi+P//fz4TAwPDZxDxD5X4i5fLMEwJgAADAEPVDbjNw87ZAAAAAElFTkSuQmCC\");}.ace_tooltip {background-color: #FFF;background-image: -webkit-linear-gradient(top, transparent, rgba(0, 0, 0, 0.1));background-image: linear-gradient(to bottom, transparent, rgba(0, 0, 0, 0.1));border: 1px solid gray;border-radius: 1px;box-shadow: 0 1px 2px rgba(0, 0, 0, 0.3);color: black;max-width: 100%;padding: 3px 4px;position: fixed;z-index: 999999;-moz-box-sizing: border-box;-webkit-box-sizing: border-box;box-sizing: border-box;cursor: default;white-space: pre;word-wrap: break-word;line-height: normal;font-style: normal;font-weight: normal;letter-spacing: normal;pointer-events: none;}.ace_folding-enabled > .ace_gutter-cell {padding-right: 13px;}.ace_fold-widget {-moz-box-sizing: border-box;-webkit-box-sizing: border-box;box-sizing: border-box;margin: 0 -12px 0 1px;display: none;width: 11px;vertical-align: top;background-image: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAUAAAAFCAYAAACNbyblAAAANElEQVR42mWKsQ0AMAzC8ixLlrzQjzmBiEjp0A6WwBCSPgKAXoLkqSot7nN3yMwR7pZ32NzpKkVoDBUxKAAAAABJRU5ErkJggg==\");background-repeat: no-repeat;background-position: center;border-radius: 3px;border: 1px solid transparent;cursor: pointer;}.ace_folding-enabled .ace_fold-widget {display: inline-block;   }.ace_fold-widget.ace_end {background-image: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAUAAAAFCAYAAACNbyblAAAANElEQVR42m3HwQkAMAhD0YzsRchFKI7sAikeWkrxwScEB0nh5e7KTPWimZki4tYfVbX+MNl4pyZXejUO1QAAAABJRU5ErkJggg==\");}.ace_fold-widget.ace_closed {background-image: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAMAAAAGCAYAAAAG5SQMAAAAOUlEQVR42jXKwQkAMAgDwKwqKD4EwQ26sSOkVWjgIIHAzPiCgaqiqnJHZnKICBERHN194O5b9vbLuAVRL+l0YWnZAAAAAElFTkSuQmCCXA==\");}.ace_fold-widget:hover {border: 1px solid rgba(0, 0, 0, 0.3);background-color: rgba(255, 255, 255, 0.2);box-shadow: 0 1px 1px rgba(255, 255, 255, 0.7);}.ace_fold-widget:active {border: 1px solid rgba(0, 0, 0, 0.4);background-color: rgba(0, 0, 0, 0.05);box-shadow: 0 1px 1px rgba(255, 255, 255, 0.8);}.ace_dark .ace_fold-widget {background-image: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAUAAAAFCAYAAACNbyblAAAAHklEQVQIW2P4//8/AzoGEQ7oGCaLLAhWiSwB146BAQCSTPYocqT0AAAAAElFTkSuQmCC\");}.ace_dark .ace_fold-widget.ace_end {background-image: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAUAAAAFCAYAAACNbyblAAAAH0lEQVQIW2P4//8/AxQ7wNjIAjDMgC4AxjCVKBirIAAF0kz2rlhxpAAAAABJRU5ErkJggg==\");}.ace_dark .ace_fold-widget.ace_closed {background-image: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAMAAAAFCAYAAACAcVaiAAAAHElEQVQIW2P4//+/AxAzgDADlOOAznHAKgPWAwARji8UIDTfQQAAAABJRU5ErkJggg==\");}.ace_dark .ace_fold-widget:hover {box-shadow: 0 1px 1px rgba(255, 255, 255, 0.2);background-color: rgba(255, 255, 255, 0.1);}.ace_dark .ace_fold-widget:active {box-shadow: 0 1px 1px rgba(255, 255, 255, 0.2);}.ace_fold-widget.ace_invalid {background-color: #FFB4B4;border-color: #DE5555;}.ace_fade-fold-widgets .ace_fold-widget {-webkit-transition: opacity 0.4s ease 0.05s;transition: opacity 0.4s ease 0.05s;opacity: 0;}.ace_fade-fold-widgets:hover .ace_fold-widget {-webkit-transition: opacity 0.05s ease 0.05s;transition: opacity 0.05s ease 0.05s;opacity:1;}.ace_underline {text-decoration: underline;}.ace_bold {font-weight: bold;}.ace_nobold .ace_bold {font-weight: normal;}.ace_italic {font-style: italic;}.ace_error-marker {background-color: rgba(255, 0, 0,0.2);position: absolute;z-index: 9;}.ace_highlight-marker {background-color: rgba(255, 255, 0,0.2);position: absolute;z-index: 8;}.ace_br1 {border-top-left-radius    : 3px;}.ace_br2 {border-top-right-radius   : 3px;}.ace_br3 {border-top-left-radius    : 3px; border-top-right-radius:    3px;}.ace_br4 {border-bottom-right-radius: 3px;}.ace_br5 {border-top-left-radius    : 3px; border-bottom-right-radius: 3px;}.ace_br6 {border-top-right-radius   : 3px; border-bottom-right-radius: 3px;}.ace_br7 {border-top-left-radius    : 3px; border-top-right-radius:    3px; border-bottom-right-radius: 3px;}.ace_br8 {border-bottom-left-radius : 3px;}.ace_br9 {border-top-left-radius    : 3px; border-bottom-left-radius:  3px;}.ace_br10{border-top-right-radius   : 3px; border-bottom-left-radius:  3px;}.ace_br11{border-top-left-radius    : 3px; border-top-right-radius:    3px; border-bottom-left-radius:  3px;}.ace_br12{border-bottom-right-radius: 3px; border-bottom-left-radius:  3px;}.ace_br13{border-top-left-radius    : 3px; border-bottom-right-radius: 3px; border-bottom-left-radius:  3px;}.ace_br14{border-top-right-radius   : 3px; border-bottom-right-radius: 3px; border-bottom-left-radius:  3px;}.ace_br15{border-top-left-radius    : 3px; border-top-right-radius:    3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px;}';i.importCssString(m,\"ace_editor.css\");var g=function(e,t){var n=this;this.container=e||i.createElement(\"div\"),this.$keepTextAreaAtCursor=!o.isOldIE,i.addCssClass(this.container,\"ace_editor\"),this.setTheme(t),this.$gutter=i.createElement(\"div\"),this.$gutter.className=\"ace_gutter\",this.container.appendChild(this.$gutter),this.scroller=i.createElement(\"div\"),this.scroller.className=\"ace_scroller\",this.container.appendChild(this.scroller),this.content=i.createElement(\"div\"),this.content.className=\"ace_content\",this.scroller.appendChild(this.content),this.$gutterLayer=new u(this.$gutter),this.$gutterLayer.on(\"changeGutterWidth\",this.onGutterResize.bind(this)),this.$markerBack=new a(this.content);var r=this.$textLayer=new f(this.content);this.canvas=r.element,this.$markerFront=new a(this.content),this.$cursorLayer=new l(this.content),this.$horizScroll=!1,this.$vScroll=!1,this.scrollBar=this.scrollBarV=new h(this.container,this),this.scrollBarH=new c(this.container,this),this.scrollBarV.addEventListener(\"scroll\",function(e){n.$scrollAnimation||n.session.setScrollTop(e.data-n.scrollMargin.top)}),this.scrollBarH.addEventListener(\"scroll\",function(e){n.$scrollAnimation||n.session.setScrollLeft(e.data-n.scrollMargin.left)}),this.scrollTop=0,this.scrollLeft=0,this.cursorPos={row:0,column:0},this.$fontMetrics=new d(this.container),this.$textLayer.$setFontMetrics(this.$fontMetrics),this.$textLayer.addEventListener(\"changeCharacterSize\",function(e){n.updateCharacterSize(),n.onResize(!0,n.gutterWidth,n.$size.width,n.$size.height),n._signal(\"changeCharacterSize\",e)}),this.$size={width:0,height:0,scrollerHeight:0,scrollerWidth:0,$dirty:!0},this.layerConfig={width:1,padding:0,firstRow:0,firstRowScreen:0,lastRow:0,lineHeight:0,characterWidth:0,minHeight:1,maxHeight:1,offset:0,height:1,gutterOffset:1},this.scrollMargin={left:0,right:0,top:0,bottom:0,v:0,h:0},this.$loop=new p(this.$renderChanges.bind(this),this.container.ownerDocument.defaultView),this.$loop.schedule(this.CHANGE_FULL),this.updateCharacterSize(),this.setPadding(4),s.resetOptions(this),s._emit(\"renderer\",this)};(function(){this.CHANGE_CURSOR=1,this.CHANGE_MARKER=2,this.CHANGE_GUTTER=4,this.CHANGE_SCROLL=8,this.CHANGE_LINES=16,this.CHANGE_TEXT=32,this.CHANGE_SIZE=64,this.CHANGE_MARKER_BACK=128,this.CHANGE_MARKER_FRONT=256,this.CHANGE_FULL=512,this.CHANGE_H_SCROLL=1024,r.implement(this,v),this.updateCharacterSize=function(){this.$textLayer.allowBoldFonts!=this.$allowBoldFonts&&(this.$allowBoldFonts=this.$textLayer.allowBoldFonts,this.setStyle(\"ace_nobold\",!this.$allowBoldFonts)),this.layerConfig.characterWidth=this.characterWidth=this.$textLayer.getCharacterWidth(),this.layerConfig.lineHeight=this.lineHeight=this.$textLayer.getLineHeight(),this.$updatePrintMargin()},this.setSession=function(e){this.session&&this.session.doc.off(\"changeNewLineMode\",this.onChangeNewLineMode),this.session=e,e&&this.scrollMargin.top&&e.getScrollTop()<=0&&e.setScrollTop(-this.scrollMargin.top),this.$cursorLayer.setSession(e),this.$markerBack.setSession(e),this.$markerFront.setSession(e),this.$gutterLayer.setSession(e),this.$textLayer.setSession(e);if(!e)return;this.$loop.schedule(this.CHANGE_FULL),this.session.$setFontMetrics(this.$fontMetrics),this.scrollBarV.scrollLeft=this.scrollBarV.scrollTop=null,this.onChangeNewLineMode=this.onChangeNewLineMode.bind(this),this.onChangeNewLineMode(),this.session.doc.on(\"changeNewLineMode\",this.onChangeNewLineMode)},this.updateLines=function(e,t,n){t===undefined&&(t=Infinity),this.$changedLines?(this.$changedLines.firstRow>e&&(this.$changedLines.firstRow=e),this.$changedLines.lastRow<t&&(this.$changedLines.lastRow=t)):this.$changedLines={firstRow:e,lastRow:t};if(this.$changedLines.lastRow<this.layerConfig.firstRow){if(!n)return;this.$changedLines.lastRow=this.layerConfig.lastRow}if(this.$changedLines.firstRow>this.layerConfig.lastRow)return;this.$loop.schedule(this.CHANGE_LINES)},this.onChangeNewLineMode=function(){this.$loop.schedule(this.CHANGE_TEXT),this.$textLayer.$updateEolChar()},this.onChangeTabSize=function(){this.$loop.schedule(this.CHANGE_TEXT|this.CHANGE_MARKER),this.$textLayer.onChangeTabSize()},this.updateText=function(){this.$loop.schedule(this.CHANGE_TEXT)},this.updateFull=function(e){e?this.$renderChanges(this.CHANGE_FULL,!0):this.$loop.schedule(this.CHANGE_FULL)},this.updateFontSize=function(){this.$textLayer.checkForSizeChanges()},this.$changes=0,this.$updateSizeAsync=function(){this.$loop.pending?this.$size.$dirty=!0:this.onResize()},this.onResize=function(e,t,n,r){if(this.resizing>2)return;this.resizing>0?this.resizing++:this.resizing=e?1:0;var i=this.container;r||(r=i.clientHeight||i.scrollHeight),n||(n=i.clientWidth||i.scrollWidth);var s=this.$updateCachedSize(e,t,n,r);if(!this.$size.scrollerHeight||!n&&!r)return this.resizing=0;e&&(this.$gutterLayer.$padding=null),e?this.$renderChanges(s|this.$changes,!0):this.$loop.schedule(s|this.$changes),this.resizing&&(this.resizing=0),this.scrollBarV.scrollLeft=this.scrollBarV.scrollTop=null},this.$updateCachedSize=function(e,t,n,r){r-=this.$extraHeight||0;var i=0,s=this.$size,o={width:s.width,height:s.height,scrollerHeight:s.scrollerHeight,scrollerWidth:s.scrollerWidth};r&&(e||s.height!=r)&&(s.height=r,i|=this.CHANGE_SIZE,s.scrollerHeight=s.height,this.$horizScroll&&(s.scrollerHeight-=this.scrollBarH.getHeight()),this.scrollBarV.element.style.bottom=this.scrollBarH.getHeight()+\"px\",i|=this.CHANGE_SCROLL);if(n&&(e||s.width!=n)){i|=this.CHANGE_SIZE,s.width=n,t==null&&(t=this.$showGutter?this.$gutter.offsetWidth:0),this.gutterWidth=t,this.scrollBarH.element.style.left=this.scroller.style.left=t+\"px\",s.scrollerWidth=Math.max(0,n-t-this.scrollBarV.getWidth()),this.scrollBarH.element.style.right=this.scroller.style.right=this.scrollBarV.getWidth()+\"px\",this.scroller.style.bottom=this.scrollBarH.getHeight()+\"px\";if(this.session&&this.session.getUseWrapMode()&&this.adjustWrapLimit()||e)i|=this.CHANGE_FULL}return s.$dirty=!n||!r,i&&this._signal(\"resize\",o),i},this.onGutterResize=function(){var e=this.$showGutter?this.$gutter.offsetWidth:0;e!=this.gutterWidth&&(this.$changes|=this.$updateCachedSize(!0,e,this.$size.width,this.$size.height)),this.session.getUseWrapMode()&&this.adjustWrapLimit()?this.$loop.schedule(this.CHANGE_FULL):this.$size.$dirty?this.$loop.schedule(this.CHANGE_FULL):(this.$computeLayerConfig(),this.$loop.schedule(this.CHANGE_MARKER))},this.adjustWrapLimit=function(){var e=this.$size.scrollerWidth-this.$padding*2,t=Math.floor(e/this.characterWidth);return this.session.adjustWrapLimit(t,this.$showPrintMargin&&this.$printMarginColumn)},this.setAnimatedScroll=function(e){this.setOption(\"animatedScroll\",e)},this.getAnimatedScroll=function(){return this.$animatedScroll},this.setShowInvisibles=function(e){this.setOption(\"showInvisibles\",e)},this.getShowInvisibles=function(){return this.getOption(\"showInvisibles\")},this.getDisplayIndentGuides=function(){return this.getOption(\"displayIndentGuides\")},this.setDisplayIndentGuides=function(e){this.setOption(\"displayIndentGuides\",e)},this.setShowPrintMargin=function(e){this.setOption(\"showPrintMargin\",e)},this.getShowPrintMargin=function(){return this.getOption(\"showPrintMargin\")},this.setPrintMarginColumn=function(e){this.setOption(\"printMarginColumn\",e)},this.getPrintMarginColumn=function(){return this.getOption(\"printMarginColumn\")},this.getShowGutter=function(){return this.getOption(\"showGutter\")},this.setShowGutter=function(e){return this.setOption(\"showGutter\",e)},this.getFadeFoldWidgets=function(){return this.getOption(\"fadeFoldWidgets\")},this.setFadeFoldWidgets=function(e){this.setOption(\"fadeFoldWidgets\",e)},this.setHighlightGutterLine=function(e){this.setOption(\"highlightGutterLine\",e)},this.getHighlightGutterLine=function(){return this.getOption(\"highlightGutterLine\")},this.$updateGutterLineHighlight=function(){var e=this.$cursorLayer.$pixelPos,t=this.layerConfig.lineHeight;if(this.session.getUseWrapMode()){var n=this.session.selection.getCursor();n.column=0,e=this.$cursorLayer.getPixelPosition(n,!0),t*=this.session.getRowLength(n.row)}this.$gutterLineHighlight.style.top=e.top-this.layerConfig.offset+\"px\",this.$gutterLineHighlight.style.height=t+\"px\"},this.$updatePrintMargin=function(){if(!this.$showPrintMargin&&!this.$printMarginEl)return;if(!this.$printMarginEl){var e=i.createElement(\"div\");e.className=\"ace_layer ace_print-margin-layer\",this.$printMarginEl=i.createElement(\"div\"),this.$printMarginEl.className=\"ace_print-margin\",e.appendChild(this.$printMarginEl),this.content.insertBefore(e,this.content.firstChild)}var t=this.$printMarginEl.style;t.left=this.characterWidth*this.$printMarginColumn+this.$padding+\"px\",t.visibility=this.$showPrintMargin?\"visible\":\"hidden\",this.session&&this.session.$wrap==-1&&this.adjustWrapLimit()},this.getContainerElement=function(){return this.container},this.getMouseEventTarget=function(){return this.scroller},this.getTextAreaContainer=function(){return this.container},this.$moveTextAreaToCursor=function(){if(!this.$keepTextAreaAtCursor)return;var e=this.layerConfig,t=this.$cursorLayer.$pixelPos.top,n=this.$cursorLayer.$pixelPos.left;t-=e.offset;var r=this.textarea.style,i=this.lineHeight;if(t<0||t>e.height-i){r.top=r.left=\"0\";return}var s=this.characterWidth;if(this.$composition){var o=this.textarea.value.replace(/^\\x01+/,\"\");s*=this.session.$getStringScreenWidth(o)[0]+2,i+=2}n-=this.scrollLeft,n>this.$size.scrollerWidth-s&&(n=this.$size.scrollerWidth-s),n+=this.gutterWidth,r.height=i+\"px\",r.width=s+\"px\",r.left=Math.min(n,this.$size.scrollerWidth-s)+\"px\",r.top=Math.min(t,this.$size.height-i)+\"px\"},this.getFirstVisibleRow=function(){return this.layerConfig.firstRow},this.getFirstFullyVisibleRow=function(){return this.layerConfig.firstRow+(this.layerConfig.offset===0?0:1)},this.getLastFullyVisibleRow=function(){var e=this.layerConfig,t=e.lastRow,n=this.session.documentToScreenRow(t,0)*e.lineHeight;return n-this.session.getScrollTop()>e.height-e.lineHeight?t-1:t},this.getLastVisibleRow=function(){return this.layerConfig.lastRow},this.$padding=null,this.setPadding=function(e){this.$padding=e,this.$textLayer.setPadding(e),this.$cursorLayer.setPadding(e),this.$markerFront.setPadding(e),this.$markerBack.setPadding(e),this.$loop.schedule(this.CHANGE_FULL),this.$updatePrintMargin()},this.setScrollMargin=function(e,t,n,r){var i=this.scrollMargin;i.top=e|0,i.bottom=t|0,i.right=r|0,i.left=n|0,i.v=i.top+i.bottom,i.h=i.left+i.right,i.top&&this.scrollTop<=0&&this.session&&this.session.setScrollTop(-i.top),this.updateFull()},this.getHScrollBarAlwaysVisible=function(){return this.$hScrollBarAlwaysVisible},this.setHScrollBarAlwaysVisible=function(e){this.setOption(\"hScrollBarAlwaysVisible\",e)},this.getVScrollBarAlwaysVisible=function(){return this.$vScrollBarAlwaysVisible},this.setVScrollBarAlwaysVisible=function(e){this.setOption(\"vScrollBarAlwaysVisible\",e)},this.$updateScrollBarV=function(){var e=this.layerConfig.maxHeight,t=this.$size.scrollerHeight;!this.$maxLines&&this.$scrollPastEnd&&(e-=(t-this.lineHeight)*this.$scrollPastEnd,this.scrollTop>e-t&&(e=this.scrollTop+t,this.scrollBarV.scrollTop=null)),this.scrollBarV.setScrollHeight(e+this.scrollMargin.v),this.scrollBarV.setScrollTop(this.scrollTop+this.scrollMargin.top)},this.$updateScrollBarH=function(){this.scrollBarH.setScrollWidth(this.layerConfig.width+2*this.$padding+this.scrollMargin.h),this.scrollBarH.setScrollLeft(this.scrollLeft+this.scrollMargin.left)},this.$frozen=!1,this.freeze=function(){this.$frozen=!0},this.unfreeze=function(){this.$frozen=!1},this.$renderChanges=function(e,t){this.$changes&&(e|=this.$changes,this.$changes=0);if(!this.session||!this.container.offsetWidth||this.$frozen||!e&&!t){this.$changes|=e;return}if(this.$size.$dirty)return this.$changes|=e,this.onResize(!0);this.lineHeight||this.$textLayer.checkForSizeChanges(),this._signal(\"beforeRender\");var n=this.layerConfig;if(e&this.CHANGE_FULL||e&this.CHANGE_SIZE||e&this.CHANGE_TEXT||e&this.CHANGE_LINES||e&this.CHANGE_SCROLL||e&this.CHANGE_H_SCROLL){e|=this.$computeLayerConfig();if(n.firstRow!=this.layerConfig.firstRow&&n.firstRowScreen==this.layerConfig.firstRowScreen){var r=this.scrollTop+(n.firstRow-this.layerConfig.firstRow)*this.lineHeight;r>0&&(this.scrollTop=r,e|=this.CHANGE_SCROLL,e|=this.$computeLayerConfig())}n=this.layerConfig,this.$updateScrollBarV(),e&this.CHANGE_H_SCROLL&&this.$updateScrollBarH(),this.$gutterLayer.element.style.marginTop=-n.offset+\"px\",this.content.style.marginTop=-n.offset+\"px\",this.content.style.width=n.width+2*this.$padding+\"px\",this.content.style.height=n.minHeight+\"px\"}e&this.CHANGE_H_SCROLL&&(this.content.style.marginLeft=-this.scrollLeft+\"px\",this.scroller.className=this.scrollLeft<=0?\"ace_scroller\":\"ace_scroller ace_scroll-left\");if(e&this.CHANGE_FULL){this.$textLayer.update(n),this.$showGutter&&this.$gutterLayer.update(n),this.$markerBack.update(n),this.$markerFront.update(n),this.$cursorLayer.update(n),this.$moveTextAreaToCursor(),this.$highlightGutterLine&&this.$updateGutterLineHighlight(),this._signal(\"afterRender\");return}if(e&this.CHANGE_SCROLL){e&this.CHANGE_TEXT||e&this.CHANGE_LINES?this.$textLayer.update(n):this.$textLayer.scrollLines(n),this.$showGutter&&this.$gutterLayer.update(n),this.$markerBack.update(n),this.$markerFront.update(n),this.$cursorLayer.update(n),this.$highlightGutterLine&&this.$updateGutterLineHighlight(),this.$moveTextAreaToCursor(),this._signal(\"afterRender\");return}e&this.CHANGE_TEXT?(this.$textLayer.update(n),this.$showGutter&&this.$gutterLayer.update(n)):e&this.CHANGE_LINES?(this.$updateLines()||e&this.CHANGE_GUTTER&&this.$showGutter)&&this.$gutterLayer.update(n):(e&this.CHANGE_TEXT||e&this.CHANGE_GUTTER)&&this.$showGutter&&this.$gutterLayer.update(n),e&this.CHANGE_CURSOR&&(this.$cursorLayer.update(n),this.$moveTextAreaToCursor(),this.$highlightGutterLine&&this.$updateGutterLineHighlight()),e&(this.CHANGE_MARKER|this.CHANGE_MARKER_FRONT)&&this.$markerFront.update(n),e&(this.CHANGE_MARKER|this.CHANGE_MARKER_BACK)&&this.$markerBack.update(n),this._signal(\"afterRender\")},this.$autosize=function(){var e=this.session.getScreenLength()*this.lineHeight,t=this.$maxLines*this.lineHeight,n=Math.min(t,Math.max((this.$minLines||1)*this.lineHeight,e))+this.scrollMargin.v+(this.$extraHeight||0);this.$horizScroll&&(n+=this.scrollBarH.getHeight()),this.$maxPixelHeight&&n>this.$maxPixelHeight&&(n=this.$maxPixelHeight);var r=e>t;if(n!=this.desiredHeight||this.$size.height!=this.desiredHeight||r!=this.$vScroll){r!=this.$vScroll&&(this.$vScroll=r,this.scrollBarV.setVisible(r));var i=this.container.clientWidth;this.container.style.height=n+\"px\",this.$updateCachedSize(!0,this.$gutterWidth,i,n),this.desiredHeight=n,this._signal(\"autosize\")}},this.$computeLayerConfig=function(){var e=this.session,t=this.$size,n=t.height<=2*this.lineHeight,r=this.session.getScreenLength(),i=r*this.lineHeight,s=this.$getLongestLine(),o=!n&&(this.$hScrollBarAlwaysVisible||t.scrollerWidth-s-2*this.$padding<0),u=this.$horizScroll!==o;u&&(this.$horizScroll=o,this.scrollBarH.setVisible(o));var a=this.$vScroll;this.$maxLines&&this.lineHeight>1&&this.$autosize();var f=this.scrollTop%this.lineHeight,l=t.scrollerHeight+this.lineHeight,c=!this.$maxLines&&this.$scrollPastEnd?(t.scrollerHeight-this.lineHeight)*this.$scrollPastEnd:0;i+=c;var h=this.scrollMargin;this.session.setScrollTop(Math.max(-h.top,Math.min(this.scrollTop,i-t.scrollerHeight+h.bottom))),this.session.setScrollLeft(Math.max(-h.left,Math.min(this.scrollLeft,s+2*this.$padding-t.scrollerWidth+h.right)));var p=!n&&(this.$vScrollBarAlwaysVisible||t.scrollerHeight-i+c<0||this.scrollTop>h.top),d=a!==p;d&&(this.$vScroll=p,this.scrollBarV.setVisible(p));var v=Math.ceil(l/this.lineHeight)-1,m=Math.max(0,Math.round((this.scrollTop-f)/this.lineHeight)),g=m+v,y,b,w=this.lineHeight;m=e.screenToDocumentRow(m,0);var E=e.getFoldLine(m);E&&(m=E.start.row),y=e.documentToScreenRow(m,0),b=e.getRowLength(m)*w,g=Math.min(e.screenToDocumentRow(g,0),e.getLength()-1),l=t.scrollerHeight+e.getRowLength(g)*w+b,f=this.scrollTop-y*w;var S=0;this.layerConfig.width!=s&&(S=this.CHANGE_H_SCROLL);if(u||d)S=this.$updateCachedSize(!0,this.gutterWidth,t.width,t.height),this._signal(\"scrollbarVisibilityChanged\"),d&&(s=this.$getLongestLine());return this.layerConfig={width:s,padding:this.$padding,firstRow:m,firstRowScreen:y,lastRow:g,lineHeight:w,characterWidth:this.characterWidth,minHeight:l,maxHeight:i,offset:f,gutterOffset:w?Math.max(0,Math.ceil((f+t.height-t.scrollerHeight)/w)):0,height:this.$size.scrollerHeight},S},this.$updateLines=function(){var e=this.$changedLines.firstRow,t=this.$changedLines.lastRow;this.$changedLines=null;var n=this.layerConfig;if(e>n.lastRow+1)return;if(t<n.firstRow)return;if(t===Infinity){this.$showGutter&&this.$gutterLayer.update(n),this.$textLayer.update(n);return}return this.$textLayer.updateLines(n,e,t),!0},this.$getLongestLine=function(){var e=this.session.getScreenWidth();return this.showInvisibles&&!this.session.$useWrapMode&&(e+=1),Math.max(this.$size.scrollerWidth-2*this.$padding,Math.round(e*this.characterWidth))},this.updateFrontMarkers=function(){this.$markerFront.setMarkers(this.session.getMarkers(!0)),this.$loop.schedule(this.CHANGE_MARKER_FRONT)},this.updateBackMarkers=function(){this.$markerBack.setMarkers(this.session.getMarkers()),this.$loop.schedule(this.CHANGE_MARKER_BACK)},this.addGutterDecoration=function(e,t){this.$gutterLayer.addGutterDecoration(e,t)},this.removeGutterDecoration=function(e,t){this.$gutterLayer.removeGutterDecoration(e,t)},this.updateBreakpoints=function(e){this.$loop.schedule(this.CHANGE_GUTTER)},this.setAnnotations=function(e){this.$gutterLayer.setAnnotations(e),this.$loop.schedule(this.CHANGE_GUTTER)},this.updateCursor=function(){this.$loop.schedule(this.CHANGE_CURSOR)},this.hideCursor=function(){this.$cursorLayer.hideCursor()},this.showCursor=function(){this.$cursorLayer.showCursor()},this.scrollSelectionIntoView=function(e,t,n){this.scrollCursorIntoView(e,n),this.scrollCursorIntoView(t,n)},this.scrollCursorIntoView=function(e,t,n){if(this.$size.scrollerHeight===0)return;var r=this.$cursorLayer.getPixelPosition(e),i=r.left,s=r.top,o=n&&n.top||0,u=n&&n.bottom||0,a=this.$scrollAnimation?this.session.getScrollTop():this.scrollTop;a+o>s?(t&&a+o>s+this.lineHeight&&(s-=t*this.$size.scrollerHeight),s===0&&(s=-this.scrollMargin.top),this.session.setScrollTop(s)):a+this.$size.scrollerHeight-u<s+this.lineHeight&&(t&&a+this.$size.scrollerHeight-u<s-this.lineHeight&&(s+=t*this.$size.scrollerHeight),this.session.setScrollTop(s+this.lineHeight-this.$size.scrollerHeight));var f=this.scrollLeft;f>i?(i<this.$padding+2*this.layerConfig.characterWidth&&(i=-this.scrollMargin.left),this.session.setScrollLeft(i)):f+this.$size.scrollerWidth<i+this.characterWidth?this.session.setScrollLeft(Math.round(i+this.characterWidth-this.$size.scrollerWidth)):f<=this.$padding&&i-f<this.characterWidth&&this.session.setScrollLeft(0)},this.getScrollTop=function(){return this.session.getScrollTop()},this.getScrollLeft=function(){return this.session.getScrollLeft()},this.getScrollTopRow=function(){return this.scrollTop/this.lineHeight},this.getScrollBottomRow=function(){return Math.max(0,Math.floor((this.scrollTop+this.$size.scrollerHeight)/this.lineHeight)-1)},this.scrollToRow=function(e){this.session.setScrollTop(e*this.lineHeight)},this.alignCursor=function(e,t){typeof e==\"number\"&&(e={row:e,column:0});var n=this.$cursorLayer.getPixelPosition(e),r=this.$size.scrollerHeight-this.lineHeight,i=n.top-r*(t||0);return this.session.setScrollTop(i),i},this.STEPS=8,this.$calcSteps=function(e,t){var n=0,r=this.STEPS,i=[],s=function(e,t,n){return n*(Math.pow(e-1,3)+1)+t};for(n=0;n<r;++n)i.push(s(n/this.STEPS,e,t-e));return i},this.scrollToLine=function(e,t,n,r){var i=this.$cursorLayer.getPixelPosition({row:e,column:0}),s=i.top;t&&(s-=this.$size.scrollerHeight/2);var o=this.scrollTop;this.session.setScrollTop(s),n!==!1&&this.animateScrolling(o,r)},this.animateScrolling=function(e,t){var n=this.scrollTop;if(!this.$animatedScroll)return;var r=this;if(e==n)return;if(this.$scrollAnimation){var i=this.$scrollAnimation.steps;if(i.length){e=i[0];if(e==n)return}}var s=r.$calcSteps(e,n);this.$scrollAnimation={from:e,to:n,steps:s},clearInterval(this.$timer),r.session.setScrollTop(s.shift()),r.session.$scrollTop=n,this.$timer=setInterval(function(){s.length?(r.session.setScrollTop(s.shift()),r.session.$scrollTop=n):n!=null?(r.session.$scrollTop=-1,r.session.setScrollTop(n),n=null):(r.$timer=clearInterval(r.$timer),r.$scrollAnimation=null,t&&t())},10)},this.scrollToY=function(e){this.scrollTop!==e&&(this.$loop.schedule(this.CHANGE_SCROLL),this.scrollTop=e)},this.scrollToX=function(e){this.scrollLeft!==e&&(this.scrollLeft=e),this.$loop.schedule(this.CHANGE_H_SCROLL)},this.scrollTo=function(e,t){this.session.setScrollTop(t),this.session.setScrollLeft(t)},this.scrollBy=function(e,t){t&&this.session.setScrollTop(this.session.getScrollTop()+t),e&&this.session.setScrollLeft(this.session.getScrollLeft()+e)},this.isScrollableBy=function(e,t){if(t<0&&this.session.getScrollTop()>=1-this.scrollMargin.top)return!0;if(t>0&&this.session.getScrollTop()+this.$size.scrollerHeight-this.layerConfig.maxHeight<-1+this.scrollMargin.bottom)return!0;if(e<0&&this.session.getScrollLeft()>=1-this.scrollMargin.left)return!0;if(e>0&&this.session.getScrollLeft()+this.$size.scrollerWidth-this.layerConfig.width<-1+this.scrollMargin.right)return!0},this.pixelToScreenCoordinates=function(e,t){var n=this.scroller.getBoundingClientRect(),r=(e+this.scrollLeft-n.left-this.$padding)/this.characterWidth,i=Math.floor((t+this.scrollTop-n.top)/this.lineHeight),s=Math.round(r);return{row:i,column:s,side:r-s>0?1:-1}},this.screenToTextCoordinates=function(e,t){var n=this.scroller.getBoundingClientRect(),r=Math.round((e+this.scrollLeft-n.left-this.$padding)/this.characterWidth),i=(t+this.scrollTop-n.top)/this.lineHeight;return this.session.screenToDocumentPosition(i,Math.max(r,0))},this.textToScreenCoordinates=function(e,t){var n=this.scroller.getBoundingClientRect(),r=this.session.documentToScreenPosition(e,t),i=this.$padding+Math.round(r.column*this.characterWidth),s=r.row*this.lineHeight;return{pageX:n.left+i-this.scrollLeft,pageY:n.top+s-this.scrollTop}},this.visualizeFocus=function(){i.addCssClass(this.container,\"ace_focus\")},this.visualizeBlur=function(){i.removeCssClass(this.container,\"ace_focus\")},this.showComposition=function(e){this.$composition||(this.$composition={keepTextAreaAtCursor:this.$keepTextAreaAtCursor,cssText:this.textarea.style.cssText}),this.$keepTextAreaAtCursor=!0,i.addCssClass(this.textarea,\"ace_composition\"),this.textarea.style.cssText=\"\",this.$moveTextAreaToCursor()},this.setCompositionText=function(e){this.$moveTextAreaToCursor()},this.hideComposition=function(){if(!this.$composition)return;i.removeCssClass(this.textarea,\"ace_composition\"),this.$keepTextAreaAtCursor=this.$composition.keepTextAreaAtCursor,this.textarea.style.cssText=this.$composition.cssText,this.$composition=null},this.setTheme=function(e,t){function o(r){if(n.$themeId!=e)return t&&t();if(!r||!r.cssClass)throw new Error(\"couldn't load module \"+e+\" or it didn't call define\");i.importCssString(r.cssText,r.cssClass,n.container.ownerDocument),n.theme&&i.removeCssClass(n.container,n.theme.cssClass);var s=\"padding\"in r?r.padding:\"padding\"in(n.theme||{})?4:n.$padding;n.$padding&&s!=n.$padding&&n.setPadding(s),n.$theme=r.cssClass,n.theme=r,i.addCssClass(n.container,r.cssClass),i.setCssClass(n.container,\"ace_dark\",r.isDark),n.$size&&(n.$size.width=0,n.$updateSizeAsync()),n._dispatchEvent(\"themeLoaded\",{theme:r}),t&&t()}var n=this;this.$themeId=e,n._dispatchEvent(\"themeChange\",{theme:e});if(!e||typeof e==\"string\"){var r=e||this.$options.theme.initialValue;s.loadModule([\"theme\",r],o)}else o(e)},this.getTheme=function(){return this.$themeId},this.setStyle=function(e,t){i.setCssClass(this.container,e,t!==!1)},this.unsetStyle=function(e){i.removeCssClass(this.container,e)},this.setCursorStyle=function(e){this.scroller.style.cursor!=e&&(this.scroller.style.cursor=e)},this.setMouseCursor=function(e){this.scroller.style.cursor=e},this.destroy=function(){this.$textLayer.destroy(),this.$cursorLayer.destroy()}}).call(g.prototype),s.defineOptions(g.prototype,\"renderer\",{animatedScroll:{initialValue:!1},showInvisibles:{set:function(e){this.$textLayer.setShowInvisibles(e)&&this.$loop.schedule(this.CHANGE_TEXT)},initialValue:!1},showPrintMargin:{set:function(){this.$updatePrintMargin()},initialValue:!0},printMarginColumn:{set:function(){this.$updatePrintMargin()},initialValue:80},printMargin:{set:function(e){typeof e==\"number\"&&(this.$printMarginColumn=e),this.$showPrintMargin=!!e,this.$updatePrintMargin()},get:function(){return this.$showPrintMargin&&this.$printMarginColumn}},showGutter:{set:function(e){this.$gutter.style.display=e?\"block\":\"none\",this.$loop.schedule(this.CHANGE_FULL),this.onGutterResize()},initialValue:!0},fadeFoldWidgets:{set:function(e){i.setCssClass(this.$gutter,\"ace_fade-fold-widgets\",e)},initialValue:!1},showFoldWidgets:{set:function(e){this.$gutterLayer.setShowFoldWidgets(e)},initialValue:!0},showLineNumbers:{set:function(e){this.$gutterLayer.setShowLineNumbers(e),this.$loop.schedule(this.CHANGE_GUTTER)},initialValue:!0},displayIndentGuides:{set:function(e){this.$textLayer.setDisplayIndentGuides(e)&&this.$loop.schedule(this.CHANGE_TEXT)},initialValue:!0},highlightGutterLine:{set:function(e){if(!this.$gutterLineHighlight){this.$gutterLineHighlight=i.createElement(\"div\"),this.$gutterLineHighlight.className=\"ace_gutter-active-line\",this.$gutter.appendChild(this.$gutterLineHighlight);return}this.$gutterLineHighlight.style.display=e?\"\":\"none\",this.$cursorLayer.$pixelPos&&this.$updateGutterLineHighlight()},initialValue:!1,value:!0},hScrollBarAlwaysVisible:{set:function(e){(!this.$hScrollBarAlwaysVisible||!this.$horizScroll)&&this.$loop.schedule(this.CHANGE_SCROLL)},initialValue:!1},vScrollBarAlwaysVisible:{set:function(e){(!this.$vScrollBarAlwaysVisible||!this.$vScroll)&&this.$loop.schedule(this.CHANGE_SCROLL)},initialValue:!1},fontSize:{set:function(e){typeof e==\"number\"&&(e+=\"px\"),this.container.style.fontSize=e,this.updateFontSize()},initialValue:12},fontFamily:{set:function(e){this.container.style.fontFamily=e,this.updateFontSize()}},maxLines:{set:function(e){this.updateFull()}},minLines:{set:function(e){this.updateFull()}},maxPixelHeight:{set:function(e){this.updateFull()},initialValue:0},scrollPastEnd:{set:function(e){e=+e||0;if(this.$scrollPastEnd==e)return;this.$scrollPastEnd=e,this.$loop.schedule(this.CHANGE_SCROLL)},initialValue:0,handlesSet:!0},fixedWidthGutter:{set:function(e){this.$gutterLayer.$fixedWidth=!!e,this.$loop.schedule(this.CHANGE_GUTTER)}},theme:{set:function(e){this.setTheme(e)},get:function(){return this.$themeId||this.theme},initialValue:\"./theme/textmate\",handlesSet:!0}}),t.VirtualRenderer=g}),define(\"ace/worker/worker_client\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/net\",\"ace/lib/event_emitter\",\"ace/config\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/net\"),s=e(\"../lib/event_emitter\").EventEmitter,o=e(\"../config\"),u=function(t,n,r,i){this.$sendDeltaQueue=this.$sendDeltaQueue.bind(this),this.changeListener=this.changeListener.bind(this),this.onMessage=this.onMessage.bind(this),e.nameToUrl&&!e.toUrl&&(e.toUrl=e.nameToUrl);if(o.get(\"packaged\")||!e.toUrl)i=i||o.moduleUrl(n,\"worker\");else{var s=this.$normalizePath;i=i||s(e.toUrl(\"ace/worker/worker.js\",null,\"_\"));var u={};t.forEach(function(t){u[t]=s(e.toUrl(t,null,\"_\").replace(/(\\.js)?(\\?.*)?$/,\"\"))})}try{this.$worker=new Worker(i)}catch(a){if(!(a instanceof window.DOMException))throw a;var f=this.$workerBlob(i),l=window.URL||window.webkitURL,c=l.createObjectURL(f);this.$worker=new Worker(c),l.revokeObjectURL(c)}this.$worker.postMessage({init:!0,tlns:u,module:n,classname:r}),this.callbackId=1,this.callbacks={},this.$worker.onmessage=this.onMessage};(function(){r.implement(this,s),this.onMessage=function(e){var t=e.data;switch(t.type){case\"event\":this._signal(t.name,{data:t.data});break;case\"call\":var n=this.callbacks[t.id];n&&(n(t.data),delete this.callbacks[t.id]);break;case\"error\":this.reportError(t.data);break;case\"log\":window.console&&console.log&&console.log.apply(console,t.data)}},this.reportError=function(e){window.console&&console.error&&console.error(e)},this.$normalizePath=function(e){return i.qualifyURL(e)},this.terminate=function(){this._signal(\"terminate\",{}),this.deltaQueue=null,this.$worker.terminate(),this.$worker=null,this.$doc&&this.$doc.off(\"change\",this.changeListener),this.$doc=null},this.send=function(e,t){this.$worker.postMessage({command:e,args:t})},this.call=function(e,t,n){if(n){var r=this.callbackId++;this.callbacks[r]=n,t.push(r)}this.send(e,t)},this.emit=function(e,t){try{this.$worker.postMessage({event:e,data:{data:t.data}})}catch(n){console.error(n.stack)}},this.attachToDocument=function(e){this.$doc&&this.terminate(),this.$doc=e,this.call(\"setValue\",[e.getValue()]),e.on(\"change\",this.changeListener)},this.changeListener=function(e){this.deltaQueue||(this.deltaQueue=[],setTimeout(this.$sendDeltaQueue,0)),e.action==\"insert\"?this.deltaQueue.push(e.start,e.lines):this.deltaQueue.push(e.start,e.end)},this.$sendDeltaQueue=function(){var e=this.deltaQueue;if(!e)return;this.deltaQueue=null,e.length>50&&e.length>this.$doc.getLength()>>1?this.call(\"setValue\",[this.$doc.getValue()]):this.emit(\"change\",{data:e})},this.$workerBlob=function(e){var t=\"importScripts('\"+i.qualifyURL(e)+\"');\";try{return new Blob([t],{type:\"application/javascript\"})}catch(n){var r=window.BlobBuilder||window.WebKitBlobBuilder||window.MozBlobBuilder,s=new r;return s.append(t),s.getBlob(\"application/javascript\")}}}).call(u.prototype);var a=function(e,t,n){this.$sendDeltaQueue=this.$sendDeltaQueue.bind(this),this.changeListener=this.changeListener.bind(this),this.callbackId=1,this.callbacks={},this.messageBuffer=[];var r=null,i=!1,u=Object.create(s),a=this;this.$worker={},this.$worker.terminate=function(){},this.$worker.postMessage=function(e){a.messageBuffer.push(e),r&&(i?setTimeout(f):f())},this.setEmitSync=function(e){i=e};var f=function(){var e=a.messageBuffer.shift();e.command?r[e.command].apply(r,e.args):e.event&&u._signal(e.event,e.data)};u.postMessage=function(e){a.onMessage({data:e})},u.callback=function(e,t){this.postMessage({type:\"call\",id:t,data:e})},u.emit=function(e,t){this.postMessage({type:\"event\",name:e,data:t})},o.loadModule([\"worker\",t],function(e){r=new e[n](u);while(a.messageBuffer.length)f()})};a.prototype=u.prototype,t.UIWorkerClient=a,t.WorkerClient=u}),define(\"ace/placeholder\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/lib/event_emitter\",\"ace/lib/oop\"],function(e,t,n){\"use strict\";var r=e(\"./range\").Range,i=e(\"./lib/event_emitter\").EventEmitter,s=e(\"./lib/oop\"),o=function(e,t,n,r,i,s){var o=this;this.length=t,this.session=e,this.doc=e.getDocument(),this.mainClass=i,this.othersClass=s,this.$onUpdate=this.onUpdate.bind(this),this.doc.on(\"change\",this.$onUpdate),this.$others=r,this.$onCursorChange=function(){setTimeout(function(){o.onCursorChange()})},this.$pos=n;var u=e.getUndoManager().$undoStack||e.getUndoManager().$undostack||{length:-1};this.$undoStackDepth=u.length,this.setup(),e.selection.on(\"changeCursor\",this.$onCursorChange)};(function(){s.implement(this,i),this.setup=function(){var e=this,t=this.doc,n=this.session;this.selectionBefore=n.selection.toJSON(),n.selection.inMultiSelectMode&&n.selection.toSingleRange(),this.pos=t.createAnchor(this.$pos.row,this.$pos.column);var i=this.pos;i.$insertRight=!0,i.detach(),i.markerId=n.addMarker(new r(i.row,i.column,i.row,i.column+this.length),this.mainClass,null,!1),this.others=[],this.$others.forEach(function(n){var r=t.createAnchor(n.row,n.column);r.$insertRight=!0,r.detach(),e.others.push(r)}),n.setUndoSelect(!1)},this.showOtherMarkers=function(){if(this.othersActive)return;var e=this.session,t=this;this.othersActive=!0,this.others.forEach(function(n){n.markerId=e.addMarker(new r(n.row,n.column,n.row,n.column+t.length),t.othersClass,null,!1)})},this.hideOtherMarkers=function(){if(!this.othersActive)return;this.othersActive=!1;for(var e=0;e<this.others.length;e++)this.session.removeMarker(this.others[e].markerId)},this.onUpdate=function(e){if(this.$updating)return this.updateAnchors(e);var t=e;if(t.start.row!==t.end.row)return;if(t.start.row!==this.pos.row)return;this.$updating=!0;var n=e.action===\"insert\"?t.end.column-t.start.column:t.start.column-t.end.column,i=t.start.column>=this.pos.column&&t.start.column<=this.pos.column+this.length+1,s=t.start.column-this.pos.column;this.updateAnchors(e),i&&(this.length+=n);if(i&&!this.session.$fromUndo)if(e.action===\"insert\")for(var o=this.others.length-1;o>=0;o--){var u=this.others[o],a={row:u.row,column:u.column+s};this.doc.insertMergedLines(a,e.lines)}else if(e.action===\"remove\")for(var o=this.others.length-1;o>=0;o--){var u=this.others[o],a={row:u.row,column:u.column+s};this.doc.remove(new r(a.row,a.column,a.row,a.column-n))}this.$updating=!1,this.updateMarkers()},this.updateAnchors=function(e){this.pos.onChange(e);for(var t=this.others.length;t--;)this.others[t].onChange(e);this.updateMarkers()},this.updateMarkers=function(){if(this.$updating)return;var e=this,t=this.session,n=function(n,i){t.removeMarker(n.markerId),n.markerId=t.addMarker(new r(n.row,n.column,n.row,n.column+e.length),i,null,!1)};n(this.pos,this.mainClass);for(var i=this.others.length;i--;)n(this.others[i],this.othersClass)},this.onCursorChange=function(e){if(this.$updating||!this.session)return;var t=this.session.selection.getCursor();t.row===this.pos.row&&t.column>=this.pos.column&&t.column<=this.pos.column+this.length?(this.showOtherMarkers(),this._emit(\"cursorEnter\",e)):(this.hideOtherMarkers(),this._emit(\"cursorLeave\",e))},this.detach=function(){this.session.removeMarker(this.pos&&this.pos.markerId),this.hideOtherMarkers(),this.doc.removeEventListener(\"change\",this.$onUpdate),this.session.selection.removeEventListener(\"changeCursor\",this.$onCursorChange),this.session.setUndoSelect(!0),this.session=null},this.cancel=function(){if(this.$undoStackDepth===-1)return;var e=this.session.getUndoManager(),t=(e.$undoStack||e.$undostack).length-this.$undoStackDepth;for(var n=0;n<t;n++)e.undo(!0);this.selectionBefore&&this.session.selection.fromJSON(this.selectionBefore)}}).call(o.prototype),t.PlaceHolder=o}),define(\"ace/mouse/multi_select_handler\",[\"require\",\"exports\",\"module\",\"ace/lib/event\",\"ace/lib/useragent\"],function(e,t,n){function s(e,t){return e.row==t.row&&e.column==t.column}function o(e){var t=e.domEvent,n=t.altKey,o=t.shiftKey,u=t.ctrlKey,a=e.getAccelKey(),f=e.getButton();u&&i.isMac&&(f=t.button);if(e.editor.inMultiSelectMode&&f==2){e.editor.textInput.onContextMenu(e.domEvent);return}if(!u&&!n&&!a){f===0&&e.editor.inMultiSelectMode&&e.editor.exitMultiSelectMode();return}if(f!==0)return;var l=e.editor,c=l.selection,h=l.inMultiSelectMode,p=e.getDocumentPosition(),d=c.getCursor(),v=e.inSelection()||c.isEmpty()&&s(p,d),m=e.x,g=e.y,y=function(e){m=e.clientX,g=e.clientY},b=l.session,w=l.renderer.pixelToScreenCoordinates(m,g),E=w,S;if(l.$mouseHandler.$enableJumpToDef)u&&n||a&&n?S=o?\"block\":\"add\":n&&l.$blockSelectEnabled&&(S=\"block\");else if(a&&!n){S=\"add\";if(!h&&o)return}else n&&l.$blockSelectEnabled&&(S=\"block\");S&&i.isMac&&t.ctrlKey&&l.$mouseHandler.cancelContextMenu();if(S==\"add\"){if(!h&&v)return;if(!h){var x=c.toOrientedRange();l.addSelectionMarker(x)}var T=c.rangeList.rangeAtPoint(p);l.$blockScrolling++,l.inVirtualSelectionMode=!0,o&&(T=null,x=c.ranges[0]||x,l.removeSelectionMarker(x)),l.once(\"mouseup\",function(){var e=c.toOrientedRange();T&&e.isEmpty()&&s(T.cursor,e.cursor)?c.substractPoint(e.cursor):(o?c.substractPoint(x.cursor):x&&(l.removeSelectionMarker(x),c.addRange(x)),c.addRange(e)),l.$blockScrolling--,l.inVirtualSelectionMode=!1})}else if(S==\"block\"){e.stop(),l.inVirtualSelectionMode=!0;var N,C=[],k=function(){var e=l.renderer.pixelToScreenCoordinates(m,g),t=b.screenToDocumentPosition(e.row,e.column);if(s(E,e)&&s(t,c.lead))return;E=e,l.$blockScrolling++,l.selection.moveToPosition(t),l.renderer.scrollCursorIntoView(),l.removeSelectionMarkers(C),C=c.rectangularRangeBlock(E,w),l.$mouseHandler.$clickSelection&&C.length==1&&C[0].isEmpty()&&(C[0]=l.$mouseHandler.$clickSelection.clone()),C.forEach(l.addSelectionMarker,l),l.updateSelectionMarkers(),l.$blockScrolling--};l.$blockScrolling++,h&&!a?c.toSingleRange():!h&&a&&(N=c.toOrientedRange(),l.addSelectionMarker(N)),o?w=b.documentToScreenPosition(c.lead):c.moveToPosition(p),l.$blockScrolling--,E={row:-1,column:-1};var L=function(e){clearInterval(O),l.removeSelectionMarkers(C),C.length||(C=[c.toOrientedRange()]),l.$blockScrolling++,N&&(l.removeSelectionMarker(N),c.toSingleRange(N));for(var t=0;t<C.length;t++)c.addRange(C[t]);l.inVirtualSelectionMode=!1,l.$mouseHandler.$clickSelection=null,l.$blockScrolling--},A=k;r.capture(l.container,y,L);var O=setInterval(function(){A()},20);return e.preventDefault()}}var r=e(\"../lib/event\"),i=e(\"../lib/useragent\");t.onMouseDown=o}),define(\"ace/commands/multi_select_commands\",[\"require\",\"exports\",\"module\",\"ace/keyboard/hash_handler\"],function(e,t,n){t.defaultCommands=[{name:\"addCursorAbove\",exec:function(e){e.selectMoreLines(-1)},bindKey:{win:\"Ctrl-Alt-Up\",mac:\"Ctrl-Alt-Up\"},scrollIntoView:\"cursor\",readOnly:!0},{name:\"addCursorBelow\",exec:function(e){e.selectMoreLines(1)},bindKey:{win:\"Ctrl-Alt-Down\",mac:\"Ctrl-Alt-Down\"},scrollIntoView:\"cursor\",readOnly:!0},{name:\"addCursorAboveSkipCurrent\",exec:function(e){e.selectMoreLines(-1,!0)},bindKey:{win:\"Ctrl-Alt-Shift-Up\",mac:\"Ctrl-Alt-Shift-Up\"},scrollIntoView:\"cursor\",readOnly:!0},{name:\"addCursorBelowSkipCurrent\",exec:function(e){e.selectMoreLines(1,!0)},bindKey:{win:\"Ctrl-Alt-Shift-Down\",mac:\"Ctrl-Alt-Shift-Down\"},scrollIntoView:\"cursor\",readOnly:!0},{name:\"selectMoreBefore\",exec:function(e){e.selectMore(-1)},bindKey:{win:\"Ctrl-Alt-Left\",mac:\"Ctrl-Alt-Left\"},scrollIntoView:\"cursor\",readOnly:!0},{name:\"selectMoreAfter\",exec:function(e){e.selectMore(1)},bindKey:{win:\"Ctrl-Alt-Right\",mac:\"Ctrl-Alt-Right\"},scrollIntoView:\"cursor\",readOnly:!0},{name:\"selectNextBefore\",exec:function(e){e.selectMore(-1,!0)},bindKey:{win:\"Ctrl-Alt-Shift-Left\",mac:\"Ctrl-Alt-Shift-Left\"},scrollIntoView:\"cursor\",readOnly:!0},{name:\"selectNextAfter\",exec:function(e){e.selectMore(1,!0)},bindKey:{win:\"Ctrl-Alt-Shift-Right\",mac:\"Ctrl-Alt-Shift-Right\"},scrollIntoView:\"cursor\",readOnly:!0},{name:\"splitIntoLines\",exec:function(e){e.multiSelect.splitIntoLines()},bindKey:{win:\"Ctrl-Alt-L\",mac:\"Ctrl-Alt-L\"},readOnly:!0},{name:\"alignCursors\",exec:function(e){e.alignCursors()},bindKey:{win:\"Ctrl-Alt-A\",mac:\"Ctrl-Alt-A\"},scrollIntoView:\"cursor\"},{name:\"findAll\",exec:function(e){e.findAll()},bindKey:{win:\"Ctrl-Alt-K\",mac:\"Ctrl-Alt-G\"},scrollIntoView:\"cursor\",readOnly:!0}],t.multiSelectCommands=[{name:\"singleSelection\",bindKey:\"esc\",exec:function(e){e.exitMultiSelectMode()},scrollIntoView:\"cursor\",readOnly:!0,isAvailable:function(e){return e&&e.inMultiSelectMode}}];var r=e(\"../keyboard/hash_handler\").HashHandler;t.keyboardHandler=new r(t.multiSelectCommands)}),define(\"ace/multi_select\",[\"require\",\"exports\",\"module\",\"ace/range_list\",\"ace/range\",\"ace/selection\",\"ace/mouse/multi_select_handler\",\"ace/lib/event\",\"ace/lib/lang\",\"ace/commands/multi_select_commands\",\"ace/search\",\"ace/edit_session\",\"ace/editor\",\"ace/config\"],function(e,t,n){function h(e,t,n){return c.$options.wrap=!0,c.$options.needle=t,c.$options.backwards=n==-1,c.find(e)}function v(e,t){return e.row==t.row&&e.column==t.column}function m(e){if(e.$multiselectOnSessionChange)return;e.$onAddRange=e.$onAddRange.bind(e),e.$onRemoveRange=e.$onRemoveRange.bind(e),e.$onMultiSelect=e.$onMultiSelect.bind(e),e.$onSingleSelect=e.$onSingleSelect.bind(e),e.$multiselectOnSessionChange=t.onSessionChange.bind(e),e.$checkMultiselectChange=e.$checkMultiselectChange.bind(e),e.$multiselectOnSessionChange(e),e.on(\"changeSession\",e.$multiselectOnSessionChange),e.on(\"mousedown\",o),e.commands.addCommands(f.defaultCommands),g(e)}function g(e){function r(t){n&&(e.renderer.setMouseCursor(\"\"),n=!1)}var t=e.textInput.getElement(),n=!1;u.addListener(t,\"keydown\",function(t){var i=t.keyCode==18&&!(t.ctrlKey||t.shiftKey||t.metaKey);e.$blockSelectEnabled&&i?n||(e.renderer.setMouseCursor(\"crosshair\"),n=!0):n&&r()}),u.addListener(t,\"keyup\",r),u.addListener(t,\"blur\",r)}var r=e(\"./range_list\").RangeList,i=e(\"./range\").Range,s=e(\"./selection\").Selection,o=e(\"./mouse/multi_select_handler\").onMouseDown,u=e(\"./lib/event\"),a=e(\"./lib/lang\"),f=e(\"./commands/multi_select_commands\");t.commands=f.defaultCommands.concat(f.multiSelectCommands);var l=e(\"./search\").Search,c=new l,p=e(\"./edit_session\").EditSession;(function(){this.getSelectionMarkers=function(){return this.$selectionMarkers}}).call(p.prototype),function(){this.ranges=null,this.rangeList=null,this.addRange=function(e,t){if(!e)return;if(!this.inMultiSelectMode&&this.rangeCount===0){var n=this.toOrientedRange();this.rangeList.add(n),this.rangeList.add(e);if(this.rangeList.ranges.length!=2)return this.rangeList.removeAll(),t||this.fromOrientedRange(e);this.rangeList.removeAll(),this.rangeList.add(n),this.$onAddRange(n)}e.cursor||(e.cursor=e.end);var r=this.rangeList.add(e);return this.$onAddRange(e),r.length&&this.$onRemoveRange(r),this.rangeCount>1&&!this.inMultiSelectMode&&(this._signal(\"multiSelect\"),this.inMultiSelectMode=!0,this.session.$undoSelect=!1,this.rangeList.attach(this.session)),t||this.fromOrientedRange(e)},this.toSingleRange=function(e){e=e||this.ranges[0];var t=this.rangeList.removeAll();t.length&&this.$onRemoveRange(t),e&&this.fromOrientedRange(e)},this.substractPoint=function(e){var t=this.rangeList.substractPoint(e);if(t)return this.$onRemoveRange(t),t[0]},this.mergeOverlappingRanges=function(){var e=this.rangeList.merge();e.length?this.$onRemoveRange(e):this.ranges[0]&&this.fromOrientedRange(this.ranges[0])},this.$onAddRange=function(e){this.rangeCount=this.rangeList.ranges.length,this.ranges.unshift(e),this._signal(\"addRange\",{range:e})},this.$onRemoveRange=function(e){this.rangeCount=this.rangeList.ranges.length;if(this.rangeCount==1&&this.inMultiSelectMode){var t=this.rangeList.ranges.pop();e.push(t),this.rangeCount=0}for(var n=e.length;n--;){var r=this.ranges.indexOf(e[n]);this.ranges.splice(r,1)}this._signal(\"removeRange\",{ranges:e}),this.rangeCount===0&&this.inMultiSelectMode&&(this.inMultiSelectMode=!1,this._signal(\"singleSelect\"),this.session.$undoSelect=!0,this.rangeList.detach(this.session)),t=t||this.ranges[0],t&&!t.isEqual(this.getRange())&&this.fromOrientedRange(t)},this.$initRangeList=function(){if(this.rangeList)return;this.rangeList=new r,this.ranges=[],this.rangeCount=0},this.getAllRanges=function(){return this.rangeCount?this.rangeList.ranges.concat():[this.getRange()]},this.splitIntoLines=function(){if(this.rangeCount>1){var e=this.rangeList.ranges,t=e[e.length-1],n=i.fromPoints(e[0].start,t.end);this.toSingleRange(),this.setSelectionRange(n,t.cursor==t.start)}else{var n=this.getRange(),r=this.isBackwards(),s=n.start.row,o=n.end.row;if(s==o){if(r)var u=n.end,a=n.start;else var u=n.start,a=n.end;this.addRange(i.fromPoints(a,a)),this.addRange(i.fromPoints(u,u));return}var f=[],l=this.getLineRange(s,!0);l.start.column=n.start.column,f.push(l);for(var c=s+1;c<o;c++)f.push(this.getLineRange(c,!0));l=this.getLineRange(o,!0),l.end.column=n.end.column,f.push(l),f.forEach(this.addRange,this)}},this.toggleBlockSelection=function(){if(this.rangeCount>1){var e=this.rangeList.ranges,t=e[e.length-1],n=i.fromPoints(e[0].start,t.end);this.toSingleRange(),this.setSelectionRange(n,t.cursor==t.start)}else{var r=this.session.documentToScreenPosition(this.selectionLead),s=this.session.documentToScreenPosition(this.selectionAnchor),o=this.rectangularRangeBlock(r,s);o.forEach(this.addRange,this)}},this.rectangularRangeBlock=function(e,t,n){var r=[],s=e.column<t.column;if(s)var o=e.column,u=t.column;else var o=t.column,u=e.column;var a=e.row<t.row;if(a)var f=e.row,l=t.row;else var f=t.row,l=e.row;o<0&&(o=0),f<0&&(f=0),f==l&&(n=!0);for(var c=f;c<=l;c++){var h=i.fromPoints(this.session.screenToDocumentPosition(c,o),this.session.screenToDocumentPosition(c,u));if(h.isEmpty()){if(p&&v(h.end,p))break;var p=h.end}h.cursor=s?h.start:h.end,r.push(h)}a&&r.reverse();if(!n){var d=r.length-1;while(r[d].isEmpty()&&d>0)d--;if(d>0){var m=0;while(r[m].isEmpty())m++}for(var g=d;g>=m;g--)r[g].isEmpty()&&r.splice(g,1)}return r}}.call(s.prototype);var d=e(\"./editor\").Editor;(function(){this.updateSelectionMarkers=function(){this.renderer.updateCursor(),this.renderer.updateBackMarkers()},this.addSelectionMarker=function(e){e.cursor||(e.cursor=e.end);var t=this.getSelectionStyle();return e.marker=this.session.addMarker(e,\"ace_selection\",t),this.session.$selectionMarkers.push(e),this.session.selectionMarkerCount=this.session.$selectionMarkers.length,e},this.removeSelectionMarker=function(e){if(!e.marker)return;this.session.removeMarker(e.marker);var t=this.session.$selectionMarkers.indexOf(e);t!=-1&&this.session.$selectionMarkers.splice(t,1),this.session.selectionMarkerCount=this.session.$selectionMarkers.length},this.removeSelectionMarkers=function(e){var t=this.session.$selectionMarkers;for(var n=e.length;n--;){var r=e[n];if(!r.marker)continue;this.session.removeMarker(r.marker);var i=t.indexOf(r);i!=-1&&t.splice(i,1)}this.session.selectionMarkerCount=t.length},this.$onAddRange=function(e){this.addSelectionMarker(e.range),this.renderer.updateCursor(),this.renderer.updateBackMarkers()},this.$onRemoveRange=function(e){this.removeSelectionMarkers(e.ranges),this.renderer.updateCursor(),this.renderer.updateBackMarkers()},this.$onMultiSelect=function(e){if(this.inMultiSelectMode)return;this.inMultiSelectMode=!0,this.setStyle(\"ace_multiselect\"),this.keyBinding.addKeyboardHandler(f.keyboardHandler),this.commands.setDefaultHandler(\"exec\",this.$onMultiSelectExec),this.renderer.updateCursor(),this.renderer.updateBackMarkers()},this.$onSingleSelect=function(e){if(this.session.multiSelect.inVirtualMode)return;this.inMultiSelectMode=!1,this.unsetStyle(\"ace_multiselect\"),this.keyBinding.removeKeyboardHandler(f.keyboardHandler),this.commands.removeDefaultHandler(\"exec\",this.$onMultiSelectExec),this.renderer.updateCursor(),this.renderer.updateBackMarkers(),this._emit(\"changeSelection\")},this.$onMultiSelectExec=function(e){var t=e.command,n=e.editor;if(!n.multiSelect)return;if(!t.multiSelectAction){var r=t.exec(n,e.args||{});n.multiSelect.addRange(n.multiSelect.toOrientedRange()),n.multiSelect.mergeOverlappingRanges()}else t.multiSelectAction==\"forEach\"?r=n.forEachSelection(t,e.args):t.multiSelectAction==\"forEachLine\"?r=n.forEachSelection(t,e.args,!0):t.multiSelectAction==\"single\"?(n.exitMultiSelectMode(),r=t.exec(n,e.args||{})):r=t.multiSelectAction(n,e.args||{});return r},this.forEachSelection=function(e,t,n){if(this.inVirtualSelectionMode)return;var r=n&&n.keepOrder,i=n==1||n&&n.$byLines,o=this.session,u=this.selection,a=u.rangeList,f=(r?u:a).ranges,l;if(!f.length)return e.exec?e.exec(this,t||{}):e(this,t||{});var c=u._eventRegistry;u._eventRegistry={};var h=new s(o);this.inVirtualSelectionMode=!0;for(var p=f.length;p--;){if(i)while(p>0&&f[p].start.row==f[p-1].end.row)p--;h.fromOrientedRange(f[p]),h.index=p,this.selection=o.selection=h;var d=e.exec?e.exec(this,t||{}):e(this,t||{});!l&&d!==undefined&&(l=d),h.toOrientedRange(f[p])}h.detach(),this.selection=o.selection=u,this.inVirtualSelectionMode=!1,u._eventRegistry=c,u.mergeOverlappingRanges();var v=this.renderer.$scrollAnimation;return this.onCursorChange(),this.onSelectionChange(),v&&v.from==v.to&&this.renderer.animateScrolling(v.from),l},this.exitMultiSelectMode=function(){if(!this.inMultiSelectMode||this.inVirtualSelectionMode)return;this.multiSelect.toSingleRange()},this.getSelectedText=function(){var e=\"\";if(this.inMultiSelectMode&&!this.inVirtualSelectionMode){var t=this.multiSelect.rangeList.ranges,n=[];for(var r=0;r<t.length;r++)n.push(this.session.getTextRange(t[r]));var i=this.session.getDocument().getNewLineCharacter();e=n.join(i),e.length==(n.length-1)*i.length&&(e=\"\")}else this.selection.isEmpty()||(e=this.session.getTextRange(this.getSelectionRange()));return e},this.$checkMultiselectChange=function(e,t){if(this.inMultiSelectMode&&!this.inVirtualSelectionMode){var n=this.multiSelect.ranges[0];if(this.multiSelect.isEmpty()&&t==this.multiSelect.anchor)return;var r=t==this.multiSelect.anchor?n.cursor==n.start?n.end:n.start:n.cursor;(r.row!=t.row||this.session.$clipPositionToDocument(r.row,r.column).column!=t.column)&&this.multiSelect.toSingleRange(this.multiSelect.toOrientedRange())}},this.findAll=function(e,t,n){t=t||{},t.needle=e||t.needle;if(t.needle==undefined){var r=this.selection.isEmpty()?this.selection.getWordRange():this.selection.getRange();t.needle=this.session.getTextRange(r)}this.$search.set(t);var i=this.$search.findAll(this.session);if(!i.length)return 0;this.$blockScrolling+=1;var s=this.multiSelect;n||s.toSingleRange(i[0]);for(var o=i.length;o--;)s.addRange(i[o],!0);return r&&s.rangeList.rangeAtPoint(r.start)&&s.addRange(r,!0),this.$blockScrolling-=1,i.length},this.selectMoreLines=function(e,t){var n=this.selection.toOrientedRange(),r=n.cursor==n.end,s=this.session.documentToScreenPosition(n.cursor);this.selection.$desiredColumn&&(s.column=this.selection.$desiredColumn);var o=this.session.screenToDocumentPosition(s.row+e,s.column);if(!n.isEmpty())var u=this.session.documentToScreenPosition(r?n.end:n.start),a=this.session.screenToDocumentPosition(u.row+e,u.column);else var a=o;if(r){var f=i.fromPoints(o,a);f.cursor=f.start}else{var f=i.fromPoints(a,o);f.cursor=f.end}f.desiredColumn=s.column;if(!this.selection.inMultiSelectMode)this.selection.addRange(n);else if(t)var l=n.cursor;this.selection.addRange(f),l&&this.selection.substractPoint(l)},this.transposeSelections=function(e){var t=this.session,n=t.multiSelect,r=n.ranges;for(var i=r.length;i--;){var s=r[i];if(s.isEmpty()){var o=t.getWordRange(s.start.row,s.start.column);s.start.row=o.start.row,s.start.column=o.start.column,s.end.row=o.end.row,s.end.column=o.end.column}}n.mergeOverlappingRanges();var u=[];for(var i=r.length;i--;){var s=r[i];u.unshift(t.getTextRange(s))}e<0?u.unshift(u.pop()):u.push(u.shift());for(var i=r.length;i--;){var s=r[i],o=s.clone();t.replace(s,u[i]),s.start.row=o.start.row,s.start.column=o.start.column}},this.selectMore=function(e,t,n){var r=this.session,i=r.multiSelect,s=i.toOrientedRange();if(s.isEmpty()){s=r.getWordRange(s.start.row,s.start.column),s.cursor=e==-1?s.start:s.end,this.multiSelect.addRange(s);if(n)return}var o=r.getTextRange(s),u=h(r,o,e);u&&(u.cursor=e==-1?u.start:u.end,this.$blockScrolling+=1,this.session.unfold(u),this.multiSelect.addRange(u),this.$blockScrolling-=1,this.renderer.scrollCursorIntoView(null,.5)),t&&this.multiSelect.substractPoint(s.cursor)},this.alignCursors=function(){var e=this.session,t=e.multiSelect,n=t.ranges,r=-1,s=n.filter(function(e){if(e.cursor.row==r)return!0;r=e.cursor.row});if(!n.length||s.length==n.length-1){var o=this.selection.getRange(),u=o.start.row,f=o.end.row,l=u==f;if(l){var c=this.session.getLength(),h;do h=this.session.getLine(f);while(/[=:]/.test(h)&&++f<c);do h=this.session.getLine(u);while(/[=:]/.test(h)&&--u>0);u<0&&(u=0),f>=c&&(f=c-1)}var p=this.session.removeFullLines(u,f);p=this.$reAlignText(p,l),this.session.insert({row:u,column:0},p.join(\"\\n\")+\"\\n\"),l||(o.start.column=0,o.end.column=p[p.length-1].length),this.selection.setRange(o)}else{s.forEach(function(e){t.substractPoint(e.cursor)});var d=0,v=Infinity,m=n.map(function(t){var n=t.cursor,r=e.getLine(n.row),i=r.substr(n.column).search(/\\S/g);return i==-1&&(i=0),n.column>d&&(d=n.column),i<v&&(v=i),i});n.forEach(function(t,n){var r=t.cursor,s=d-r.column,o=m[n]-v;s>o?e.insert(r,a.stringRepeat(\" \",s-o)):e.remove(new i(r.row,r.column,r.row,r.column-s+o)),t.start.column=t.end.column=d,t.start.row=t.end.row=r.row,t.cursor=t.end}),t.fromOrientedRange(n[0]),this.renderer.updateCursor(),this.renderer.updateBackMarkers()}},this.$reAlignText=function(e,t){function u(e){return a.stringRepeat(\" \",e)}function f(e){return e[2]?u(i)+e[2]+u(s-e[2].length+o)+e[4].replace(/^([=:])\\s+/,\"$1 \"):e[0]}function l(e){return e[2]?u(i+s-e[2].length)+e[2]+u(o,\" \")+e[4].replace(/^([=:])\\s+/,\"$1 \"):e[0]}function c(e){return e[2]?u(i)+e[2]+u(o)+e[4].replace(/^([=:])\\s+/,\"$1 \"):e[0]}var n=!0,r=!0,i,s,o;return e.map(function(e){var t=e.match(/(\\s*)(.*?)(\\s*)([=:].*)/);return t?i==null?(i=t[1].length,s=t[2].length,o=t[3].length,t):(i+s+o!=t[1].length+t[2].length+t[3].length&&(r=!1),i!=t[1].length&&(n=!1),i>t[1].length&&(i=t[1].length),s<t[2].length&&(s=t[2].length),o>t[3].length&&(o=t[3].length),t):[e]}).map(t?f:n?r?l:f:c)}}).call(d.prototype),t.onSessionChange=function(e){var t=e.session;t&&!t.multiSelect&&(t.$selectionMarkers=[],t.selection.$initRangeList(),t.multiSelect=t.selection),this.multiSelect=t&&t.multiSelect;var n=e.oldSession;n&&(n.multiSelect.off(\"addRange\",this.$onAddRange),n.multiSelect.off(\"removeRange\",this.$onRemoveRange),n.multiSelect.off(\"multiSelect\",this.$onMultiSelect),n.multiSelect.off(\"singleSelect\",this.$onSingleSelect),n.multiSelect.lead.off(\"change\",this.$checkMultiselectChange),n.multiSelect.anchor.off(\"change\",this.$checkMultiselectChange)),t&&(t.multiSelect.on(\"addRange\",this.$onAddRange),t.multiSelect.on(\"removeRange\",this.$onRemoveRange),t.multiSelect.on(\"multiSelect\",this.$onMultiSelect),t.multiSelect.on(\"singleSelect\",this.$onSingleSelect),t.multiSelect.lead.on(\"change\",this.$checkMultiselectChange),t.multiSelect.anchor.on(\"change\",this.$checkMultiselectChange)),t&&this.inMultiSelectMode!=t.selection.inMultiSelectMode&&(t.selection.inMultiSelectMode?this.$onMultiSelect():this.$onSingleSelect())},t.MultiSelect=m,e(\"./config\").defineOptions(d.prototype,\"editor\",{enableMultiselect:{set:function(e){m(this),e?(this.on(\"changeSession\",this.$multiselectOnSessionChange),this.on(\"mousedown\",o)):(this.off(\"changeSession\",this.$multiselectOnSessionChange),this.off(\"mousedown\",o))},value:!0},enableBlockSelect:{set:function(e){this.$blockSelectEnabled=e},value:!0}})}),define(\"ace/mode/folding/fold_mode\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../../range\").Range,i=t.FoldMode=function(){};(function(){this.foldingStartMarker=null,this.foldingStopMarker=null,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);return this.foldingStartMarker.test(r)?\"start\":t==\"markbeginend\"&&this.foldingStopMarker&&this.foldingStopMarker.test(r)?\"end\":\"\"},this.getFoldWidgetRange=function(e,t,n){return null},this.indentationBlock=function(e,t,n){var i=/\\S/,s=e.getLine(t),o=s.search(i);if(o==-1)return;var u=n||s.length,a=e.getLength(),f=t,l=t;while(++t<a){var c=e.getLine(t).search(i);if(c==-1)continue;if(c<=o)break;l=t}if(l>f){var h=e.getLine(l).length;return new r(f,u,l,h)}},this.openingBracketBlock=function(e,t,n,i,s){var o={row:n,column:i+1},u=e.$findClosingBracket(t,o,s);if(!u)return;var a=e.foldWidgets[u.row];return a==null&&(a=e.getFoldWidget(u.row)),a==\"start\"&&u.row>o.row&&(u.row--,u.column=e.getLine(u.row).length),r.fromPoints(o,u)},this.closingBracketBlock=function(e,t,n,i,s){var o={row:n,column:i},u=e.$findOpeningBracket(t,o);if(!u)return;return u.column++,o.column--,r.fromPoints(u,o)}}).call(i.prototype)}),define(\"ace/theme/textmate\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\"],function(e,t,n){\"use strict\";t.isDark=!1,t.cssClass=\"ace-tm\",t.cssText='.ace-tm .ace_gutter {background: #f0f0f0;color: #333;}.ace-tm .ace_print-margin {width: 1px;background: #e8e8e8;}.ace-tm .ace_fold {background-color: #6B72E6;}.ace-tm {background-color: #FFFFFF;color: black;}.ace-tm .ace_cursor {color: black;}.ace-tm .ace_invisible {color: rgb(191, 191, 191);}.ace-tm .ace_storage,.ace-tm .ace_keyword {color: blue;}.ace-tm .ace_constant {color: rgb(197, 6, 11);}.ace-tm .ace_constant.ace_buildin {color: rgb(88, 72, 246);}.ace-tm .ace_constant.ace_language {color: rgb(88, 92, 246);}.ace-tm .ace_constant.ace_library {color: rgb(6, 150, 14);}.ace-tm .ace_invalid {background-color: rgba(255, 0, 0, 0.1);color: red;}.ace-tm .ace_support.ace_function {color: rgb(60, 76, 114);}.ace-tm .ace_support.ace_constant {color: rgb(6, 150, 14);}.ace-tm .ace_support.ace_type,.ace-tm .ace_support.ace_class {color: rgb(109, 121, 222);}.ace-tm .ace_keyword.ace_operator {color: rgb(104, 118, 135);}.ace-tm .ace_string {color: rgb(3, 106, 7);}.ace-tm .ace_comment {color: rgb(76, 136, 107);}.ace-tm .ace_comment.ace_doc {color: rgb(0, 102, 255);}.ace-tm .ace_comment.ace_doc.ace_tag {color: rgb(128, 159, 191);}.ace-tm .ace_constant.ace_numeric {color: rgb(0, 0, 205);}.ace-tm .ace_variable {color: rgb(49, 132, 149);}.ace-tm .ace_xml-pe {color: rgb(104, 104, 91);}.ace-tm .ace_entity.ace_name.ace_function {color: #0000A2;}.ace-tm .ace_heading {color: rgb(12, 7, 255);}.ace-tm .ace_list {color:rgb(185, 6, 144);}.ace-tm .ace_meta.ace_tag {color:rgb(0, 22, 142);}.ace-tm .ace_string.ace_regex {color: rgb(255, 0, 0)}.ace-tm .ace_marker-layer .ace_selection {background: rgb(181, 213, 255);}.ace-tm.ace_multiselect .ace_selection.ace_start {box-shadow: 0 0 3px 0px white;}.ace-tm .ace_marker-layer .ace_step {background: rgb(252, 255, 0);}.ace-tm .ace_marker-layer .ace_stack {background: rgb(164, 229, 101);}.ace-tm .ace_marker-layer .ace_bracket {margin: -1px 0 0 -1px;border: 1px solid rgb(192, 192, 192);}.ace-tm .ace_marker-layer .ace_active-line {background: rgba(0, 0, 0, 0.07);}.ace-tm .ace_gutter-active-line {background-color : #dcdcdc;}.ace-tm .ace_marker-layer .ace_selected-word {background: rgb(250, 250, 255);border: 1px solid rgb(200, 200, 250);}.ace-tm .ace_indent-guide {background: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAACCAYAAACZgbYnAAAAE0lEQVQImWP4////f4bLly//BwAmVgd1/w11/gAAAABJRU5ErkJggg==\") right repeat-y;}';var r=e(\"../lib/dom\");r.importCssString(t.cssText,t.cssClass)}),define(\"ace/line_widgets\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/dom\",\"ace/range\"],function(e,t,n){\"use strict\";function o(e){this.session=e,this.session.widgetManager=this,this.session.getRowLength=this.getRowLength,this.session.$getWidgetScreenLength=this.$getWidgetScreenLength,this.updateOnChange=this.updateOnChange.bind(this),this.renderWidgets=this.renderWidgets.bind(this),this.measureWidgets=this.measureWidgets.bind(this),this.session._changedWidgets=[],this.$onChangeEditor=this.$onChangeEditor.bind(this),this.session.on(\"change\",this.updateOnChange),this.session.on(\"changeFold\",this.updateOnFold),this.session.on(\"changeEditor\",this.$onChangeEditor)}var r=e(\"./lib/oop\"),i=e(\"./lib/dom\"),s=e(\"./range\").Range;(function(){this.getRowLength=function(e){var t;return this.lineWidgets?t=this.lineWidgets[e]&&this.lineWidgets[e].rowCount||0:t=0,!this.$useWrapMode||!this.$wrapData[e]?1+t:this.$wrapData[e].length+1+t},this.$getWidgetScreenLength=function(){var e=0;return this.lineWidgets.forEach(function(t){t&&t.rowCount&&!t.hidden&&(e+=t.rowCount)}),e},this.$onChangeEditor=function(e){this.attach(e.editor)},this.attach=function(e){e&&e.widgetManager&&e.widgetManager!=this&&e.widgetManager.detach();if(this.editor==e)return;this.detach(),this.editor=e,e&&(e.widgetManager=this,e.renderer.on(\"beforeRender\",this.measureWidgets),e.renderer.on(\"afterRender\",this.renderWidgets))},this.detach=function(e){var t=this.editor;if(!t)return;this.editor=null,t.widgetManager=null,t.renderer.off(\"beforeRender\",this.measureWidgets),t.renderer.off(\"afterRender\",this.renderWidgets);var n=this.session.lineWidgets;n&&n.forEach(function(e){e&&e.el&&e.el.parentNode&&(e._inDocument=!1,e.el.parentNode.removeChild(e.el))})},this.updateOnFold=function(e,t){var n=t.lineWidgets;if(!n||!e.action)return;var r=e.data,i=r.start.row,s=r.end.row,o=e.action==\"add\";for(var u=i+1;u<s;u++)n[u]&&(n[u].hidden=o);n[s]&&(o?n[i]?n[s].hidden=o:n[i]=n[s]:(n[i]==n[s]&&(n[i]=undefined),n[s].hidden=o))},this.updateOnChange=function(e){var t=this.session.lineWidgets;if(!t)return;var n=e.start.row,r=e.end.row-n;if(r!==0)if(e.action==\"remove\"){var i=t.splice(n+1,r);i.forEach(function(e){e&&this.removeLineWidget(e)},this),this.$updateRows()}else{var s=new Array(r);s.unshift(n,0),t.splice.apply(t,s),this.$updateRows()}},this.$updateRows=function(){var e=this.session.lineWidgets;if(!e)return;var t=!0;e.forEach(function(e,n){if(e){t=!1,e.row=n;while(e.$oldWidget)e.$oldWidget.row=n,e=e.$oldWidget}}),t&&(this.session.lineWidgets=null)},this.addLineWidget=function(e){this.session.lineWidgets||(this.session.lineWidgets=new Array(this.session.getLength()));var t=this.session.lineWidgets[e.row];t&&(e.$oldWidget=t,t.el&&t.el.parentNode&&(t.el.parentNode.removeChild(t.el),t._inDocument=!1)),this.session.lineWidgets[e.row]=e,e.session=this.session;var n=this.editor.renderer;e.html&&!e.el&&(e.el=i.createElement(\"div\"),e.el.innerHTML=e.html),e.el&&(i.addCssClass(e.el,\"ace_lineWidgetContainer\"),e.el.style.position=\"absolute\",e.el.style.zIndex=5,n.container.appendChild(e.el),e._inDocument=!0),e.coverGutter||(e.el.style.zIndex=3),e.pixelHeight==null&&(e.pixelHeight=e.el.offsetHeight),e.rowCount==null&&(e.rowCount=e.pixelHeight/n.layerConfig.lineHeight);var r=this.session.getFoldAt(e.row,0);e.$fold=r;if(r){var s=this.session.lineWidgets;e.row==r.end.row&&!s[r.start.row]?s[r.start.row]=e:e.hidden=!0}return this.session._emit(\"changeFold\",{data:{start:{row:e.row}}}),this.$updateRows(),this.renderWidgets(null,n),this.onWidgetChanged(e),e},this.removeLineWidget=function(e){e._inDocument=!1,e.session=null,e.el&&e.el.parentNode&&e.el.parentNode.removeChild(e.el);if(e.editor&&e.editor.destroy)try{e.editor.destroy()}catch(t){}if(this.session.lineWidgets){var n=this.session.lineWidgets[e.row];if(n==e)this.session.lineWidgets[e.row]=e.$oldWidget,e.$oldWidget&&this.onWidgetChanged(e.$oldWidget);else while(n){if(n.$oldWidget==e){n.$oldWidget=e.$oldWidget;break}n=n.$oldWidget}}this.session._emit(\"changeFold\",{data:{start:{row:e.row}}}),this.$updateRows()},this.getWidgetsAtRow=function(e){var t=this.session.lineWidgets,n=t&&t[e],r=[];while(n)r.push(n),n=n.$oldWidget;return r},this.onWidgetChanged=function(e){this.session._changedWidgets.push(e),this.editor&&this.editor.renderer.updateFull()},this.measureWidgets=function(e,t){var n=this.session._changedWidgets,r=t.layerConfig;if(!n||!n.length)return;var i=Infinity;for(var s=0;s<n.length;s++){var o=n[s];if(!o||!o.el)continue;if(o.session!=this.session)continue;if(!o._inDocument){if(this.session.lineWidgets[o.row]!=o)continue;o._inDocument=!0,t.container.appendChild(o.el)}o.h=o.el.offsetHeight,o.fixedWidth||(o.w=o.el.offsetWidth,o.screenWidth=Math.ceil(o.w/r.characterWidth));var u=o.h/r.lineHeight;o.coverLine&&(u-=this.session.getRowLineCount(o.row),u<0&&(u=0)),o.rowCount!=u&&(o.rowCount=u,o.row<i&&(i=o.row))}i!=Infinity&&(this.session._emit(\"changeFold\",{data:{start:{row:i}}}),this.session.lineWidgetWidth=null),this.session._changedWidgets=[]},this.renderWidgets=function(e,t){var n=t.layerConfig,r=this.session.lineWidgets;if(!r)return;var i=Math.min(this.firstRow,n.firstRow),s=Math.max(this.lastRow,n.lastRow,r.length);while(i>0&&!r[i])i--;this.firstRow=n.firstRow,this.lastRow=n.lastRow,t.$cursorLayer.config=n;for(var o=i;o<=s;o++){var u=r[o];if(!u||!u.el)continue;if(u.hidden){u.el.style.top=-100-(u.pixelHeight||0)+\"px\";continue}u._inDocument||(u._inDocument=!0,t.container.appendChild(u.el));var a=t.$cursorLayer.getPixelPosition({row:o,column:0},!0).top;u.coverLine||(a+=n.lineHeight*this.session.getRowLineCount(u.row)),u.el.style.top=a-n.offset+\"px\";var f=u.coverGutter?0:t.gutterWidth;u.fixedWidth||(f-=t.scrollLeft),u.el.style.left=f+\"px\",u.fullWidth&&u.screenWidth&&(u.el.style.minWidth=n.width+2*n.padding+\"px\"),u.fixedWidth?u.el.style.right=t.scrollBar.getWidth()+\"px\":u.el.style.right=\"\"}}}).call(o.prototype),t.LineWidgets=o}),define(\"ace/ext/error_marker\",[\"require\",\"exports\",\"module\",\"ace/line_widgets\",\"ace/lib/dom\",\"ace/range\"],function(e,t,n){\"use strict\";function o(e,t,n){var r=0,i=e.length-1;while(r<=i){var s=r+i>>1,o=n(t,e[s]);if(o>0)r=s+1;else{if(!(o<0))return s;i=s-1}}return-(r+1)}function u(e,t,n){var r=e.getAnnotations().sort(s.comparePoints);if(!r.length)return;var i=o(r,{row:t,column:-1},s.comparePoints);i<0&&(i=-i-1),i>=r.length?i=n>0?0:r.length-1:i===0&&n<0&&(i=r.length-1);var u=r[i];if(!u||!n)return;if(u.row===t){do u=r[i+=n];while(u&&u.row===t);if(!u)return r.slice()}var a=[];t=u.row;do a[n<0?\"unshift\":\"push\"](u),u=r[i+=n];while(u&&u.row==t);return a.length&&a}var r=e(\"../line_widgets\").LineWidgets,i=e(\"../lib/dom\"),s=e(\"../range\").Range;t.showErrorMarker=function(e,t){var n=e.session;n.widgetManager||(n.widgetManager=new r(n),n.widgetManager.attach(e));var s=e.getCursorPosition(),o=s.row,a=n.widgetManager.getWidgetsAtRow(o).filter(function(e){return e.type==\"errorMarker\"})[0];a?a.destroy():o-=t;var f=u(n,o,t),l;if(f){var c=f[0];s.column=(c.pos&&typeof c.column!=\"number\"?c.pos.sc:c.column)||0,s.row=c.row,l=e.renderer.$gutterLayer.$annotations[s.row]}else{if(a)return;l={text:[\"Looks good!\"],className:\"ace_ok\"}}e.session.unfold(s.row),e.selection.moveToPosition(s);var h={row:s.row,fixedWidth:!0,coverGutter:!0,el:i.createElement(\"div\"),type:\"errorMarker\"},p=h.el.appendChild(i.createElement(\"div\")),d=h.el.appendChild(i.createElement(\"div\"));d.className=\"error_widget_arrow \"+l.className;var v=e.renderer.$cursorLayer.getPixelPosition(s).left;d.style.left=v+e.renderer.gutterWidth-5+\"px\",h.el.className=\"error_widget_wrapper\",p.className=\"error_widget \"+l.className,p.innerHTML=l.text.join(\"<br>\"),p.appendChild(i.createElement(\"div\"));var m=function(e,t,n){if(t===0&&(n===\"esc\"||n===\"return\"))return h.destroy(),{command:\"null\"}};h.destroy=function(){if(e.$mouseHandler.isMousePressed)return;e.keyBinding.removeKeyboardHandler(m),n.widgetManager.removeLineWidget(h),e.off(\"changeSelection\",h.destroy),e.off(\"changeSession\",h.destroy),e.off(\"mouseup\",h.destroy),e.off(\"change\",h.destroy)},e.keyBinding.addKeyboardHandler(m),e.on(\"changeSelection\",h.destroy),e.on(\"changeSession\",h.destroy),e.on(\"mouseup\",h.destroy),e.on(\"change\",h.destroy),e.session.widgetManager.addLineWidget(h),h.el.onmousedown=e.focus.bind(e),e.renderer.scrollCursorIntoView(null,.5,{bottom:h.el.offsetHeight})},i.importCssString(\"    .error_widget_wrapper {        background: inherit;        color: inherit;        border:none    }    .error_widget {        border-top: solid 2px;        border-bottom: solid 2px;        margin: 5px 0;        padding: 10px 40px;        white-space: pre-wrap;    }    .error_widget.ace_error, .error_widget_arrow.ace_error{        border-color: #ff5a5a    }    .error_widget.ace_warning, .error_widget_arrow.ace_warning{        border-color: #F1D817    }    .error_widget.ace_info, .error_widget_arrow.ace_info{        border-color: #5a5a5a    }    .error_widget.ace_ok, .error_widget_arrow.ace_ok{        border-color: #5aaa5a    }    .error_widget_arrow {        position: absolute;        border: solid 5px;        border-top-color: transparent!important;        border-right-color: transparent!important;        border-left-color: transparent!important;        top: -5px;    }\",\"\")}),define(\"ace/ace\",[\"require\",\"exports\",\"module\",\"ace/lib/fixoldbrowsers\",\"ace/lib/dom\",\"ace/lib/event\",\"ace/editor\",\"ace/edit_session\",\"ace/undomanager\",\"ace/virtual_renderer\",\"ace/worker/worker_client\",\"ace/keyboard/hash_handler\",\"ace/placeholder\",\"ace/multi_select\",\"ace/mode/folding/fold_mode\",\"ace/theme/textmate\",\"ace/ext/error_marker\",\"ace/config\"],function(e,t,n){\"use strict\";e(\"./lib/fixoldbrowsers\");var r=e(\"./lib/dom\"),i=e(\"./lib/event\"),s=e(\"./editor\").Editor,o=e(\"./edit_session\").EditSession,u=e(\"./undomanager\").UndoManager,a=e(\"./virtual_renderer\").VirtualRenderer;e(\"./worker/worker_client\"),e(\"./keyboard/hash_handler\"),e(\"./placeholder\"),e(\"./multi_select\"),e(\"./mode/folding/fold_mode\"),e(\"./theme/textmate\"),e(\"./ext/error_marker\"),t.config=e(\"./config\"),t.require=e,typeof define==\"function\"&&(t.define=define),t.edit=function(e){if(typeof e==\"string\"){var n=e;e=document.getElementById(n);if(!e)throw new Error(\"ace.edit can't find div #\"+n)}if(e&&e.env&&e.env.editor instanceof s)return e.env.editor;var o=\"\";if(e&&/input|textarea/i.test(e.tagName)){var u=e;o=u.value,e=r.createElement(\"pre\"),u.parentNode.replaceChild(e,u)}else e&&(o=r.getInnerText(e),e.innerHTML=\"\");var f=t.createEditSession(o),l=new s(new a(e));l.setSession(f);var c={document:f,editor:l,onResize:l.resize.bind(l,null)};return u&&(c.textarea=u),i.addListener(window,\"resize\",c.onResize),l.on(\"destroy\",function(){i.removeListener(window,\"resize\",c.onResize),c.editor.container.env=null}),l.container.env=l.env=c,l},t.createEditSession=function(e,t){var n=new o(e,t);return n.setUndoManager(new u),n},t.EditSession=o,t.UndoManager=u,t.version=\"1.2.6\"});\n            (function() {\n                window.require([\"ace/ace\"], function(a) {\n                    if (a) {\n                        a.config.init(true);\n                        a.define = window.define;\n                    }\n                    if (!window.ace)\n                        window.ace = a;\n                    for (var key in a) if (a.hasOwnProperty(key))\n                        window.ace[key] = a[key];\n                });\n            })();\n        "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-elastic_tabstops_lite.js",
    "content": "define(\"ace/ext/elastic_tabstops_lite\",[\"require\",\"exports\",\"module\",\"ace/editor\",\"ace/config\"],function(e,t,n){\"use strict\";var r=function(e){this.$editor=e;var t=this,n=[],r=!1;this.onAfterExec=function(){r=!1,t.processRows(n),n=[]},this.onExec=function(){r=!0},this.onChange=function(e){r&&(n.indexOf(e.start.row)==-1&&n.push(e.start.row),e.end.row!=e.start.row&&n.push(e.end.row))}};(function(){this.processRows=function(e){this.$inChange=!0;var t=[];for(var n=0,r=e.length;n<r;n++){var i=e[n];if(t.indexOf(i)>-1)continue;var s=this.$findCellWidthsForBlock(i),o=this.$setBlockCellWidthsToMax(s.cellWidths),u=s.firstRow;for(var a=0,f=o.length;a<f;a++){var l=o[a];t.push(u),this.$adjustRow(u,l),u++}}this.$inChange=!1},this.$findCellWidthsForBlock=function(e){var t=[],n,r=e;while(r>=0){n=this.$cellWidthsForRow(r);if(n.length==0)break;t.unshift(n),r--}var i=r+1;r=e;var s=this.$editor.session.getLength();while(r<s-1){r++,n=this.$cellWidthsForRow(r);if(n.length==0)break;t.push(n)}return{cellWidths:t,firstRow:i}},this.$cellWidthsForRow=function(e){var t=this.$selectionColumnsForRow(e),n=[-1].concat(this.$tabsForRow(e)),r=n.map(function(e){return 0}).slice(1),i=this.$editor.session.getLine(e);for(var s=0,o=n.length-1;s<o;s++){var u=n[s]+1,a=n[s+1],f=this.$rightmostSelectionInCell(t,a),l=i.substring(u,a);r[s]=Math.max(l.replace(/\\s+$/g,\"\").length,f-u)}return r},this.$selectionColumnsForRow=function(e){var t=[],n=this.$editor.getCursorPosition();return this.$editor.session.getSelection().isEmpty()&&e==n.row&&t.push(n.column),t},this.$setBlockCellWidthsToMax=function(e){var t=!0,n,r,i,s=this.$izip_longest(e);for(var o=0,u=s.length;o<u;o++){var a=s[o];if(!a.push){console.error(a);continue}a.push(NaN);for(var f=0,l=a.length;f<l;f++){var c=a[f];t&&(n=f,i=0,t=!1);if(isNaN(c)){r=f;for(var h=n;h<r;h++)e[h][o]=i;t=!0}i=Math.max(i,c)}}return e},this.$rightmostSelectionInCell=function(e,t){var n=0;if(e.length){var r=[];for(var i=0,s=e.length;i<s;i++)e[i]<=t?r.push(i):r.push(0);n=Math.max.apply(Math,r)}return n},this.$tabsForRow=function(e){var t=[],n=this.$editor.session.getLine(e),r=/\\t/g,i;while((i=r.exec(n))!=null)t.push(i.index);return t},this.$adjustRow=function(e,t){var n=this.$tabsForRow(e);if(n.length==0)return;var r=0,i=-1,s=this.$izip(t,n);for(var o=0,u=s.length;o<u;o++){var a=s[o][0],f=s[o][1];i+=1+a,f+=r;var l=i-f;if(l==0)continue;var c=this.$editor.session.getLine(e).substr(0,f),h=c.replace(/\\s*$/g,\"\"),p=c.length-h.length;l>0&&(this.$editor.session.getDocument().insertInLine({row:e,column:f+1},Array(l+1).join(\" \")+\"\t\"),this.$editor.session.getDocument().removeInLine(e,f,f+1),r+=l),l<0&&p>=-l&&(this.$editor.session.getDocument().removeInLine(e,f+l,f),r+=l)}},this.$izip_longest=function(e){if(!e[0])return[];var t=e[0].length,n=e.length;for(var r=1;r<n;r++){var i=e[r].length;i>t&&(t=i)}var s=[];for(var o=0;o<t;o++){var u=[];for(var r=0;r<n;r++)e[r][o]===\"\"?u.push(NaN):u.push(e[r][o]);s.push(u)}return s},this.$izip=function(e,t){var n=e.length>=t.length?t.length:e.length,r=[];for(var i=0;i<n;i++){var s=[e[i],t[i]];r.push(s)}return r}}).call(r.prototype),t.ElasticTabstopsLite=r;var i=e(\"../editor\").Editor;e(\"../config\").defineOptions(i.prototype,\"editor\",{useElasticTabstops:{set:function(e){e?(this.elasticTabstops||(this.elasticTabstops=new r(this)),this.commands.on(\"afterExec\",this.elasticTabstops.onAfterExec),this.commands.on(\"exec\",this.elasticTabstops.onExec),this.on(\"change\",this.elasticTabstops.onChange)):this.elasticTabstops&&(this.commands.removeListener(\"afterExec\",this.elasticTabstops.onAfterExec),this.commands.removeListener(\"exec\",this.elasticTabstops.onExec),this.removeListener(\"change\",this.elasticTabstops.onChange))}}})});\n                (function() {\n                    window.require([\"ace/ext/elastic_tabstops_lite\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-error_marker.js",
    "content": ";\n                (function() {\n                    window.require([\"ace/ext/error_marker\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-linking.js",
    "content": "define(\"ace/ext/linking\",[\"require\",\"exports\",\"module\",\"ace/editor\",\"ace/config\"],function(e,t,n){function i(e){var t=e.editor,n=e.getAccelKey();if(n){var t=e.editor,r=e.getDocumentPosition(),i=t.session,s=i.getTokenAt(r.row,r.column);t._emit(\"linkHover\",{position:r,token:s})}}function s(e){var t=e.getAccelKey(),n=e.getButton();if(n==0&&t){var r=e.editor,i=e.getDocumentPosition(),s=r.session,o=s.getTokenAt(i.row,i.column);r._emit(\"linkClick\",{position:i,token:o})}}var r=e(\"ace/editor\").Editor;e(\"../config\").defineOptions(r.prototype,\"editor\",{enableLinking:{set:function(e){e?(this.on(\"click\",s),this.on(\"mousemove\",i)):(this.off(\"click\",s),this.off(\"mousemove\",i))},value:!1}})});\n                (function() {\n                    window.require([\"ace/ext/linking\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-modelist.js",
    "content": "define(\"ace/ext/modelist\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function i(e){var t=a.text,n=e.split(/[\\/\\\\]/).pop();for(var i=0;i<r.length;i++)if(r[i].supportsFile(n)){t=r[i];break}return t}var r=[],s=function(e,t,n){this.name=e,this.caption=t,this.mode=\"ace/mode/\"+e,this.extensions=n;var r;/\\^/.test(n)?r=n.replace(/\\|(\\^)?/g,function(e,t){return\"$|\"+(t?\"^\":\"^.*\\\\.\")})+\"$\":r=\"^.*\\\\.(\"+n+\")$\",this.extRe=new RegExp(r,\"gi\")};s.prototype.supportsFile=function(e){return e.match(this.extRe)};var o={ABAP:[\"abap\"],ABC:[\"abc\"],ActionScript:[\"as\"],ADA:[\"ada|adb\"],Apache_Conf:[\"^htaccess|^htgroups|^htpasswd|^conf|htaccess|htgroups|htpasswd\"],AsciiDoc:[\"asciidoc|adoc\"],Assembly_x86:[\"asm|a\"],AutoHotKey:[\"ahk\"],BatchFile:[\"bat|cmd\"],Bro:[\"bro\"],C_Cpp:[\"cpp|c|cc|cxx|h|hh|hpp|ino\"],C9Search:[\"c9search_results\"],Cirru:[\"cirru|cr\"],Clojure:[\"clj|cljs\"],Cobol:[\"CBL|COB\"],coffee:[\"coffee|cf|cson|^Cakefile\"],ColdFusion:[\"cfm\"],CSharp:[\"cs\"],CSS:[\"css\"],Curly:[\"curly\"],D:[\"d|di\"],Dart:[\"dart\"],Diff:[\"diff|patch\"],Dockerfile:[\"^Dockerfile\"],Dot:[\"dot\"],Drools:[\"drl\"],Dummy:[\"dummy\"],DummySyntax:[\"dummy\"],Eiffel:[\"e|ge\"],EJS:[\"ejs\"],Elixir:[\"ex|exs\"],Elm:[\"elm\"],Erlang:[\"erl|hrl\"],Forth:[\"frt|fs|ldr|fth|4th\"],Fortran:[\"f|f90\"],FTL:[\"ftl\"],Gcode:[\"gcode\"],Gherkin:[\"feature\"],Gitignore:[\"^.gitignore\"],Glsl:[\"glsl|frag|vert\"],Gobstones:[\"gbs\"],golang:[\"go\"],Groovy:[\"groovy\"],HAML:[\"haml\"],Handlebars:[\"hbs|handlebars|tpl|mustache\"],Haskell:[\"hs\"],Haskell_Cabal:[\"cabal\"],haXe:[\"hx\"],Hjson:[\"hjson\"],HTML:[\"html|htm|xhtml\"],HTML_Elixir:[\"eex|html.eex\"],HTML_Ruby:[\"erb|rhtml|html.erb\"],INI:[\"ini|conf|cfg|prefs\"],Io:[\"io\"],Jack:[\"jack\"],Jade:[\"jade|pug\"],Java:[\"java\"],JavaScript:[\"js|jsm|jsx\"],JSON:[\"json\"],JSONiq:[\"jq\"],JSP:[\"jsp\"],JSX:[\"jsx\"],Julia:[\"jl\"],Kotlin:[\"kt|kts\"],LaTeX:[\"tex|latex|ltx|bib\"],LESS:[\"less\"],Liquid:[\"liquid\"],Lisp:[\"lisp\"],LiveScript:[\"ls\"],LogiQL:[\"logic|lql\"],LSL:[\"lsl\"],Lua:[\"lua\"],LuaPage:[\"lp\"],Lucene:[\"lucene\"],Makefile:[\"^Makefile|^GNUmakefile|^makefile|^OCamlMakefile|make\"],Markdown:[\"md|markdown\"],Mask:[\"mask\"],MATLAB:[\"matlab\"],Maze:[\"mz\"],MEL:[\"mel\"],MUSHCode:[\"mc|mush\"],MySQL:[\"mysql\"],Nix:[\"nix\"],NSIS:[\"nsi|nsh\"],ObjectiveC:[\"m|mm\"],OCaml:[\"ml|mli\"],Pascal:[\"pas|p\"],Perl:[\"pl|pm\"],pgSQL:[\"pgsql\"],PHP:[\"php|phtml|shtml|php3|php4|php5|phps|phpt|aw|ctp|module\"],Powershell:[\"ps1\"],Praat:[\"praat|praatscript|psc|proc\"],Prolog:[\"plg|prolog\"],Properties:[\"properties\"],Protobuf:[\"proto\"],Python:[\"py\"],R:[\"r\"],Razor:[\"cshtml|asp\"],RDoc:[\"Rd\"],RHTML:[\"Rhtml\"],RST:[\"rst\"],Ruby:[\"rb|ru|gemspec|rake|^Guardfile|^Rakefile|^Gemfile\"],Rust:[\"rs\"],SASS:[\"sass\"],SCAD:[\"scad\"],Scala:[\"scala\"],Scheme:[\"scm|sm|rkt|oak|scheme\"],SCSS:[\"scss\"],SH:[\"sh|bash|^.bashrc\"],SJS:[\"sjs\"],Smarty:[\"smarty|tpl\"],snippets:[\"snippets\"],Soy_Template:[\"soy\"],Space:[\"space\"],SQL:[\"sql\"],SQLServer:[\"sqlserver\"],Stylus:[\"styl|stylus\"],SVG:[\"svg\"],Swift:[\"swift\"],Tcl:[\"tcl\"],Tex:[\"tex\"],Text:[\"txt\"],Textile:[\"textile\"],Toml:[\"toml\"],TSX:[\"tsx\"],Twig:[\"twig|swig\"],Typescript:[\"ts|typescript|str\"],Vala:[\"vala\"],VBScript:[\"vbs|vb\"],Velocity:[\"vm\"],Verilog:[\"v|vh|sv|svh\"],VHDL:[\"vhd|vhdl\"],Wollok:[\"wlk|wpgm|wtest\"],XML:[\"xml|rdf|rss|wsdl|xslt|atom|mathml|mml|xul|xbl|xaml\"],XQuery:[\"xq\"],YAML:[\"yaml|yml\"],Django:[\"html\"]},u={ObjectiveC:\"Objective-C\",CSharp:\"C#\",golang:\"Go\",C_Cpp:\"C and C++\",coffee:\"CoffeeScript\",HTML_Ruby:\"HTML (Ruby)\",HTML_Elixir:\"HTML (Elixir)\",FTL:\"FreeMarker\"},a={};for(var f in o){var l=o[f],c=(u[f]||f).replace(/_/g,\" \"),h=f.toLowerCase(),p=new s(h,c,l[0]);a[h]=p,r.push(p)}n.exports={getModeForPath:i,modes:r,modesByName:a}});\n                (function() {\n                    window.require([\"ace/ext/modelist\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-old_ie.js",
    "content": "define(\"ace/ext/searchbox\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\",\"ace/lib/lang\",\"ace/lib/event\",\"ace/keyboard/hash_handler\",\"ace/lib/keys\"],function(e,t,n){\"use strict\";var r=e(\"../lib/dom\"),i=e(\"../lib/lang\"),s=e(\"../lib/event\"),o=\".ace_search {background-color: #ddd;border: 1px solid #cbcbcb;border-top: 0 none;max-width: 325px;overflow: hidden;margin: 0;padding: 4px;padding-right: 6px;padding-bottom: 0;position: absolute;top: 0px;z-index: 99;white-space: normal;}.ace_search.left {border-left: 0 none;border-radius: 0px 0px 5px 0px;left: 0;}.ace_search.right {border-radius: 0px 0px 0px 5px;border-right: 0 none;right: 0;}.ace_search_form, .ace_replace_form {border-radius: 3px;border: 1px solid #cbcbcb;float: left;margin-bottom: 4px;overflow: hidden;}.ace_search_form.ace_nomatch {outline: 1px solid red;}.ace_search_field {background-color: white;color: black;border-right: 1px solid #cbcbcb;border: 0 none;-webkit-box-sizing: border-box;-moz-box-sizing: border-box;box-sizing: border-box;float: left;height: 22px;outline: 0;padding: 0 7px;width: 214px;margin: 0;}.ace_searchbtn,.ace_replacebtn {background: #fff;border: 0 none;border-left: 1px solid #dcdcdc;cursor: pointer;float: left;height: 22px;margin: 0;position: relative;}.ace_searchbtn:last-child,.ace_replacebtn:last-child {border-top-right-radius: 3px;border-bottom-right-radius: 3px;}.ace_searchbtn:disabled {background: none;cursor: default;}.ace_searchbtn {background-position: 50% 50%;background-repeat: no-repeat;width: 27px;}.ace_searchbtn.prev {background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAgAAAAFCAYAAAB4ka1VAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAADFJREFUeNpiSU1NZUAC/6E0I0yACYskCpsJiySKIiY0SUZk40FyTEgCjGgKwTRAgAEAQJUIPCE+qfkAAAAASUVORK5CYII=);    }.ace_searchbtn.next {background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAgAAAAFCAYAAAB4ka1VAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAADRJREFUeNpiTE1NZQCC/0DMyIAKwGJMUAYDEo3M/s+EpvM/mkKwCQxYjIeLMaELoLMBAgwAU7UJObTKsvAAAAAASUVORK5CYII=);    }.ace_searchbtn_close {background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAA4AAAAcCAYAAABRVo5BAAAAZ0lEQVR42u2SUQrAMAhDvazn8OjZBilCkYVVxiis8H4CT0VrAJb4WHT3C5xU2a2IQZXJjiQIRMdkEoJ5Q2yMqpfDIo+XY4k6h+YXOyKqTIj5REaxloNAd0xiKmAtsTHqW8sR2W5f7gCu5nWFUpVjZwAAAABJRU5ErkJggg==) no-repeat 50% 0;border-radius: 50%;border: 0 none;color: #656565;cursor: pointer;float: right;font: 16px/16px Arial;height: 14px;margin: 5px 1px 9px 5px;padding: 0;text-align: center;width: 14px;}.ace_searchbtn_close:hover {background-color: #656565;background-position: 50% 100%;color: white;}.ace_replacebtn.prev {width: 54px}.ace_replacebtn.next {width: 27px}.ace_button {margin-left: 2px;cursor: pointer;-webkit-user-select: none;-moz-user-select: none;-o-user-select: none;-ms-user-select: none;user-select: none;overflow: hidden;opacity: 0.7;border: 1px solid rgba(100,100,100,0.23);padding: 1px;-moz-box-sizing: border-box;box-sizing:    border-box;color: black;}.ace_button:hover {background-color: #eee;opacity:1;}.ace_button:active {background-color: #ddd;}.ace_button.checked {border-color: #3399ff;opacity:1;}.ace_search_options{margin-bottom: 3px;text-align: right;-webkit-user-select: none;-moz-user-select: none;-o-user-select: none;-ms-user-select: none;user-select: none;}\",u=e(\"../keyboard/hash_handler\").HashHandler,a=e(\"../lib/keys\");r.importCssString(o,\"ace_searchbox\");var f='<div class=\"ace_search right\">    <button type=\"button\" action=\"hide\" class=\"ace_searchbtn_close\"></button>    <div class=\"ace_search_form\">        <input class=\"ace_search_field\" placeholder=\"Search for\" spellcheck=\"false\"></input>        <button type=\"button\" action=\"findNext\" class=\"ace_searchbtn next\"></button>        <button type=\"button\" action=\"findPrev\" class=\"ace_searchbtn prev\"></button>        <button type=\"button\" action=\"findAll\" class=\"ace_searchbtn\" title=\"Alt-Enter\">All</button>    </div>    <div class=\"ace_replace_form\">        <input class=\"ace_search_field\" placeholder=\"Replace with\" spellcheck=\"false\"></input>        <button type=\"button\" action=\"replaceAndFindNext\" class=\"ace_replacebtn\">Replace</button>        <button type=\"button\" action=\"replaceAll\" class=\"ace_replacebtn\">All</button>    </div>    <div class=\"ace_search_options\">        <span action=\"toggleRegexpMode\" class=\"ace_button\" title=\"RegExp Search\">.*</span>        <span action=\"toggleCaseSensitive\" class=\"ace_button\" title=\"CaseSensitive Search\">Aa</span>        <span action=\"toggleWholeWords\" class=\"ace_button\" title=\"Whole Word Search\">\\\\b</span>    </div></div>'.replace(/>\\s+/g,\">\"),l=function(e,t,n){var i=r.createElement(\"div\");i.innerHTML=f,this.element=i.firstChild,this.$init(),this.setEditor(e)};(function(){this.setEditor=function(e){e.searchBox=this,e.container.appendChild(this.element),this.editor=e},this.$initElements=function(e){this.searchBox=e.querySelector(\".ace_search_form\"),this.replaceBox=e.querySelector(\".ace_replace_form\"),this.searchOptions=e.querySelector(\".ace_search_options\"),this.regExpOption=e.querySelector(\"[action=toggleRegexpMode]\"),this.caseSensitiveOption=e.querySelector(\"[action=toggleCaseSensitive]\"),this.wholeWordOption=e.querySelector(\"[action=toggleWholeWords]\"),this.searchInput=this.searchBox.querySelector(\".ace_search_field\"),this.replaceInput=this.replaceBox.querySelector(\".ace_search_field\")},this.$init=function(){var e=this.element;this.$initElements(e);var t=this;s.addListener(e,\"mousedown\",function(e){setTimeout(function(){t.activeInput.focus()},0),s.stopPropagation(e)}),s.addListener(e,\"click\",function(e){var n=e.target||e.srcElement,r=n.getAttribute(\"action\");r&&t[r]?t[r]():t.$searchBarKb.commands[r]&&t.$searchBarKb.commands[r].exec(t),s.stopPropagation(e)}),s.addCommandKeyListener(e,function(e,n,r){var i=a.keyCodeToString(r),o=t.$searchBarKb.findKeyCommand(n,i);o&&o.exec&&(o.exec(t),s.stopEvent(e))}),this.$onChange=i.delayedCall(function(){t.find(!1,!1)}),s.addListener(this.searchInput,\"input\",function(){t.$onChange.schedule(20)}),s.addListener(this.searchInput,\"focus\",function(){t.activeInput=t.searchInput,t.searchInput.value&&t.highlight()}),s.addListener(this.replaceInput,\"focus\",function(){t.activeInput=t.replaceInput,t.searchInput.value&&t.highlight()})},this.$closeSearchBarKb=new u([{bindKey:\"Esc\",name:\"closeSearchBar\",exec:function(e){e.searchBox.hide()}}]),this.$searchBarKb=new u,this.$searchBarKb.bindKeys({\"Ctrl-f|Command-f\":function(e){var t=e.isReplace=!e.isReplace;e.replaceBox.style.display=t?\"\":\"none\",e.searchInput.focus()},\"Ctrl-H|Command-Option-F\":function(e){e.replaceBox.style.display=\"\",e.replaceInput.focus()},\"Ctrl-G|Command-G\":function(e){e.findNext()},\"Ctrl-Shift-G|Command-Shift-G\":function(e){e.findPrev()},esc:function(e){setTimeout(function(){e.hide()})},Return:function(e){e.activeInput==e.replaceInput&&e.replace(),e.findNext()},\"Shift-Return\":function(e){e.activeInput==e.replaceInput&&e.replace(),e.findPrev()},\"Alt-Return\":function(e){e.activeInput==e.replaceInput&&e.replaceAll(),e.findAll()},Tab:function(e){(e.activeInput==e.replaceInput?e.searchInput:e.replaceInput).focus()}}),this.$searchBarKb.addCommands([{name:\"toggleRegexpMode\",bindKey:{win:\"Alt-R|Alt-/\",mac:\"Ctrl-Alt-R|Ctrl-Alt-/\"},exec:function(e){e.regExpOption.checked=!e.regExpOption.checked,e.$syncOptions()}},{name:\"toggleCaseSensitive\",bindKey:{win:\"Alt-C|Alt-I\",mac:\"Ctrl-Alt-R|Ctrl-Alt-I\"},exec:function(e){e.caseSensitiveOption.checked=!e.caseSensitiveOption.checked,e.$syncOptions()}},{name:\"toggleWholeWords\",bindKey:{win:\"Alt-B|Alt-W\",mac:\"Ctrl-Alt-B|Ctrl-Alt-W\"},exec:function(e){e.wholeWordOption.checked=!e.wholeWordOption.checked,e.$syncOptions()}}]),this.$syncOptions=function(){r.setCssClass(this.regExpOption,\"checked\",this.regExpOption.checked),r.setCssClass(this.wholeWordOption,\"checked\",this.wholeWordOption.checked),r.setCssClass(this.caseSensitiveOption,\"checked\",this.caseSensitiveOption.checked),this.find(!1,!1)},this.highlight=function(e){this.editor.session.highlight(e||this.editor.$search.$options.re),this.editor.renderer.updateBackMarkers()},this.find=function(e,t,n){var i=this.editor.find(this.searchInput.value,{skipCurrent:e,backwards:t,wrap:!0,regExp:this.regExpOption.checked,caseSensitive:this.caseSensitiveOption.checked,wholeWord:this.wholeWordOption.checked,preventScroll:n}),s=!i&&this.searchInput.value;r.setCssClass(this.searchBox,\"ace_nomatch\",s),this.editor._emit(\"findSearchBox\",{match:!s}),this.highlight()},this.findNext=function(){this.find(!0,!1)},this.findPrev=function(){this.find(!0,!0)},this.findAll=function(){var e=this.editor.findAll(this.searchInput.value,{regExp:this.regExpOption.checked,caseSensitive:this.caseSensitiveOption.checked,wholeWord:this.wholeWordOption.checked}),t=!e&&this.searchInput.value;r.setCssClass(this.searchBox,\"ace_nomatch\",t),this.editor._emit(\"findSearchBox\",{match:!t}),this.highlight(),this.hide()},this.replace=function(){this.editor.getReadOnly()||this.editor.replace(this.replaceInput.value)},this.replaceAndFindNext=function(){this.editor.getReadOnly()||(this.editor.replace(this.replaceInput.value),this.findNext())},this.replaceAll=function(){this.editor.getReadOnly()||this.editor.replaceAll(this.replaceInput.value)},this.hide=function(){this.element.style.display=\"none\",this.editor.keyBinding.removeKeyboardHandler(this.$closeSearchBarKb),this.editor.focus()},this.show=function(e,t){this.element.style.display=\"\",this.replaceBox.style.display=t?\"\":\"none\",this.isReplace=t,e&&(this.searchInput.value=e),this.find(!1,!1,!0),this.searchInput.focus(),this.searchInput.select(),this.editor.keyBinding.addKeyboardHandler(this.$closeSearchBarKb)},this.isFocused=function(){var e=document.activeElement;return e==this.searchInput||e==this.replaceInput}}).call(l.prototype),t.SearchBox=l,t.Search=function(e,t){var n=e.searchBox||new l(e);n.show(e.session.getTextRange(),t)}}),define(\"ace/ext/old_ie\",[\"require\",\"exports\",\"module\",\"ace/lib/useragent\",\"ace/tokenizer\",\"ace/ext/searchbox\",\"ace/mode/text\"],function(require,exports,module){\"use strict\";function patch(obj,name,regexp,replacement){eval(\"obj['\"+name+\"']=\"+obj[name].toString().replace(regexp,replacement))}var MAX_TOKEN_COUNT=1e3,useragent=require(\"../lib/useragent\"),TokenizerModule=require(\"../tokenizer\");useragent.isIE&&useragent.isIE<10&&window.top.document.compatMode===\"BackCompat\"&&(useragent.isOldIE=!0);if(typeof document!=\"undefined\"&&!document.documentElement.querySelector){useragent.isOldIE=!0;var qs=function(e,t){if(t.charAt(0)==\".\")var n=t.slice(1);else var r=t.match(/(\\w+)=(\\w+)/),i=r&&r[1],s=r&&r[2];for(var o=0;o<e.all.length;o++){var u=e.all[o];if(n){if(u.className.indexOf(n)!=-1)return u}else if(i&&u.getAttribute(i)==s)return u}},sb=require(\"./searchbox\").SearchBox.prototype;patch(sb,\"$initElements\",/([^\\s=]*).querySelector\\((\".*?\")\\)/g,\"qs($1, $2)\")}var compliantExecNpcg=/()??/.exec(\"\")[1]===undefined;if(compliantExecNpcg)return;var proto=TokenizerModule.Tokenizer.prototype;TokenizerModule.Tokenizer_orig=TokenizerModule.Tokenizer,proto.getLineTokens_orig=proto.getLineTokens,patch(TokenizerModule,\"Tokenizer\",\"ruleRegExps.push(adjustedregex);\\n\",function(e){return e+'        if (state[i].next && RegExp(adjustedregex).test(\"\"))\\n            rule._qre = RegExp(adjustedregex, \"g\");\\n        '}),TokenizerModule.Tokenizer.prototype=proto,patch(proto,\"getLineTokens\",/if \\(match\\[i \\+ 1\\] === undefined\\)\\s*continue;/,\"if (!match[i + 1]) {\\n        if (value)continue;\\n        var qre = state[mapping[i]]._qre;\\n        if (!qre) continue;\\n        qre.lastIndex = lastIndex;\\n        if (!qre.exec(line) || qre.lastIndex != lastIndex)\\n            continue;\\n    }\"),patch(require(\"../mode/text\").Mode.prototype,\"getTokenizer\",/Tokenizer/,\"TokenizerModule.Tokenizer\"),useragent.isOldIE=!0});\n                (function() {\n                    window.require([\"ace/ext/old_ie\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-searchbox.js",
    "content": "define(\"ace/ext/searchbox\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\",\"ace/lib/lang\",\"ace/lib/event\",\"ace/keyboard/hash_handler\",\"ace/lib/keys\"],function(e,t,n){\"use strict\";var r=e(\"../lib/dom\"),i=e(\"../lib/lang\"),s=e(\"../lib/event\"),o=\".ace_search {background-color: #ddd;border: 1px solid #cbcbcb;border-top: 0 none;max-width: 325px;overflow: hidden;margin: 0;padding: 4px;padding-right: 6px;padding-bottom: 0;position: absolute;top: 0px;z-index: 99;white-space: normal;}.ace_search.left {border-left: 0 none;border-radius: 0px 0px 5px 0px;left: 0;}.ace_search.right {border-radius: 0px 0px 0px 5px;border-right: 0 none;right: 0;}.ace_search_form, .ace_replace_form {border-radius: 3px;border: 1px solid #cbcbcb;float: left;margin-bottom: 4px;overflow: hidden;}.ace_search_form.ace_nomatch {outline: 1px solid red;}.ace_search_field {background-color: white;color: black;border-right: 1px solid #cbcbcb;border: 0 none;-webkit-box-sizing: border-box;-moz-box-sizing: border-box;box-sizing: border-box;float: left;height: 22px;outline: 0;padding: 0 7px;width: 214px;margin: 0;}.ace_searchbtn,.ace_replacebtn {background: #fff;border: 0 none;border-left: 1px solid #dcdcdc;cursor: pointer;float: left;height: 22px;margin: 0;position: relative;}.ace_searchbtn:last-child,.ace_replacebtn:last-child {border-top-right-radius: 3px;border-bottom-right-radius: 3px;}.ace_searchbtn:disabled {background: none;cursor: default;}.ace_searchbtn {background-position: 50% 50%;background-repeat: no-repeat;width: 27px;}.ace_searchbtn.prev {background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAgAAAAFCAYAAAB4ka1VAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAADFJREFUeNpiSU1NZUAC/6E0I0yACYskCpsJiySKIiY0SUZk40FyTEgCjGgKwTRAgAEAQJUIPCE+qfkAAAAASUVORK5CYII=);    }.ace_searchbtn.next {background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAgAAAAFCAYAAAB4ka1VAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAADRJREFUeNpiTE1NZQCC/0DMyIAKwGJMUAYDEo3M/s+EpvM/mkKwCQxYjIeLMaELoLMBAgwAU7UJObTKsvAAAAAASUVORK5CYII=);    }.ace_searchbtn_close {background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAA4AAAAcCAYAAABRVo5BAAAAZ0lEQVR42u2SUQrAMAhDvazn8OjZBilCkYVVxiis8H4CT0VrAJb4WHT3C5xU2a2IQZXJjiQIRMdkEoJ5Q2yMqpfDIo+XY4k6h+YXOyKqTIj5REaxloNAd0xiKmAtsTHqW8sR2W5f7gCu5nWFUpVjZwAAAABJRU5ErkJggg==) no-repeat 50% 0;border-radius: 50%;border: 0 none;color: #656565;cursor: pointer;float: right;font: 16px/16px Arial;height: 14px;margin: 5px 1px 9px 5px;padding: 0;text-align: center;width: 14px;}.ace_searchbtn_close:hover {background-color: #656565;background-position: 50% 100%;color: white;}.ace_replacebtn.prev {width: 54px}.ace_replacebtn.next {width: 27px}.ace_button {margin-left: 2px;cursor: pointer;-webkit-user-select: none;-moz-user-select: none;-o-user-select: none;-ms-user-select: none;user-select: none;overflow: hidden;opacity: 0.7;border: 1px solid rgba(100,100,100,0.23);padding: 1px;-moz-box-sizing: border-box;box-sizing:    border-box;color: black;}.ace_button:hover {background-color: #eee;opacity:1;}.ace_button:active {background-color: #ddd;}.ace_button.checked {border-color: #3399ff;opacity:1;}.ace_search_options{margin-bottom: 3px;text-align: right;-webkit-user-select: none;-moz-user-select: none;-o-user-select: none;-ms-user-select: none;user-select: none;}\",u=e(\"../keyboard/hash_handler\").HashHandler,a=e(\"../lib/keys\");r.importCssString(o,\"ace_searchbox\");var f='<div class=\"ace_search right\">    <button type=\"button\" action=\"hide\" class=\"ace_searchbtn_close\"></button>    <div class=\"ace_search_form\">        <input class=\"ace_search_field\" placeholder=\"Search for\" spellcheck=\"false\"></input>        <button type=\"button\" action=\"findNext\" class=\"ace_searchbtn next\"></button>        <button type=\"button\" action=\"findPrev\" class=\"ace_searchbtn prev\"></button>        <button type=\"button\" action=\"findAll\" class=\"ace_searchbtn\" title=\"Alt-Enter\">All</button>    </div>    <div class=\"ace_replace_form\">        <input class=\"ace_search_field\" placeholder=\"Replace with\" spellcheck=\"false\"></input>        <button type=\"button\" action=\"replaceAndFindNext\" class=\"ace_replacebtn\">Replace</button>        <button type=\"button\" action=\"replaceAll\" class=\"ace_replacebtn\">All</button>    </div>    <div class=\"ace_search_options\">        <span action=\"toggleRegexpMode\" class=\"ace_button\" title=\"RegExp Search\">.*</span>        <span action=\"toggleCaseSensitive\" class=\"ace_button\" title=\"CaseSensitive Search\">Aa</span>        <span action=\"toggleWholeWords\" class=\"ace_button\" title=\"Whole Word Search\">\\\\b</span>    </div></div>'.replace(/>\\s+/g,\">\"),l=function(e,t,n){var i=r.createElement(\"div\");i.innerHTML=f,this.element=i.firstChild,this.$init(),this.setEditor(e)};(function(){this.setEditor=function(e){e.searchBox=this,e.container.appendChild(this.element),this.editor=e},this.$initElements=function(e){this.searchBox=e.querySelector(\".ace_search_form\"),this.replaceBox=e.querySelector(\".ace_replace_form\"),this.searchOptions=e.querySelector(\".ace_search_options\"),this.regExpOption=e.querySelector(\"[action=toggleRegexpMode]\"),this.caseSensitiveOption=e.querySelector(\"[action=toggleCaseSensitive]\"),this.wholeWordOption=e.querySelector(\"[action=toggleWholeWords]\"),this.searchInput=this.searchBox.querySelector(\".ace_search_field\"),this.replaceInput=this.replaceBox.querySelector(\".ace_search_field\")},this.$init=function(){var e=this.element;this.$initElements(e);var t=this;s.addListener(e,\"mousedown\",function(e){setTimeout(function(){t.activeInput.focus()},0),s.stopPropagation(e)}),s.addListener(e,\"click\",function(e){var n=e.target||e.srcElement,r=n.getAttribute(\"action\");r&&t[r]?t[r]():t.$searchBarKb.commands[r]&&t.$searchBarKb.commands[r].exec(t),s.stopPropagation(e)}),s.addCommandKeyListener(e,function(e,n,r){var i=a.keyCodeToString(r),o=t.$searchBarKb.findKeyCommand(n,i);o&&o.exec&&(o.exec(t),s.stopEvent(e))}),this.$onChange=i.delayedCall(function(){t.find(!1,!1)}),s.addListener(this.searchInput,\"input\",function(){t.$onChange.schedule(20)}),s.addListener(this.searchInput,\"focus\",function(){t.activeInput=t.searchInput,t.searchInput.value&&t.highlight()}),s.addListener(this.replaceInput,\"focus\",function(){t.activeInput=t.replaceInput,t.searchInput.value&&t.highlight()})},this.$closeSearchBarKb=new u([{bindKey:\"Esc\",name:\"closeSearchBar\",exec:function(e){e.searchBox.hide()}}]),this.$searchBarKb=new u,this.$searchBarKb.bindKeys({\"Ctrl-f|Command-f\":function(e){var t=e.isReplace=!e.isReplace;e.replaceBox.style.display=t?\"\":\"none\",e.searchInput.focus()},\"Ctrl-H|Command-Option-F\":function(e){e.replaceBox.style.display=\"\",e.replaceInput.focus()},\"Ctrl-G|Command-G\":function(e){e.findNext()},\"Ctrl-Shift-G|Command-Shift-G\":function(e){e.findPrev()},esc:function(e){setTimeout(function(){e.hide()})},Return:function(e){e.activeInput==e.replaceInput&&e.replace(),e.findNext()},\"Shift-Return\":function(e){e.activeInput==e.replaceInput&&e.replace(),e.findPrev()},\"Alt-Return\":function(e){e.activeInput==e.replaceInput&&e.replaceAll(),e.findAll()},Tab:function(e){(e.activeInput==e.replaceInput?e.searchInput:e.replaceInput).focus()}}),this.$searchBarKb.addCommands([{name:\"toggleRegexpMode\",bindKey:{win:\"Alt-R|Alt-/\",mac:\"Ctrl-Alt-R|Ctrl-Alt-/\"},exec:function(e){e.regExpOption.checked=!e.regExpOption.checked,e.$syncOptions()}},{name:\"toggleCaseSensitive\",bindKey:{win:\"Alt-C|Alt-I\",mac:\"Ctrl-Alt-R|Ctrl-Alt-I\"},exec:function(e){e.caseSensitiveOption.checked=!e.caseSensitiveOption.checked,e.$syncOptions()}},{name:\"toggleWholeWords\",bindKey:{win:\"Alt-B|Alt-W\",mac:\"Ctrl-Alt-B|Ctrl-Alt-W\"},exec:function(e){e.wholeWordOption.checked=!e.wholeWordOption.checked,e.$syncOptions()}}]),this.$syncOptions=function(){r.setCssClass(this.regExpOption,\"checked\",this.regExpOption.checked),r.setCssClass(this.wholeWordOption,\"checked\",this.wholeWordOption.checked),r.setCssClass(this.caseSensitiveOption,\"checked\",this.caseSensitiveOption.checked),this.find(!1,!1)},this.highlight=function(e){this.editor.session.highlight(e||this.editor.$search.$options.re),this.editor.renderer.updateBackMarkers()},this.find=function(e,t,n){var i=this.editor.find(this.searchInput.value,{skipCurrent:e,backwards:t,wrap:!0,regExp:this.regExpOption.checked,caseSensitive:this.caseSensitiveOption.checked,wholeWord:this.wholeWordOption.checked,preventScroll:n}),s=!i&&this.searchInput.value;r.setCssClass(this.searchBox,\"ace_nomatch\",s),this.editor._emit(\"findSearchBox\",{match:!s}),this.highlight()},this.findNext=function(){this.find(!0,!1)},this.findPrev=function(){this.find(!0,!0)},this.findAll=function(){var e=this.editor.findAll(this.searchInput.value,{regExp:this.regExpOption.checked,caseSensitive:this.caseSensitiveOption.checked,wholeWord:this.wholeWordOption.checked}),t=!e&&this.searchInput.value;r.setCssClass(this.searchBox,\"ace_nomatch\",t),this.editor._emit(\"findSearchBox\",{match:!t}),this.highlight(),this.hide()},this.replace=function(){this.editor.getReadOnly()||this.editor.replace(this.replaceInput.value)},this.replaceAndFindNext=function(){this.editor.getReadOnly()||(this.editor.replace(this.replaceInput.value),this.findNext())},this.replaceAll=function(){this.editor.getReadOnly()||this.editor.replaceAll(this.replaceInput.value)},this.hide=function(){this.element.style.display=\"none\",this.editor.keyBinding.removeKeyboardHandler(this.$closeSearchBarKb),this.editor.focus()},this.show=function(e,t){this.element.style.display=\"\",this.replaceBox.style.display=t?\"\":\"none\",this.isReplace=t,e&&(this.searchInput.value=e),this.find(!1,!1,!0),this.searchInput.focus(),this.searchInput.select(),this.editor.keyBinding.addKeyboardHandler(this.$closeSearchBarKb)},this.isFocused=function(){var e=document.activeElement;return e==this.searchInput||e==this.replaceInput}}).call(l.prototype),t.SearchBox=l,t.Search=function(e,t){var n=e.searchBox||new l(e);n.show(e.session.getTextRange(),t)}});\n                (function() {\n                    window.require([\"ace/ext/searchbox\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-settings_menu.js",
    "content": "define(\"ace/ext/menu_tools/element_generator\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";n.exports.createOption=function(t){var n,r=document.createElement(\"option\");for(n in t)t.hasOwnProperty(n)&&(n===\"selected\"?r.setAttribute(n,t[n]):r[n]=t[n]);return r},n.exports.createCheckbox=function(t,n,r){var i=document.createElement(\"input\");return i.setAttribute(\"type\",\"checkbox\"),i.setAttribute(\"id\",t),i.setAttribute(\"name\",t),i.setAttribute(\"value\",n),i.setAttribute(\"class\",r),n&&i.setAttribute(\"checked\",\"checked\"),i},n.exports.createInput=function(t,n,r){var i=document.createElement(\"input\");return i.setAttribute(\"type\",\"text\"),i.setAttribute(\"id\",t),i.setAttribute(\"name\",t),i.setAttribute(\"value\",n),i.setAttribute(\"class\",r),i},n.exports.createLabel=function(t,n){var r=document.createElement(\"label\");return r.setAttribute(\"for\",n),r.textContent=t,r},n.exports.createSelection=function(t,r,i){var s=document.createElement(\"select\");return s.setAttribute(\"id\",t),s.setAttribute(\"name\",t),s.setAttribute(\"class\",i),r.forEach(function(e){s.appendChild(n.exports.createOption(e))}),s}}),define(\"ace/ext/modelist\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function i(e){var t=a.text,n=e.split(/[\\/\\\\]/).pop();for(var i=0;i<r.length;i++)if(r[i].supportsFile(n)){t=r[i];break}return t}var r=[],s=function(e,t,n){this.name=e,this.caption=t,this.mode=\"ace/mode/\"+e,this.extensions=n;var r;/\\^/.test(n)?r=n.replace(/\\|(\\^)?/g,function(e,t){return\"$|\"+(t?\"^\":\"^.*\\\\.\")})+\"$\":r=\"^.*\\\\.(\"+n+\")$\",this.extRe=new RegExp(r,\"gi\")};s.prototype.supportsFile=function(e){return e.match(this.extRe)};var o={ABAP:[\"abap\"],ABC:[\"abc\"],ActionScript:[\"as\"],ADA:[\"ada|adb\"],Apache_Conf:[\"^htaccess|^htgroups|^htpasswd|^conf|htaccess|htgroups|htpasswd\"],AsciiDoc:[\"asciidoc|adoc\"],Assembly_x86:[\"asm|a\"],AutoHotKey:[\"ahk\"],BatchFile:[\"bat|cmd\"],Bro:[\"bro\"],C_Cpp:[\"cpp|c|cc|cxx|h|hh|hpp|ino\"],C9Search:[\"c9search_results\"],Cirru:[\"cirru|cr\"],Clojure:[\"clj|cljs\"],Cobol:[\"CBL|COB\"],coffee:[\"coffee|cf|cson|^Cakefile\"],ColdFusion:[\"cfm\"],CSharp:[\"cs\"],CSS:[\"css\"],Curly:[\"curly\"],D:[\"d|di\"],Dart:[\"dart\"],Diff:[\"diff|patch\"],Dockerfile:[\"^Dockerfile\"],Dot:[\"dot\"],Drools:[\"drl\"],Dummy:[\"dummy\"],DummySyntax:[\"dummy\"],Eiffel:[\"e|ge\"],EJS:[\"ejs\"],Elixir:[\"ex|exs\"],Elm:[\"elm\"],Erlang:[\"erl|hrl\"],Forth:[\"frt|fs|ldr|fth|4th\"],Fortran:[\"f|f90\"],FTL:[\"ftl\"],Gcode:[\"gcode\"],Gherkin:[\"feature\"],Gitignore:[\"^.gitignore\"],Glsl:[\"glsl|frag|vert\"],Gobstones:[\"gbs\"],golang:[\"go\"],Groovy:[\"groovy\"],HAML:[\"haml\"],Handlebars:[\"hbs|handlebars|tpl|mustache\"],Haskell:[\"hs\"],Haskell_Cabal:[\"cabal\"],haXe:[\"hx\"],Hjson:[\"hjson\"],HTML:[\"html|htm|xhtml\"],HTML_Elixir:[\"eex|html.eex\"],HTML_Ruby:[\"erb|rhtml|html.erb\"],INI:[\"ini|conf|cfg|prefs\"],Io:[\"io\"],Jack:[\"jack\"],Jade:[\"jade|pug\"],Java:[\"java\"],JavaScript:[\"js|jsm|jsx\"],JSON:[\"json\"],JSONiq:[\"jq\"],JSP:[\"jsp\"],JSX:[\"jsx\"],Julia:[\"jl\"],Kotlin:[\"kt|kts\"],LaTeX:[\"tex|latex|ltx|bib\"],LESS:[\"less\"],Liquid:[\"liquid\"],Lisp:[\"lisp\"],LiveScript:[\"ls\"],LogiQL:[\"logic|lql\"],LSL:[\"lsl\"],Lua:[\"lua\"],LuaPage:[\"lp\"],Lucene:[\"lucene\"],Makefile:[\"^Makefile|^GNUmakefile|^makefile|^OCamlMakefile|make\"],Markdown:[\"md|markdown\"],Mask:[\"mask\"],MATLAB:[\"matlab\"],Maze:[\"mz\"],MEL:[\"mel\"],MUSHCode:[\"mc|mush\"],MySQL:[\"mysql\"],Nix:[\"nix\"],NSIS:[\"nsi|nsh\"],ObjectiveC:[\"m|mm\"],OCaml:[\"ml|mli\"],Pascal:[\"pas|p\"],Perl:[\"pl|pm\"],pgSQL:[\"pgsql\"],PHP:[\"php|phtml|shtml|php3|php4|php5|phps|phpt|aw|ctp|module\"],Powershell:[\"ps1\"],Praat:[\"praat|praatscript|psc|proc\"],Prolog:[\"plg|prolog\"],Properties:[\"properties\"],Protobuf:[\"proto\"],Python:[\"py\"],R:[\"r\"],Razor:[\"cshtml|asp\"],RDoc:[\"Rd\"],RHTML:[\"Rhtml\"],RST:[\"rst\"],Ruby:[\"rb|ru|gemspec|rake|^Guardfile|^Rakefile|^Gemfile\"],Rust:[\"rs\"],SASS:[\"sass\"],SCAD:[\"scad\"],Scala:[\"scala\"],Scheme:[\"scm|sm|rkt|oak|scheme\"],SCSS:[\"scss\"],SH:[\"sh|bash|^.bashrc\"],SJS:[\"sjs\"],Smarty:[\"smarty|tpl\"],snippets:[\"snippets\"],Soy_Template:[\"soy\"],Space:[\"space\"],SQL:[\"sql\"],SQLServer:[\"sqlserver\"],Stylus:[\"styl|stylus\"],SVG:[\"svg\"],Swift:[\"swift\"],Tcl:[\"tcl\"],Tex:[\"tex\"],Text:[\"txt\"],Textile:[\"textile\"],Toml:[\"toml\"],TSX:[\"tsx\"],Twig:[\"twig|swig\"],Typescript:[\"ts|typescript|str\"],Vala:[\"vala\"],VBScript:[\"vbs|vb\"],Velocity:[\"vm\"],Verilog:[\"v|vh|sv|svh\"],VHDL:[\"vhd|vhdl\"],Wollok:[\"wlk|wpgm|wtest\"],XML:[\"xml|rdf|rss|wsdl|xslt|atom|mathml|mml|xul|xbl|xaml\"],XQuery:[\"xq\"],YAML:[\"yaml|yml\"],Django:[\"html\"]},u={ObjectiveC:\"Objective-C\",CSharp:\"C#\",golang:\"Go\",C_Cpp:\"C and C++\",coffee:\"CoffeeScript\",HTML_Ruby:\"HTML (Ruby)\",HTML_Elixir:\"HTML (Elixir)\",FTL:\"FreeMarker\"},a={};for(var f in o){var l=o[f],c=(u[f]||f).replace(/_/g,\" \"),h=f.toLowerCase(),p=new s(h,c,l[0]);a[h]=p,r.push(p)}n.exports={getModeForPath:i,modes:r,modesByName:a}}),define(\"ace/ext/themelist\",[\"require\",\"exports\",\"module\",\"ace/lib/fixoldbrowsers\"],function(e,t,n){\"use strict\";e(\"ace/lib/fixoldbrowsers\");var r=[[\"Chrome\"],[\"Clouds\"],[\"Crimson Editor\"],[\"Dawn\"],[\"Dreamweaver\"],[\"Eclipse\"],[\"GitHub\"],[\"IPlastic\"],[\"Solarized Light\"],[\"TextMate\"],[\"Tomorrow\"],[\"XCode\"],[\"Kuroir\"],[\"KatzenMilch\"],[\"SQL Server\",\"sqlserver\",\"light\"],[\"Ambiance\",\"ambiance\",\"dark\"],[\"Chaos\",\"chaos\",\"dark\"],[\"Clouds Midnight\",\"clouds_midnight\",\"dark\"],[\"Cobalt\",\"cobalt\",\"dark\"],[\"Gruvbox\",\"gruvbox\",\"dark\"],[\"idle Fingers\",\"idle_fingers\",\"dark\"],[\"krTheme\",\"kr_theme\",\"dark\"],[\"Merbivore\",\"merbivore\",\"dark\"],[\"Merbivore Soft\",\"merbivore_soft\",\"dark\"],[\"Mono Industrial\",\"mono_industrial\",\"dark\"],[\"Monokai\",\"monokai\",\"dark\"],[\"Pastel on dark\",\"pastel_on_dark\",\"dark\"],[\"Solarized Dark\",\"solarized_dark\",\"dark\"],[\"Terminal\",\"terminal\",\"dark\"],[\"Tomorrow Night\",\"tomorrow_night\",\"dark\"],[\"Tomorrow Night Blue\",\"tomorrow_night_blue\",\"dark\"],[\"Tomorrow Night Bright\",\"tomorrow_night_bright\",\"dark\"],[\"Tomorrow Night 80s\",\"tomorrow_night_eighties\",\"dark\"],[\"Twilight\",\"twilight\",\"dark\"],[\"Vibrant Ink\",\"vibrant_ink\",\"dark\"]];t.themesByName={},t.themes=r.map(function(e){var n=e[1]||e[0].replace(/ /g,\"_\").toLowerCase(),r={caption:e[0],theme:\"ace/theme/\"+n,isDark:e[2]==\"dark\",name:n};return t.themesByName[n]=r,r})}),define(\"ace/ext/menu_tools/add_editor_menu_options\",[\"require\",\"exports\",\"module\",\"ace/ext/modelist\",\"ace/ext/themelist\"],function(e,t,n){\"use strict\";n.exports.addEditorMenuOptions=function(n){var r=e(\"../modelist\"),i=e(\"../themelist\");n.menuOptions={setNewLineMode:[{textContent:\"unix\",value:\"unix\"},{textContent:\"windows\",value:\"windows\"},{textContent:\"auto\",value:\"auto\"}],setTheme:[],setMode:[],setKeyboardHandler:[{textContent:\"ace\",value:\"\"},{textContent:\"vim\",value:\"ace/keyboard/vim\"},{textContent:\"emacs\",value:\"ace/keyboard/emacs\"},{textContent:\"textarea\",value:\"ace/keyboard/textarea\"},{textContent:\"sublime\",value:\"ace/keyboard/sublime\"}]},n.menuOptions.setTheme=i.themes.map(function(e){return{textContent:e.caption,value:e.theme}}),n.menuOptions.setMode=r.modes.map(function(e){return{textContent:e.name,value:e.mode}})}}),define(\"ace/ext/menu_tools/get_set_functions\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";n.exports.getSetFunctions=function(t){var n=[],r={editor:t,session:t.session,renderer:t.renderer},i=[],s=[\"setOption\",\"setUndoManager\",\"setDocument\",\"setValue\",\"setBreakpoints\",\"setScrollTop\",\"setScrollLeft\",\"setSelectionStyle\",\"setWrapLimitRange\"];return[\"renderer\",\"session\",\"editor\"].forEach(function(e){var t=r[e],o=e;for(var u in t)s.indexOf(u)===-1&&/^set/.test(u)&&i.indexOf(u)===-1&&(i.push(u),n.push({functionName:u,parentObj:t,parentName:o}))}),n}}),define(\"ace/ext/menu_tools/generate_settings_menu\",[\"require\",\"exports\",\"module\",\"ace/ext/menu_tools/element_generator\",\"ace/ext/menu_tools/add_editor_menu_options\",\"ace/ext/menu_tools/get_set_functions\",\"ace/ace\"],function(e,t,n){\"use strict\";var r=e(\"./element_generator\"),i=e(\"./add_editor_menu_options\").addEditorMenuOptions,s=e(\"./get_set_functions\").getSetFunctions;n.exports.generateSettingsMenu=function(n){function u(){o.sort(function(e,t){var n=e.getAttribute(\"contains\"),r=t.getAttribute(\"contains\");return n.localeCompare(r)})}function a(){var t=document.createElement(\"div\");t.setAttribute(\"id\",\"ace_settingsmenu\"),o.forEach(function(e){t.appendChild(e)});var n=t.appendChild(document.createElement(\"div\")),r=e(\"../../ace\").version;return n.style.padding=\"1em\",n.textContent=\"Ace version \"+r,t}function f(e,t,i,s){var o,u=document.createElement(\"div\");return u.setAttribute(\"contains\",i),u.setAttribute(\"class\",\"ace_optionsMenuEntry\"),u.setAttribute(\"style\",\"clear: both;\"),u.appendChild(r.createLabel(i.replace(/^set/,\"\").replace(/([A-Z])/g,\" $1\").trim(),i)),Array.isArray(s)?(o=r.createSelection(i,s,t),o.addEventListener(\"change\",function(t){try{n.menuOptions[t.target.id].forEach(function(e){e.textContent!==t.target.textContent&&delete e.selected}),e[t.target.id](t.target.value)}catch(r){throw new Error(r)}})):typeof s==\"boolean\"?(o=r.createCheckbox(i,s,t),o.addEventListener(\"change\",function(t){try{e[t.target.id](!!t.target.checked)}catch(n){throw new Error(n)}})):(o=r.createInput(i,s,t),o.addEventListener(\"change\",function(t){try{t.target.value===\"true\"?e[t.target.id](!0):t.target.value===\"false\"?e[t.target.id](!1):e[t.target.id](t.target.value)}catch(n){throw new Error(n)}})),o.style.cssText=\"float:right;\",u.appendChild(o),u}function l(e,t,r,i){var s=n.menuOptions[e],o=t[i]();return typeof o==\"object\"&&(o=o.$id),s.forEach(function(e){e.value===o&&(e.selected=\"selected\")}),f(t,r,e,s)}function c(e){var t=e.functionName,r=e.parentObj,i=e.parentName,s,u=t.replace(/^set/,\"get\");if(n.menuOptions[t]!==undefined)o.push(l(t,r,i,u));else if(typeof r[u]==\"function\")try{s=r[u](),typeof s==\"object\"&&(s=s.$id),o.push(f(r,i,t,s))}catch(a){}}var o=[];return i(n),s(n).forEach(function(e){c(e)}),u(),a()}}),define(\"ace/ext/menu_tools/overlay_page\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/dom\"),i=\"#ace_settingsmenu, #kbshortcutmenu {background-color: #F7F7F7;color: black;box-shadow: -5px 4px 5px rgba(126, 126, 126, 0.55);padding: 1em 0.5em 2em 1em;overflow: auto;position: absolute;margin: 0;bottom: 0;right: 0;top: 0;z-index: 9991;cursor: default;}.ace_dark #ace_settingsmenu, .ace_dark #kbshortcutmenu {box-shadow: -20px 10px 25px rgba(126, 126, 126, 0.25);background-color: rgba(255, 255, 255, 0.6);color: black;}.ace_optionsMenuEntry:hover {background-color: rgba(100, 100, 100, 0.1);-webkit-transition: all 0.5s;transition: all 0.3s}.ace_closeButton {background: rgba(245, 146, 146, 0.5);border: 1px solid #F48A8A;border-radius: 50%;padding: 7px;position: absolute;right: -8px;top: -8px;z-index: 1000;}.ace_closeButton{background: rgba(245, 146, 146, 0.9);}.ace_optionsMenuKey {color: darkslateblue;font-weight: bold;}.ace_optionsMenuCommand {color: darkcyan;font-weight: normal;}\";r.importCssString(i),n.exports.overlayPage=function(t,n,i,s,o,u){function l(e){e.keyCode===27&&a.click()}i=i?\"top: \"+i+\";\":\"\",o=o?\"bottom: \"+o+\";\":\"\",s=s?\"right: \"+s+\";\":\"\",u=u?\"left: \"+u+\";\":\"\";var a=document.createElement(\"div\"),f=document.createElement(\"div\");a.style.cssText=\"margin: 0; padding: 0; position: fixed; top:0; bottom:0; left:0; right:0;z-index: 9990; background-color: rgba(0, 0, 0, 0.3);\",a.addEventListener(\"click\",function(){document.removeEventListener(\"keydown\",l),a.parentNode.removeChild(a),t.focus(),a=null}),document.addEventListener(\"keydown\",l),f.style.cssText=i+s+o+u,f.addEventListener(\"click\",function(e){e.stopPropagation()});var c=r.createElement(\"div\");c.style.position=\"relative\";var h=r.createElement(\"div\");h.className=\"ace_closeButton\",h.addEventListener(\"click\",function(){a.click()}),c.appendChild(h),f.appendChild(c),f.appendChild(n),a.appendChild(f),document.body.appendChild(a),t.blur()}}),define(\"ace/ext/settings_menu\",[\"require\",\"exports\",\"module\",\"ace/ext/menu_tools/generate_settings_menu\",\"ace/ext/menu_tools/overlay_page\",\"ace/editor\"],function(e,t,n){\"use strict\";function s(e){var t=document.getElementById(\"ace_settingsmenu\");t||i(e,r(e),\"0\",\"0\",\"0\")}var r=e(\"./menu_tools/generate_settings_menu\").generateSettingsMenu,i=e(\"./menu_tools/overlay_page\").overlayPage;n.exports.init=function(t){var n=e(\"ace/editor\").Editor;n.prototype.showSettingsMenu=function(){s(this)}}});\n                (function() {\n                    window.require([\"ace/ext/settings_menu\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-spellcheck.js",
    "content": "define(\"ace/ext/spellcheck\",[\"require\",\"exports\",\"module\",\"ace/lib/event\",\"ace/editor\",\"ace/config\"],function(e,t,n){\"use strict\";var r=e(\"../lib/event\");t.contextMenuHandler=function(e){var t=e.target,n=t.textInput.getElement();if(!t.selection.isEmpty())return;var i=t.getCursorPosition(),s=t.session.getWordRange(i.row,i.column),o=t.session.getTextRange(s);t.session.tokenRe.lastIndex=0;if(!t.session.tokenRe.test(o))return;var u=\"\u0001\u0001\",a=o+\" \"+u;n.value=a,n.setSelectionRange(o.length,o.length+1),n.setSelectionRange(0,0),n.setSelectionRange(0,o.length);var f=!1;r.addListener(n,\"keydown\",function l(){r.removeListener(n,\"keydown\",l),f=!0}),t.textInput.setInputHandler(function(e){console.log(e,a,n.selectionStart,n.selectionEnd);if(e==a)return\"\";if(e.lastIndexOf(a,0)===0)return e.slice(a.length);if(e.substr(n.selectionEnd)==a)return e.slice(0,-a.length);if(e.slice(-2)==u){var r=e.slice(0,-2);if(r.slice(-1)==\" \")return f?r.substring(0,n.selectionEnd):(r=r.slice(0,-1),t.session.replace(s,r),\"\")}return e})};var i=e(\"../editor\").Editor;e(\"../config\").defineOptions(i.prototype,\"editor\",{spellcheck:{set:function(e){var n=this.textInput.getElement();n.spellcheck=!!e,e?this.on(\"nativecontextmenu\",t.contextMenuHandler):this.removeListener(\"nativecontextmenu\",t.contextMenuHandler)},value:!0}})});\n                (function() {\n                    window.require([\"ace/ext/spellcheck\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-split.js",
    "content": "define(\"ace/split\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/lib/event_emitter\",\"ace/editor\",\"ace/virtual_renderer\",\"ace/edit_session\"],function(e,t,n){\"use strict\";function l(e,t){this.$u=e,this.$doc=t}var r=e(\"./lib/oop\"),i=e(\"./lib/lang\"),s=e(\"./lib/event_emitter\").EventEmitter,o=e(\"./editor\").Editor,u=e(\"./virtual_renderer\").VirtualRenderer,a=e(\"./edit_session\").EditSession,f=function(e,t,n){this.BELOW=1,this.BESIDE=0,this.$container=e,this.$theme=t,this.$splits=0,this.$editorCSS=\"\",this.$editors=[],this.$orientation=this.BESIDE,this.setSplits(n||1),this.$cEditor=this.$editors[0],this.on(\"focus\",function(e){this.$cEditor=e}.bind(this))};(function(){r.implement(this,s),this.$createEditor=function(){var e=document.createElement(\"div\");e.className=this.$editorCSS,e.style.cssText=\"position: absolute; top:0px; bottom:0px\",this.$container.appendChild(e);var t=new o(new u(e,this.$theme));return t.on(\"focus\",function(){this._emit(\"focus\",t)}.bind(this)),this.$editors.push(t),t.setFontSize(this.$fontSize),t},this.setSplits=function(e){var t;if(e<1)throw\"The number of splits have to be > 0!\";if(e==this.$splits)return;if(e>this.$splits){while(this.$splits<this.$editors.length&&this.$splits<e)t=this.$editors[this.$splits],this.$container.appendChild(t.container),t.setFontSize(this.$fontSize),this.$splits++;while(this.$splits<e)this.$createEditor(),this.$splits++}else while(this.$splits>e)t=this.$editors[this.$splits-1],this.$container.removeChild(t.container),this.$splits--;this.resize()},this.getSplits=function(){return this.$splits},this.getEditor=function(e){return this.$editors[e]},this.getCurrentEditor=function(){return this.$cEditor},this.focus=function(){this.$cEditor.focus()},this.blur=function(){this.$cEditor.blur()},this.setTheme=function(e){this.$editors.forEach(function(t){t.setTheme(e)})},this.setKeyboardHandler=function(e){this.$editors.forEach(function(t){t.setKeyboardHandler(e)})},this.forEach=function(e,t){this.$editors.forEach(e,t)},this.$fontSize=\"\",this.setFontSize=function(e){this.$fontSize=e,this.forEach(function(t){t.setFontSize(e)})},this.$cloneSession=function(e){var t=new a(e.getDocument(),e.getMode()),n=e.getUndoManager();if(n){var r=new l(n,t);t.setUndoManager(r)}return t.$informUndoManager=i.delayedCall(function(){t.$deltas=[]}),t.setTabSize(e.getTabSize()),t.setUseSoftTabs(e.getUseSoftTabs()),t.setOverwrite(e.getOverwrite()),t.setBreakpoints(e.getBreakpoints()),t.setUseWrapMode(e.getUseWrapMode()),t.setUseWorker(e.getUseWorker()),t.setWrapLimitRange(e.$wrapLimitRange.min,e.$wrapLimitRange.max),t.$foldData=e.$cloneFoldData(),t},this.setSession=function(e,t){var n;t==null?n=this.$cEditor:n=this.$editors[t];var r=this.$editors.some(function(t){return t.session===e});return r&&(e=this.$cloneSession(e)),n.setSession(e),e},this.getOrientation=function(){return this.$orientation},this.setOrientation=function(e){if(this.$orientation==e)return;this.$orientation=e,this.resize()},this.resize=function(){var e=this.$container.clientWidth,t=this.$container.clientHeight,n;if(this.$orientation==this.BESIDE){var r=e/this.$splits;for(var i=0;i<this.$splits;i++)n=this.$editors[i],n.container.style.width=r+\"px\",n.container.style.top=\"0px\",n.container.style.left=i*r+\"px\",n.container.style.height=t+\"px\",n.resize()}else{var s=t/this.$splits;for(var i=0;i<this.$splits;i++)n=this.$editors[i],n.container.style.width=e+\"px\",n.container.style.top=i*s+\"px\",n.container.style.left=\"0px\",n.container.style.height=s+\"px\",n.resize()}}}).call(f.prototype),function(){this.execute=function(e){this.$u.execute(e)},this.undo=function(){var e=this.$u.undo(!0);e&&this.$doc.selection.setSelectionRange(e)},this.redo=function(){var e=this.$u.redo(!0);e&&this.$doc.selection.setSelectionRange(e)},this.reset=function(){this.$u.reset()},this.hasUndo=function(){return this.$u.hasUndo()},this.hasRedo=function(){return this.$u.hasRedo()}}.call(l.prototype),t.Split=f}),define(\"ace/ext/split\",[\"require\",\"exports\",\"module\",\"ace/split\"],function(e,t,n){\"use strict\";n.exports=e(\"../split\")});\n                (function() {\n                    window.require([\"ace/ext/split\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-static_highlight.js",
    "content": "define(\"ace/ext/static_highlight\",[\"require\",\"exports\",\"module\",\"ace/edit_session\",\"ace/layer/text\",\"ace/config\",\"ace/lib/dom\"],function(e,t,n){\"use strict\";var r=e(\"../edit_session\").EditSession,i=e(\"../layer/text\").Text,s=\".ace_static_highlight {font-family: 'Monaco', 'Menlo', 'Ubuntu Mono', 'Consolas', 'source-code-pro', 'Droid Sans Mono', monospace;font-size: 12px;white-space: pre-wrap}.ace_static_highlight .ace_gutter {width: 2em;text-align: right;padding: 0 3px 0 0;margin-right: 3px;}.ace_static_highlight.ace_show_gutter .ace_line {padding-left: 2.6em;}.ace_static_highlight .ace_line { position: relative; }.ace_static_highlight .ace_gutter-cell {-moz-user-select: -moz-none;-khtml-user-select: none;-webkit-user-select: none;user-select: none;top: 0;bottom: 0;left: 0;position: absolute;}.ace_static_highlight .ace_gutter-cell:before {content: counter(ace_line, decimal);counter-increment: ace_line;}.ace_static_highlight {counter-reset: ace_line;}\",o=e(\"../config\"),u=e(\"../lib/dom\"),a=function(){this.config={}};a.prototype=i.prototype;var f=function(e,t,n){var r=e.className.match(/lang-(\\w+)/),i=t.mode||r&&\"ace/mode/\"+r[1];if(!i)return!1;var s=t.theme||\"ace/theme/textmate\",o=\"\",a=[];if(e.firstElementChild){var l=0;for(var c=0;c<e.childNodes.length;c++){var h=e.childNodes[c];h.nodeType==3?(l+=h.data.length,o+=h.data):a.push(l,h)}}else o=u.getInnerText(e),t.trim&&(o=o.trim());f.render(o,i,s,t.firstLineNumber,!t.showGutter,function(t){u.importCssString(t.css,\"ace_highlight\"),e.innerHTML=t.html;var r=e.firstChild.firstChild;for(var i=0;i<a.length;i+=2){var s=t.session.doc.indexToPosition(a[i]),o=a[i+1],f=r.children[s.row];f&&f.appendChild(o)}n&&n()})};f.render=function(e,t,n,i,s,u){function h(){var r=f.renderSync(e,t,n,i,s);return u?u(r):r}var a=1,l=r.prototype.$modes;typeof n==\"string\"&&(a++,o.loadModule([\"theme\",n],function(e){n=e,--a||h()}));var c;return t&&typeof t==\"object\"&&!t.getTokenizer&&(c=t,t=c.path),typeof t==\"string\"&&(a++,o.loadModule([\"mode\",t],function(e){if(!l[t]||c)l[t]=new e.Mode(c);t=l[t],--a||h()})),--a||h()},f.renderSync=function(e,t,n,i,o){i=parseInt(i||1,10);var u=new r(\"\");u.setUseWorker(!1),u.setMode(t);var f=new a;f.setSession(u),u.setValue(e);var l=[],c=u.getLength();for(var h=0;h<c;h++)l.push(\"<div class='ace_line'>\"),o||l.push(\"<span class='ace_gutter ace_gutter-cell' unselectable='on'></span>\"),f.$renderLine(l,h,!0,!1),l.push(\"\\n</div>\");var p=\"<div class='\"+n.cssClass+\"'>\"+\"<div class='ace_static_highlight\"+(o?\"\":\" ace_show_gutter\")+\"' style='counter-reset:ace_line \"+(i-1)+\"'>\"+l.join(\"\")+\"</div>\"+\"</div>\";return f.destroy(),{css:s+n.cssText,html:p,session:u}},n.exports=f,n.exports.highlight=f});\n                (function() {\n                    window.require([\"ace/ext/static_highlight\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-textarea.js",
    "content": "define(\"ace/theme/textmate\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\"],function(e,t,n){\"use strict\";t.isDark=!1,t.cssClass=\"ace-tm\",t.cssText='.ace-tm .ace_gutter {background: #f0f0f0;color: #333;}.ace-tm .ace_print-margin {width: 1px;background: #e8e8e8;}.ace-tm .ace_fold {background-color: #6B72E6;}.ace-tm {background-color: #FFFFFF;color: black;}.ace-tm .ace_cursor {color: black;}.ace-tm .ace_invisible {color: rgb(191, 191, 191);}.ace-tm .ace_storage,.ace-tm .ace_keyword {color: blue;}.ace-tm .ace_constant {color: rgb(197, 6, 11);}.ace-tm .ace_constant.ace_buildin {color: rgb(88, 72, 246);}.ace-tm .ace_constant.ace_language {color: rgb(88, 92, 246);}.ace-tm .ace_constant.ace_library {color: rgb(6, 150, 14);}.ace-tm .ace_invalid {background-color: rgba(255, 0, 0, 0.1);color: red;}.ace-tm .ace_support.ace_function {color: rgb(60, 76, 114);}.ace-tm .ace_support.ace_constant {color: rgb(6, 150, 14);}.ace-tm .ace_support.ace_type,.ace-tm .ace_support.ace_class {color: rgb(109, 121, 222);}.ace-tm .ace_keyword.ace_operator {color: rgb(104, 118, 135);}.ace-tm .ace_string {color: rgb(3, 106, 7);}.ace-tm .ace_comment {color: rgb(76, 136, 107);}.ace-tm .ace_comment.ace_doc {color: rgb(0, 102, 255);}.ace-tm .ace_comment.ace_doc.ace_tag {color: rgb(128, 159, 191);}.ace-tm .ace_constant.ace_numeric {color: rgb(0, 0, 205);}.ace-tm .ace_variable {color: rgb(49, 132, 149);}.ace-tm .ace_xml-pe {color: rgb(104, 104, 91);}.ace-tm .ace_entity.ace_name.ace_function {color: #0000A2;}.ace-tm .ace_heading {color: rgb(12, 7, 255);}.ace-tm .ace_list {color:rgb(185, 6, 144);}.ace-tm .ace_meta.ace_tag {color:rgb(0, 22, 142);}.ace-tm .ace_string.ace_regex {color: rgb(255, 0, 0)}.ace-tm .ace_marker-layer .ace_selection {background: rgb(181, 213, 255);}.ace-tm.ace_multiselect .ace_selection.ace_start {box-shadow: 0 0 3px 0px white;}.ace-tm .ace_marker-layer .ace_step {background: rgb(252, 255, 0);}.ace-tm .ace_marker-layer .ace_stack {background: rgb(164, 229, 101);}.ace-tm .ace_marker-layer .ace_bracket {margin: -1px 0 0 -1px;border: 1px solid rgb(192, 192, 192);}.ace-tm .ace_marker-layer .ace_active-line {background: rgba(0, 0, 0, 0.07);}.ace-tm .ace_gutter-active-line {background-color : #dcdcdc;}.ace-tm .ace_marker-layer .ace_selected-word {background: rgb(250, 250, 255);border: 1px solid rgb(200, 200, 250);}.ace-tm .ace_indent-guide {background: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAACCAYAAACZgbYnAAAAE0lEQVQImWP4////f4bLly//BwAmVgd1/w11/gAAAABJRU5ErkJggg==\") right repeat-y;}';var r=e(\"../lib/dom\");r.importCssString(t.cssText,t.cssClass)}),define(\"ace/ext/textarea\",[\"require\",\"exports\",\"module\",\"ace/lib/event\",\"ace/lib/useragent\",\"ace/lib/net\",\"ace/ace\",\"ace/theme/textmate\"],function(e,t,n){\"use strict\";function a(e,t){for(var n in t)e.style[n]=t[n]}function f(e,t){if(e.type!=\"textarea\")throw new Error(\"Textarea required!\");var n=e.parentNode,i=document.createElement(\"div\"),s=function(){var t=\"position:relative;\";[\"margin-top\",\"margin-left\",\"margin-right\",\"margin-bottom\"].forEach(function(n){t+=n+\":\"+u(e,i,n)+\";\"});var n=u(e,i,\"width\")||e.clientWidth+\"px\",r=u(e,i,\"height\")||e.clientHeight+\"px\";t+=\"height:\"+r+\";width:\"+n+\";\",t+=\"display:inline-block;\",i.setAttribute(\"style\",t)};r.addListener(window,\"resize\",s),s(),n.insertBefore(i,e.nextSibling);while(n!==document){if(n.tagName.toUpperCase()===\"FORM\"){var o=n.onsubmit;n.onsubmit=function(n){e.value=t(),o&&o.call(this,n)};break}n=n.parentNode}return i}function l(t,n,r){s.loadScript(t,function(){e([n],r)})}function c(e,t,n,r,i,s){function a(e){return e===\"true\"||e==1}var o=e.getSession(),u=e.renderer;return s=s||l,e.setDisplaySettings=function(t){t==null&&(t=n.style.display==\"none\"),t?(n.style.display=\"block\",n.hideButton.focus(),e.on(\"focus\",function r(){e.removeListener(\"focus\",r),n.style.display=\"none\"})):e.focus()},e.$setOption=e.setOption,e.$getOption=e.getOption,e.setOption=function(t,n){switch(t){case\"mode\":e.$setOption(\"mode\",\"ace/mode/\"+n);break;case\"theme\":e.$setOption(\"theme\",\"ace/theme/\"+n);break;case\"keybindings\":switch(n){case\"vim\":e.setKeyboardHandler(\"ace/keyboard/vim\");break;case\"emacs\":e.setKeyboardHandler(\"ace/keyboard/emacs\");break;default:e.setKeyboardHandler(null)}break;case\"softWrap\":case\"fontSize\":e.$setOption(t,n);break;default:e.$setOption(t,a(n))}},e.getOption=function(t){switch(t){case\"mode\":return e.$getOption(\"mode\").substr(\"ace/mode/\".length);case\"theme\":return e.$getOption(\"theme\").substr(\"ace/theme/\".length);case\"keybindings\":var n=e.getKeyboardHandler();switch(n&&n.$id){case\"ace/keyboard/vim\":return\"vim\";case\"ace/keyboard/emacs\":return\"emacs\";default:return\"ace\"}break;default:return e.$getOption(t)}},e.setOptions(i),e}function h(e,n,i){function f(e,t,n,r){if(!n){e.push(\"<input type='checkbox' title='\",t,\"' \",r+\"\"==\"true\"?\"checked='true'\":\"\",\"'></input>\");return}e.push(\"<select title='\"+t+\"'>\");for(var i in n)e.push(\"<option value='\"+i+\"' \"),r==i&&e.push(\" selected \"),e.push(\">\",n[i],\"</option>\");e.push(\"</select>\")}var s=null,o={mode:\"Mode:\",wrap:\"Soft Wrap:\",theme:\"Theme:\",fontSize:\"Font Size:\",showGutter:\"Display Gutter:\",keybindings:\"Keyboard\",showPrintMargin:\"Show Print Margin:\",useSoftTabs:\"Use Soft Tabs:\",showInvisibles:\"Show Invisibles\"},u={mode:{text:\"Plain\",javascript:\"JavaScript\",xml:\"XML\",html:\"HTML\",css:\"CSS\",scss:\"SCSS\",python:\"Python\",php:\"PHP\",java:\"Java\",ruby:\"Ruby\",c_cpp:\"C/C++\",coffee:\"CoffeeScript\",json:\"json\",perl:\"Perl\",clojure:\"Clojure\",ocaml:\"OCaml\",csharp:\"C#\",haxe:\"haXe\",svg:\"SVG\",textile:\"Textile\",groovy:\"Groovy\",liquid:\"Liquid\",Scala:\"Scala\"},theme:{clouds:\"Clouds\",clouds_midnight:\"Clouds Midnight\",cobalt:\"Cobalt\",crimson_editor:\"Crimson Editor\",dawn:\"Dawn\",eclipse:\"Eclipse\",idle_fingers:\"Idle Fingers\",kr_theme:\"Kr Theme\",merbivore:\"Merbivore\",merbivore_soft:\"Merbivore Soft\",mono_industrial:\"Mono Industrial\",monokai:\"Monokai\",pastel_on_dark:\"Pastel On Dark\",solarized_dark:\"Solarized Dark\",solarized_light:\"Solarized Light\",textmate:\"Textmate\",twilight:\"Twilight\",vibrant_ink:\"Vibrant Ink\"},showGutter:s,fontSize:{\"10px\":\"10px\",\"11px\":\"11px\",\"12px\":\"12px\",\"14px\":\"14px\",\"16px\":\"16px\"},wrap:{off:\"Off\",40:\"40\",80:\"80\",free:\"Free\"},keybindings:{ace:\"ace\",vim:\"vim\",emacs:\"emacs\"},showPrintMargin:s,useSoftTabs:s,showInvisibles:s},a=[];a.push(\"<table><tr><th>Setting</th><th>Value</th></tr>\");for(var l in t.defaultOptions)a.push(\"<tr><td>\",o[l],\"</td>\"),a.push(\"<td>\"),f(a,l,u[l],i.getOption(l)),a.push(\"</td></tr>\");a.push(\"</table>\"),e.innerHTML=a.join(\"\");var c=function(e){var t=e.currentTarget;i.setOption(t.title,t.value)},h=function(e){var t=e.currentTarget;i.setOption(t.title,t.checked)},p=e.getElementsByTagName(\"select\");for(var d=0;d<p.length;d++)p[d].onchange=c;var v=e.getElementsByTagName(\"input\");for(var d=0;d<v.length;d++)v[d].onclick=h;var m=document.createElement(\"input\");m.type=\"button\",m.value=\"Hide\",r.addListener(m,\"click\",function(){i.setDisplaySettings(!1)}),e.appendChild(m),e.hideButton=m}var r=e(\"../lib/event\"),i=e(\"../lib/useragent\"),s=e(\"../lib/net\"),o=e(\"../ace\");e(\"../theme/textmate\"),n.exports=t=o;var u=function(e,t,n){var r=e.style[n];r||(window.getComputedStyle?r=window.getComputedStyle(e,\"\").getPropertyValue(n):r=e.currentStyle[n]);if(!r||r==\"auto\"||r==\"intrinsic\")r=t.style[n];return r};t.transformTextarea=function(e,n){var s,u=f(e,function(){return s.getValue()});e.style.display=\"none\",u.style.background=\"white\";var p=document.createElement(\"div\");a(p,{top:\"0px\",left:\"0px\",right:\"0px\",bottom:\"0px\",border:\"1px solid gray\",position:\"absolute\"}),u.appendChild(p);var d=document.createElement(\"div\");a(d,{position:\"absolute\",right:\"0px\",bottom:\"0px\",background:\"red\",cursor:\"nw-resize\",borderStyle:\"solid\",borderWidth:\"9px 8px 10px 9px\",width:\"2px\",borderColor:\"lightblue gray gray lightblue\",zIndex:101});var v=document.createElement(\"div\"),m={top:\"0px\",left:\"20%\",right:\"0px\",bottom:\"0px\",position:\"absolute\",padding:\"5px\",zIndex:100,color:\"white\",display:\"none\",overflow:\"auto\",fontSize:\"14px\",boxShadow:\"-5px 2px 3px gray\"};i.isOldIE?m.backgroundColor=\"#333\":m.backgroundColor=\"rgba(0, 0, 0, 0.6)\",a(v,m),u.appendChild(v),n=n||t.defaultOptions;var g=o.edit(p);s=g.getSession(),s.setValue(e.value||e.innerHTML),g.focus(),u.appendChild(d),c(g,p,v,o,n,l),h(v,d,g);var y=\"\";return r.addListener(d,\"mousemove\",function(e){var t=this.getBoundingClientRect(),n=e.clientX-t.left,r=e.clientY-t.top;n+r<(t.width+t.height)/2?(this.style.cursor=\"pointer\",y=\"toggle\"):(y=\"resize\",this.style.cursor=\"nw-resize\")}),r.addListener(d,\"mousedown\",function(e){if(y==\"toggle\"){g.setDisplaySettings();return}u.style.zIndex=1e5;var t=u.getBoundingClientRect(),n=t.width+t.left-e.clientX,i=t.height+t.top-e.clientY;r.capture(d,function(e){u.style.width=e.clientX-t.left+n+\"px\",u.style.height=e.clientY-t.top+i+\"px\",g.resize()},function(){})}),g},t.defaultOptions={mode:\"javascript\",theme:\"textmate\",wrap:\"off\",fontSize:\"12px\",showGutter:\"false\",keybindings:\"ace\",showPrintMargin:\"false\",useSoftTabs:\"true\",showInvisibles:\"false\"}});\n                (function() {\n                    window.require([\"ace/ext/textarea\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-themelist.js",
    "content": "define(\"ace/ext/themelist\",[\"require\",\"exports\",\"module\",\"ace/lib/fixoldbrowsers\"],function(e,t,n){\"use strict\";e(\"ace/lib/fixoldbrowsers\");var r=[[\"Chrome\"],[\"Clouds\"],[\"Crimson Editor\"],[\"Dawn\"],[\"Dreamweaver\"],[\"Eclipse\"],[\"GitHub\"],[\"IPlastic\"],[\"Solarized Light\"],[\"TextMate\"],[\"Tomorrow\"],[\"XCode\"],[\"Kuroir\"],[\"KatzenMilch\"],[\"SQL Server\",\"sqlserver\",\"light\"],[\"Ambiance\",\"ambiance\",\"dark\"],[\"Chaos\",\"chaos\",\"dark\"],[\"Clouds Midnight\",\"clouds_midnight\",\"dark\"],[\"Cobalt\",\"cobalt\",\"dark\"],[\"Gruvbox\",\"gruvbox\",\"dark\"],[\"idle Fingers\",\"idle_fingers\",\"dark\"],[\"krTheme\",\"kr_theme\",\"dark\"],[\"Merbivore\",\"merbivore\",\"dark\"],[\"Merbivore Soft\",\"merbivore_soft\",\"dark\"],[\"Mono Industrial\",\"mono_industrial\",\"dark\"],[\"Monokai\",\"monokai\",\"dark\"],[\"Pastel on dark\",\"pastel_on_dark\",\"dark\"],[\"Solarized Dark\",\"solarized_dark\",\"dark\"],[\"Terminal\",\"terminal\",\"dark\"],[\"Tomorrow Night\",\"tomorrow_night\",\"dark\"],[\"Tomorrow Night Blue\",\"tomorrow_night_blue\",\"dark\"],[\"Tomorrow Night Bright\",\"tomorrow_night_bright\",\"dark\"],[\"Tomorrow Night 80s\",\"tomorrow_night_eighties\",\"dark\"],[\"Twilight\",\"twilight\",\"dark\"],[\"Vibrant Ink\",\"vibrant_ink\",\"dark\"]];t.themesByName={},t.themes=r.map(function(e){var n=e[1]||e[0].replace(/ /g,\"_\").toLowerCase(),r={caption:e[0],theme:\"ace/theme/\"+n,isDark:e[2]==\"dark\",name:n};return t.themesByName[n]=r,r})});\n                (function() {\n                    window.require([\"ace/ext/themelist\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/ext-whitespace.js",
    "content": "define(\"ace/ext/whitespace\",[\"require\",\"exports\",\"module\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../lib/lang\");t.$detectIndentation=function(e,t){function c(e){var t=0;for(var r=e;r<n.length;r+=e)t+=n[r]||0;return t}var n=[],r=[],i=0,s=0,o=Math.min(e.length,1e3);for(var u=0;u<o;u++){var a=e[u];if(!/^\\s*[^*+\\-\\s]/.test(a))continue;if(a[0]==\"\t\")i++,s=-Number.MAX_VALUE;else{var f=a.match(/^ */)[0].length;if(f&&a[f]!=\"\t\"){var l=f-s;l>0&&!(s%l)&&!(f%l)&&(r[l]=(r[l]||0)+1),n[f]=(n[f]||0)+1}s=f}while(u<o&&a[a.length-1]==\"\\\\\")a=e[u++]}var h=r.reduce(function(e,t){return e+t},0),p={score:0,length:0},d=0;for(var u=1;u<12;u++){var v=c(u);u==1?(d=v,v=n[1]?.9:.8,n.length||(v=0)):v/=d,r[u]&&(v+=r[u]/h),v>p.score&&(p={score:v,length:u})}if(p.score&&p.score>1.4)var m=p.length;if(i>d+1){if(m==1||d<i/4||p.score<1.8)m=undefined;return{ch:\"\t\",length:m}}if(d>i+1)return{ch:\" \",length:m}},t.detectIndentation=function(e){var n=e.getLines(0,1e3),r=t.$detectIndentation(n)||{};return r.ch&&e.setUseSoftTabs(r.ch==\" \"),r.length&&e.setTabSize(r.length),r},t.trimTrailingSpace=function(e,t){var n=e.getDocument(),r=n.getAllLines(),i=t?-1:0;for(var s=0,o=r.length;s<o;s++){var u=r[s],a=u.search(/\\s+$/);a>i&&n.removeInLine(s,a,u.length)}},t.convertIndentation=function(e,t,n){var i=e.getTabString()[0],s=e.getTabSize();n||(n=s),t||(t=i);var o=t==\"\t\"?t:r.stringRepeat(t,n),u=e.doc,a=u.getAllLines(),f={},l={};for(var c=0,h=a.length;c<h;c++){var p=a[c],d=p.match(/^\\s*/)[0];if(d){var v=e.$getStringScreenWidth(d)[0],m=Math.floor(v/s),g=v%s,y=f[m]||(f[m]=r.stringRepeat(o,m));y+=l[g]||(l[g]=r.stringRepeat(\" \",g)),y!=d&&(u.removeInLine(c,0,d.length),u.insertInLine({row:c,column:0},y))}}e.setTabSize(n),e.setUseSoftTabs(t==\" \")},t.$parseStringArg=function(e){var t={};/t/.test(e)?t.ch=\"\t\":/s/.test(e)&&(t.ch=\" \");var n=e.match(/\\d+/);return n&&(t.length=parseInt(n[0],10)),t},t.$parseArg=function(e){return e?typeof e==\"string\"?t.$parseStringArg(e):typeof e.text==\"string\"?t.$parseStringArg(e.text):e:{}},t.commands=[{name:\"detectIndentation\",exec:function(e){t.detectIndentation(e.session)}},{name:\"trimTrailingSpace\",exec:function(e){t.trimTrailingSpace(e.session)}},{name:\"convertIndentation\",exec:function(e,n){var r=t.$parseArg(n);t.convertIndentation(e.session,r.ch,r.length)}},{name:\"setIndentation\",exec:function(e,n){var r=t.$parseArg(n);r.length&&e.session.setTabSize(r.length),r.ch&&e.session.setUseSoftTabs(r.ch==\" \")}}]});\n                (function() {\n                    window.require([\"ace/ext/whitespace\"], function() {});\n                })();\n            "
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/keybinding-emacs.js",
    "content": "define(\"ace/occur\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/search\",\"ace/edit_session\",\"ace/search_highlight\",\"ace/lib/dom\"],function(e,t,n){\"use strict\";function a(){}var r=e(\"./lib/oop\"),i=e(\"./range\").Range,s=e(\"./search\").Search,o=e(\"./edit_session\").EditSession,u=e(\"./search_highlight\").SearchHighlight;r.inherits(a,s),function(){this.enter=function(e,t){if(!t.needle)return!1;var n=e.getCursorPosition();this.displayOccurContent(e,t);var r=this.originalToOccurPosition(e.session,n);return e.moveCursorToPosition(r),!0},this.exit=function(e,t){var n=t.translatePosition&&e.getCursorPosition(),r=n&&this.occurToOriginalPosition(e.session,n);return this.displayOriginalContent(e),r&&e.moveCursorToPosition(r),!0},this.highlight=function(e,t){var n=e.$occurHighlight=e.$occurHighlight||e.addDynamicMarker(new u(null,\"ace_occur-highlight\",\"text\"));n.setRegexp(t),e._emit(\"changeBackMarker\")},this.displayOccurContent=function(e,t){this.$originalSession=e.session;var n=this.matchingLines(e.session,t),r=n.map(function(e){return e.content}),i=new o(r.join(\"\\n\"));i.$occur=this,i.$occurMatchingLines=n,e.setSession(i),this.$useEmacsStyleLineStart=this.$originalSession.$useEmacsStyleLineStart,i.$useEmacsStyleLineStart=this.$useEmacsStyleLineStart,this.highlight(i,t.re),i._emit(\"changeBackMarker\")},this.displayOriginalContent=function(e){e.setSession(this.$originalSession),this.$originalSession.$useEmacsStyleLineStart=this.$useEmacsStyleLineStart},this.originalToOccurPosition=function(e,t){var n=e.$occurMatchingLines,r={row:0,column:0};if(!n)return r;for(var i=0;i<n.length;i++)if(n[i].row===t.row)return{row:i,column:t.column};return r},this.occurToOriginalPosition=function(e,t){var n=e.$occurMatchingLines;return!n||!n[t.row]?t:{row:n[t.row].row,column:t.column}},this.matchingLines=function(e,t){t=r.mixin({},t);if(!e||!t.needle)return[];var n=new s;return n.set(t),n.findAll(e).reduce(function(t,n){var r=n.start.row,i=t[t.length-1];return i&&i.row===r?t:t.concat({row:r,content:e.getLine(r)})},[])}}.call(a.prototype);var f=e(\"./lib/dom\");f.importCssString(\".ace_occur-highlight {\\n    border-radius: 4px;\\n    background-color: rgba(87, 255, 8, 0.25);\\n    position: absolute;\\n    z-index: 4;\\n    -moz-box-sizing: border-box;\\n    -webkit-box-sizing: border-box;\\n    box-sizing: border-box;\\n    box-shadow: 0 0 4px rgb(91, 255, 50);\\n}\\n.ace_dark .ace_occur-highlight {\\n    background-color: rgb(80, 140, 85);\\n    box-shadow: 0 0 4px rgb(60, 120, 70);\\n}\\n\",\"incremental-occur-highlighting\"),t.Occur=a}),define(\"ace/commands/occur_commands\",[\"require\",\"exports\",\"module\",\"ace/config\",\"ace/occur\",\"ace/keyboard/hash_handler\",\"ace/lib/oop\"],function(e,t,n){function f(){}var r=e(\"../config\"),i=e(\"../occur\").Occur,s={name:\"occur\",exec:function(e,t){var n=!!e.session.$occur,r=(new i).enter(e,t);r&&!n&&f.installIn(e)},readOnly:!0},o=[{name:\"occurexit\",bindKey:\"esc|Ctrl-G\",exec:function(e){var t=e.session.$occur;if(!t)return;t.exit(e,{}),e.session.$occur||f.uninstallFrom(e)},readOnly:!0},{name:\"occuraccept\",bindKey:\"enter\",exec:function(e){var t=e.session.$occur;if(!t)return;t.exit(e,{translatePosition:!0}),e.session.$occur||f.uninstallFrom(e)},readOnly:!0}],u=e(\"../keyboard/hash_handler\").HashHandler,a=e(\"../lib/oop\");a.inherits(f,u),function(){this.isOccurHandler=!0,this.attach=function(e){u.call(this,o,e.commands.platform),this.$editor=e};var e=this.handleKeyboard;this.handleKeyboard=function(t,n,r,i){var s=e.call(this,t,n,r,i);return s&&s.command?s:undefined}}.call(f.prototype),f.installIn=function(e){var t=new this;e.keyBinding.addKeyboardHandler(t),e.commands.addCommands(o)},f.uninstallFrom=function(e){e.commands.removeCommands(o);var t=e.getKeyboardHandler();t.isOccurHandler&&e.keyBinding.removeKeyboardHandler(t)},t.occurStartCommand=s}),define(\"ace/commands/incremental_search_commands\",[\"require\",\"exports\",\"module\",\"ace/config\",\"ace/lib/oop\",\"ace/keyboard/hash_handler\",\"ace/commands/occur_commands\"],function(e,t,n){function u(e){this.$iSearch=e}var r=e(\"../config\"),i=e(\"../lib/oop\"),s=e(\"../keyboard/hash_handler\").HashHandler,o=e(\"./occur_commands\").occurStartCommand;t.iSearchStartCommands=[{name:\"iSearch\",bindKey:{win:\"Ctrl-F\",mac:\"Command-F\"},exec:function(e,t){r.loadModule([\"core\",\"ace/incremental_search\"],function(n){var r=n.iSearch=n.iSearch||new n.IncrementalSearch;r.activate(e,t.backwards),t.jumpToFirstMatch&&r.next(t)})},readOnly:!0},{name:\"iSearchBackwards\",exec:function(e,t){e.execCommand(\"iSearch\",{backwards:!0})},readOnly:!0},{name:\"iSearchAndGo\",bindKey:{win:\"Ctrl-K\",mac:\"Command-G\"},exec:function(e,t){e.execCommand(\"iSearch\",{jumpToFirstMatch:!0,useCurrentOrPrevSearch:!0})},readOnly:!0},{name:\"iSearchBackwardsAndGo\",bindKey:{win:\"Ctrl-Shift-K\",mac:\"Command-Shift-G\"},exec:function(e){e.execCommand(\"iSearch\",{jumpToFirstMatch:!0,backwards:!0,useCurrentOrPrevSearch:!0})},readOnly:!0}],t.iSearchCommands=[{name:\"restartSearch\",bindKey:{win:\"Ctrl-F\",mac:\"Command-F\"},exec:function(e){e.cancelSearch(!0)}},{name:\"searchForward\",bindKey:{win:\"Ctrl-S|Ctrl-K\",mac:\"Ctrl-S|Command-G\"},exec:function(e,t){t.useCurrentOrPrevSearch=!0,e.next(t)}},{name:\"searchBackward\",bindKey:{win:\"Ctrl-R|Ctrl-Shift-K\",mac:\"Ctrl-R|Command-Shift-G\"},exec:function(e,t){t.useCurrentOrPrevSearch=!0,t.backwards=!0,e.next(t)}},{name:\"extendSearchTerm\",exec:function(e,t){e.addString(t)}},{name:\"extendSearchTermSpace\",bindKey:\"space\",exec:function(e){e.addString(\" \")}},{name:\"shrinkSearchTerm\",bindKey:\"backspace\",exec:function(e){e.removeChar()}},{name:\"confirmSearch\",bindKey:\"return\",exec:function(e){e.deactivate()}},{name:\"cancelSearch\",bindKey:\"esc|Ctrl-G\",exec:function(e){e.deactivate(!0)}},{name:\"occurisearch\",bindKey:\"Ctrl-O\",exec:function(e){var t=i.mixin({},e.$options);e.deactivate(),o.exec(e.$editor,t)}},{name:\"yankNextWord\",bindKey:\"Ctrl-w\",exec:function(e){var t=e.$editor,n=t.selection.getRangeOfMovements(function(e){e.moveCursorWordRight()}),r=t.session.getTextRange(n);e.addString(r)}},{name:\"yankNextChar\",bindKey:\"Ctrl-Alt-y\",exec:function(e){var t=e.$editor,n=t.selection.getRangeOfMovements(function(e){e.moveCursorRight()}),r=t.session.getTextRange(n);e.addString(r)}},{name:\"recenterTopBottom\",bindKey:\"Ctrl-l\",exec:function(e){e.$editor.execCommand(\"recenterTopBottom\")}},{name:\"selectAllMatches\",bindKey:\"Ctrl-space\",exec:function(e){var t=e.$editor,n=t.session.$isearchHighlight,r=n&&n.cache?n.cache.reduce(function(e,t){return e.concat(t?t:[])},[]):[];e.deactivate(!1),r.forEach(t.selection.addRange.bind(t.selection))}},{name:\"searchAsRegExp\",bindKey:\"Alt-r\",exec:function(e){e.convertNeedleToRegExp()}}].map(function(e){return e.readOnly=!0,e.isIncrementalSearchCommand=!0,e.scrollIntoView=\"animate-cursor\",e}),i.inherits(u,s),function(){this.attach=function(e){var n=this.$iSearch;s.call(this,t.iSearchCommands,e.commands.platform),this.$commandExecHandler=e.commands.addEventListener(\"exec\",function(t){if(!t.command.isIncrementalSearchCommand)return n.deactivate();t.stopPropagation(),t.preventDefault();var r=e.session.getScrollTop(),i=t.command.exec(n,t.args||{});return e.renderer.scrollCursorIntoView(null,.5),e.renderer.animateScrolling(r),i})},this.detach=function(e){if(!this.$commandExecHandler)return;e.commands.removeEventListener(\"exec\",this.$commandExecHandler),delete this.$commandExecHandler};var e=this.handleKeyboard;this.handleKeyboard=function(t,n,r,i){if((n===1||n===8)&&r===\"v\"||n===1&&r===\"y\")return null;var s=e.call(this,t,n,r,i);if(s.command)return s;if(n==-1){var o=this.commands.extendSearchTerm;if(o)return{command:o,args:r}}return!1}}.call(u.prototype),t.IncrementalSearchKeyboardHandler=u}),define(\"ace/incremental_search\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/search\",\"ace/search_highlight\",\"ace/commands/incremental_search_commands\",\"ace/lib/dom\",\"ace/commands/command_manager\",\"ace/editor\",\"ace/config\"],function(e,t,n){\"use strict\";function f(){this.$options={wrap:!1,skipCurrent:!1},this.$keyboardHandler=new a(this)}function l(e){return e instanceof RegExp}function c(e){var t=String(e),n=t.indexOf(\"/\"),r=t.lastIndexOf(\"/\");return{expression:t.slice(n+1,r),flags:t.slice(r+1)}}function h(e,t){try{return new RegExp(e,t)}catch(n){return e}}function p(e){return h(e.expression,e.flags)}var r=e(\"./lib/oop\"),i=e(\"./range\").Range,s=e(\"./search\").Search,o=e(\"./search_highlight\").SearchHighlight,u=e(\"./commands/incremental_search_commands\"),a=u.IncrementalSearchKeyboardHandler;r.inherits(f,s),function(){this.activate=function(e,t){this.$editor=e,this.$startPos=this.$currentPos=e.getCursorPosition(),this.$options.needle=\"\",this.$options.backwards=t,e.keyBinding.addKeyboardHandler(this.$keyboardHandler),this.$originalEditorOnPaste=e.onPaste,e.onPaste=this.onPaste.bind(this),this.$mousedownHandler=e.addEventListener(\"mousedown\",this.onMouseDown.bind(this)),this.selectionFix(e),this.statusMessage(!0)},this.deactivate=function(e){this.cancelSearch(e);var t=this.$editor;t.keyBinding.removeKeyboardHandler(this.$keyboardHandler),this.$mousedownHandler&&(t.removeEventListener(\"mousedown\",this.$mousedownHandler),delete this.$mousedownHandler),t.onPaste=this.$originalEditorOnPaste,this.message(\"\")},this.selectionFix=function(e){e.selection.isEmpty()&&!e.session.$emacsMark&&e.clearSelection()},this.highlight=function(e){var t=this.$editor.session,n=t.$isearchHighlight=t.$isearchHighlight||t.addDynamicMarker(new o(null,\"ace_isearch-result\",\"text\"));n.setRegexp(e),t._emit(\"changeBackMarker\")},this.cancelSearch=function(e){var t=this.$editor;return this.$prevNeedle=this.$options.needle,this.$options.needle=\"\",e?(t.moveCursorToPosition(this.$startPos),this.$currentPos=this.$startPos):t.pushEmacsMark&&t.pushEmacsMark(this.$startPos,!1),this.highlight(null),i.fromPoints(this.$currentPos,this.$currentPos)},this.highlightAndFindWithNeedle=function(e,t){if(!this.$editor)return null;var n=this.$options;t&&(n.needle=t.call(this,n.needle||\"\")||\"\");if(n.needle.length===0)return this.statusMessage(!0),this.cancelSearch(!0);n.start=this.$currentPos;var r=this.$editor.session,s=this.find(r),o=this.$editor.emacsMark?!!this.$editor.emacsMark():!this.$editor.selection.isEmpty();return s&&(n.backwards&&(s=i.fromPoints(s.end,s.start)),this.$editor.selection.setRange(i.fromPoints(o?this.$startPos:s.end,s.end)),e&&(this.$currentPos=s.end),this.highlight(n.re)),this.statusMessage(s),s},this.addString=function(e){return this.highlightAndFindWithNeedle(!1,function(t){if(!l(t))return t+e;var n=c(t);return n.expression+=e,p(n)})},this.removeChar=function(e){return this.highlightAndFindWithNeedle(!1,function(e){if(!l(e))return e.substring(0,e.length-1);var t=c(e);return t.expression=t.expression.substring(0,t.expression.length-1),p(t)})},this.next=function(e){return e=e||{},this.$options.backwards=!!e.backwards,this.$currentPos=this.$editor.getCursorPosition(),this.highlightAndFindWithNeedle(!0,function(t){return e.useCurrentOrPrevSearch&&t.length===0?this.$prevNeedle||\"\":t})},this.onMouseDown=function(e){return this.deactivate(),!0},this.onPaste=function(e){this.addString(e)},this.convertNeedleToRegExp=function(){return this.highlightAndFindWithNeedle(!1,function(e){return l(e)?e:h(e,\"ig\")})},this.convertNeedleToString=function(){return this.highlightAndFindWithNeedle(!1,function(e){return l(e)?c(e).expression:e})},this.statusMessage=function(e){var t=this.$options,n=\"\";n+=t.backwards?\"reverse-\":\"\",n+=\"isearch: \"+t.needle,n+=e?\"\":\" (not found)\",this.message(n)},this.message=function(e){this.$editor.showCommandLine?(this.$editor.showCommandLine(e),this.$editor.focus()):console.log(e)}}.call(f.prototype),t.IncrementalSearch=f;var d=e(\"./lib/dom\");d.importCssString&&d.importCssString(\".ace_marker-layer .ace_isearch-result {  position: absolute;  z-index: 6;  -moz-box-sizing: border-box;  -webkit-box-sizing: border-box;  box-sizing: border-box;}div.ace_isearch-result {  border-radius: 4px;  background-color: rgba(255, 200, 0, 0.5);  box-shadow: 0 0 4px rgb(255, 200, 0);}.ace_dark div.ace_isearch-result {  background-color: rgb(100, 110, 160);  box-shadow: 0 0 4px rgb(80, 90, 140);}\",\"incremental-search-highlighting\");var v=e(\"./commands/command_manager\");(function(){this.setupIncrementalSearch=function(e,t){if(this.usesIncrementalSearch==t)return;this.usesIncrementalSearch=t;var n=u.iSearchStartCommands,r=t?\"addCommands\":\"removeCommands\";this[r](n)}}).call(v.CommandManager.prototype);var m=e(\"./editor\").Editor;e(\"./config\").defineOptions(m.prototype,\"editor\",{useIncrementalSearch:{set:function(e){this.keyBinding.$handlers.forEach(function(t){t.setupIncrementalSearch&&t.setupIncrementalSearch(this,e)}),this._emit(\"incrementalSearchSettingChanged\",{isEnabled:e})}}})}),define(\"ace/keyboard/emacs\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\",\"ace/incremental_search\",\"ace/commands/incremental_search_commands\",\"ace/keyboard/hash_handler\",\"ace/lib/keys\"],function(e,t,n){\"use strict\";var r=e(\"../lib/dom\");e(\"../incremental_search\");var i=e(\"../commands/incremental_search_commands\"),s=function(e,t){var n=this.scroller.getBoundingClientRect(),r=Math.floor((e+this.scrollLeft-n.left-this.$padding)/this.characterWidth),i=Math.floor((t+this.scrollTop-n.top)/this.lineHeight);return this.session.screenToDocumentPosition(i,r)},o=e(\"./hash_handler\").HashHandler;t.handler=new o,t.handler.isEmacs=!0,t.handler.$id=\"ace/keyboard/emacs\";var u=!1,a,f;t.handler.attach=function(e){u||(u=!0,r.importCssString(\"            .emacs-mode .ace_cursor{                border: 1px rgba(50,250,50,0.8) solid!important;                -moz-box-sizing: border-box!important;                -webkit-box-sizing: border-box!important;                box-sizing: border-box!important;                background-color: rgba(0,250,0,0.9);                opacity: 0.5;            }            .emacs-mode .ace_hidden-cursors .ace_cursor{                opacity: 1;                background-color: transparent;            }            .emacs-mode .ace_overwrite-cursors .ace_cursor {                opacity: 1;                background-color: transparent;                border-width: 0 0 2px 2px !important;            }            .emacs-mode .ace_text-layer {                z-index: 4            }            .emacs-mode .ace_cursor-layer {                z-index: 2            }\",\"emacsMode\")),a=e.session.$selectLongWords,e.session.$selectLongWords=!0,f=e.session.$useEmacsStyleLineStart,e.session.$useEmacsStyleLineStart=!0,e.session.$emacsMark=null,e.session.$emacsMarkRing=e.session.$emacsMarkRing||[],e.emacsMark=function(){return this.session.$emacsMark},e.setEmacsMark=function(e){this.session.$emacsMark=e},e.pushEmacsMark=function(e,t){var n=this.session.$emacsMark;n&&this.session.$emacsMarkRing.push(n),!e||t?this.setEmacsMark(e):this.session.$emacsMarkRing.push(e)},e.popEmacsMark=function(){var e=this.emacsMark();return e?(this.setEmacsMark(null),e):this.session.$emacsMarkRing.pop()},e.getLastEmacsMark=function(e){return this.session.$emacsMark||this.session.$emacsMarkRing.slice(-1)[0]},e.emacsMarkForSelection=function(e){var t=this.selection,n=this.multiSelect?this.multiSelect.getAllRanges().length:1,r=t.index||0,i=this.session.$emacsMarkRing,s=i.length-(n-r),o=i[s]||t.anchor;return e&&i.splice(s,1,\"row\"in e&&\"column\"in e?e:undefined),o},e.on(\"click\",c),e.on(\"changeSession\",l),e.renderer.screenToTextCoordinates=s,e.setStyle(\"emacs-mode\"),e.commands.addCommands(v),t.handler.platform=e.commands.platform,e.$emacsModeHandler=this,e.addEventListener(\"copy\",this.onCopy),e.addEventListener(\"paste\",this.onPaste)},t.handler.detach=function(e){delete e.renderer.screenToTextCoordinates,e.session.$selectLongWords=a,e.session.$useEmacsStyleLineStart=f,e.removeEventListener(\"click\",c),e.removeEventListener(\"changeSession\",l),e.unsetStyle(\"emacs-mode\"),e.commands.removeCommands(v),e.removeEventListener(\"copy\",this.onCopy),e.removeEventListener(\"paste\",this.onPaste),e.$emacsModeHandler=null};var l=function(e){e.oldSession&&(e.oldSession.$selectLongWords=a,e.oldSession.$useEmacsStyleLineStart=f),a=e.session.$selectLongWords,e.session.$selectLongWords=!0,f=e.session.$useEmacsStyleLineStart,e.session.$useEmacsStyleLineStart=!0,e.session.hasOwnProperty(\"$emacsMark\")||(e.session.$emacsMark=null),e.session.hasOwnProperty(\"$emacsMarkRing\")||(e.session.$emacsMarkRing=[])},c=function(e){e.editor.session.$emacsMark=null},h=e(\"../lib/keys\").KEY_MODS,p={C:\"ctrl\",S:\"shift\",M:\"alt\",CMD:\"command\"},d=[\"C-S-M-CMD\",\"S-M-CMD\",\"C-M-CMD\",\"C-S-CMD\",\"C-S-M\",\"M-CMD\",\"S-CMD\",\"S-M\",\"C-CMD\",\"C-M\",\"C-S\",\"CMD\",\"M\",\"S\",\"C\"];d.forEach(function(e){var t=0;e.split(\"-\").forEach(function(e){t|=h[p[e]]}),p[t]=e.toLowerCase()+\"-\"}),t.handler.onCopy=function(e,n){if(n.$handlesEmacsOnCopy)return;n.$handlesEmacsOnCopy=!0,t.handler.commands.killRingSave.exec(n),n.$handlesEmacsOnCopy=!1},t.handler.onPaste=function(e,t){t.pushEmacsMark(t.getCursorPosition())},t.handler.bindKey=function(e,t){typeof e==\"object\"&&(e=e[this.platform]);if(!e)return;var n=this.commandKeyBinding;e.split(\"|\").forEach(function(e){e=e.toLowerCase(),n[e]=t;var r=e.split(\" \").slice(0,-1);r.reduce(function(e,t,n){var r=e[n-1]?e[n-1]+\" \":\"\";return e.concat([r+t])},[]).forEach(function(e){n[e]||(n[e]=\"null\")})},this)},t.handler.getStatusText=function(e,t){var n=\"\";return t.count&&(n+=t.count),t.keyChain&&(n+=\" \"+t.keyChain),n},t.handler.handleKeyboard=function(e,t,n,r){if(r===-1)return undefined;var i=e.editor;i._signal(\"changeStatus\");if(t==-1){i.pushEmacsMark();if(e.count){var s=(new Array(e.count+1)).join(n);return e.count=null,{command:\"insertstring\",args:s}}}var o=p[t];if(o==\"c-\"||e.count){var u=parseInt(n[n.length-1]);if(typeof u==\"number\"&&!isNaN(u))return e.count=Math.max(e.count,0)||0,e.count=10*e.count+u,{command:\"null\"}}o&&(n=o+n),e.keyChain&&(n=e.keyChain+=\" \"+n);var a=this.commandKeyBinding[n];e.keyChain=a==\"null\"?n:\"\";if(!a)return undefined;if(a===\"null\")return{command:\"null\"};if(a===\"universalArgument\")return e.count=-4,{command:\"null\"};var f;typeof a!=\"string\"&&(f=a.args,a.command&&(a=a.command),a===\"goorselect\"&&(a=i.emacsMark()?f[1]:f[0],f=null));if(typeof a==\"string\"){(a===\"insertstring\"||a===\"splitline\"||a===\"togglecomment\")&&i.pushEmacsMark(),a=this.commands[a]||i.commands.commands[a];if(!a)return undefined}!a.readOnly&&!a.isYank&&(e.lastCommand=null),!a.readOnly&&i.emacsMark()&&i.setEmacsMark(null);if(e.count){var u=e.count;e.count=0;if(!a||!a.handlesCount)return{args:f,command:{exec:function(e,t){for(var n=0;n<u;n++)a.exec(e,t)},multiSelectAction:a.multiSelectAction}};f||(f={}),typeof f==\"object\"&&(f.count=u)}return{command:a,args:f}},t.emacsKeys={\"Up|C-p\":{command:\"goorselect\",args:[\"golineup\",\"selectup\"]},\"Down|C-n\":{command:\"goorselect\",args:[\"golinedown\",\"selectdown\"]},\"Left|C-b\":{command:\"goorselect\",args:[\"gotoleft\",\"selectleft\"]},\"Right|C-f\":{command:\"goorselect\",args:[\"gotoright\",\"selectright\"]},\"C-Left|M-b\":{command:\"goorselect\",args:[\"gotowordleft\",\"selectwordleft\"]},\"C-Right|M-f\":{command:\"goorselect\",args:[\"gotowordright\",\"selectwordright\"]},\"Home|C-a\":{command:\"goorselect\",args:[\"gotolinestart\",\"selecttolinestart\"]},\"End|C-e\":{command:\"goorselect\",args:[\"gotolineend\",\"selecttolineend\"]},\"C-Home|S-M-,\":{command:\"goorselect\",args:[\"gotostart\",\"selecttostart\"]},\"C-End|S-M-.\":{command:\"goorselect\",args:[\"gotoend\",\"selecttoend\"]},\"S-Up|S-C-p\":\"selectup\",\"S-Down|S-C-n\":\"selectdown\",\"S-Left|S-C-b\":\"selectleft\",\"S-Right|S-C-f\":\"selectright\",\"S-C-Left|S-M-b\":\"selectwordleft\",\"S-C-Right|S-M-f\":\"selectwordright\",\"S-Home|S-C-a\":\"selecttolinestart\",\"S-End|S-C-e\":\"selecttolineend\",\"S-C-Home\":\"selecttostart\",\"S-C-End\":\"selecttoend\",\"C-l\":\"recenterTopBottom\",\"M-s\":\"centerselection\",\"M-g\":\"gotoline\",\"C-x C-p\":\"selectall\",\"C-Down\":{command:\"goorselect\",args:[\"gotopagedown\",\"selectpagedown\"]},\"C-Up\":{command:\"goorselect\",args:[\"gotopageup\",\"selectpageup\"]},\"PageDown|C-v\":{command:\"goorselect\",args:[\"gotopagedown\",\"selectpagedown\"]},\"PageUp|M-v\":{command:\"goorselect\",args:[\"gotopageup\",\"selectpageup\"]},\"S-C-Down\":\"selectpagedown\",\"S-C-Up\":\"selectpageup\",\"C-s\":\"iSearch\",\"C-r\":\"iSearchBackwards\",\"M-C-s\":\"findnext\",\"M-C-r\":\"findprevious\",\"S-M-5\":\"replace\",Backspace:\"backspace\",\"Delete|C-d\":\"del\",\"Return|C-m\":{command:\"insertstring\",args:\"\\n\"},\"C-o\":\"splitline\",\"M-d|C-Delete\":{command:\"killWord\",args:\"right\"},\"C-Backspace|M-Backspace|M-Delete\":{command:\"killWord\",args:\"left\"},\"C-k\":\"killLine\",\"C-y|S-Delete\":\"yank\",\"M-y\":\"yankRotate\",\"C-g\":\"keyboardQuit\",\"C-w|C-S-W\":\"killRegion\",\"M-w\":\"killRingSave\",\"C-Space\":\"setMark\",\"C-x C-x\":\"exchangePointAndMark\",\"C-t\":\"transposeletters\",\"M-u\":\"touppercase\",\"M-l\":\"tolowercase\",\"M-/\":\"autocomplete\",\"C-u\":\"universalArgument\",\"M-;\":\"togglecomment\",\"C-/|C-x u|S-C--|C-z\":\"undo\",\"S-C-/|S-C-x u|C--|S-C-z\":\"redo\",\"C-x r\":\"selectRectangularRegion\",\"M-x\":{command:\"focusCommandLine\",args:\"M-x \"}},t.handler.bindKeys(t.emacsKeys),t.handler.addCommands({recenterTopBottom:function(e){var t=e.renderer,n=t.$cursorLayer.getPixelPosition(),r=t.$size.scrollerHeight-t.lineHeight,i=t.scrollTop;Math.abs(n.top-i)<2?i=n.top-r:Math.abs(n.top-i-r*.5)<2?i=n.top:i=n.top-r*.5,e.session.setScrollTop(i)},selectRectangularRegion:function(e){e.multiSelect.toggleBlockSelection()},setMark:{exec:function(e,t){function u(){var t=e.popEmacsMark();t&&e.moveCursorToPosition(t)}if(t&&t.count){e.inMultiSelectMode?e.forEachSelection(u):u(),u();return}var n=e.emacsMark(),r=e.selection.getAllRanges(),i=r.map(function(e){return{row:e.start.row,column:e.start.column}}),s=!0,o=r.every(function(e){return e.isEmpty()});if(s&&(n||!o)){e.inMultiSelectMode?e.forEachSelection({exec:e.clearSelection.bind(e)}):e.clearSelection(),n&&e.pushEmacsMark(null);return}if(!n){i.forEach(function(t){e.pushEmacsMark(t)}),e.setEmacsMark(i[i.length-1]);return}},readOnly:!0,handlesCount:!0},exchangePointAndMark:{exec:function(t,n){var r=t.selection;if(!n.count&&!r.isEmpty()){r.setSelectionRange(r.getRange(),!r.isBackwards());return}if(n.count){var i={row:r.lead.row,column:r.lead.column};r.clearSelection(),r.moveCursorToPosition(t.emacsMarkForSelection(i))}else r.selectToPosition(t.emacsMarkForSelection())},readOnly:!0,handlesCount:!0,multiSelectAction:\"forEach\"},killWord:{exec:function(e,n){e.clearSelection(),n==\"left\"?e.selection.selectWordLeft():e.selection.selectWordRight();var r=e.getSelectionRange(),i=e.session.getTextRange(r);t.killRing.add(i),e.session.remove(r),e.clearSelection()},multiSelectAction:\"forEach\"},killLine:function(e){e.pushEmacsMark(null),e.clearSelection();var n=e.getSelectionRange(),r=e.session.getLine(n.start.row);n.end.column=r.length,r=r.substr(n.start.column);var i=e.session.getFoldLine(n.start.row);i&&n.end.row!=i.end.row&&(n.end.row=i.end.row,r=\"x\"),/^\\s*$/.test(r)&&(n.end.row++,r=e.session.getLine(n.end.row),n.end.column=/^\\s*$/.test(r)?r.length:0);var s=e.session.getTextRange(n);e.prevOp.command==this?t.killRing.append(s):t.killRing.add(s),e.session.remove(n),e.clearSelection()},yank:function(e){e.onPaste(t.killRing.get()||\"\"),e.keyBinding.$data.lastCommand=\"yank\"},yankRotate:function(e){if(e.keyBinding.$data.lastCommand!=\"yank\")return;e.undo(),e.session.$emacsMarkRing.pop(),e.onPaste(t.killRing.rotate()),e.keyBinding.$data.lastCommand=\"yank\"},killRegion:{exec:function(e){t.killRing.add(e.getCopyText()),e.commands.byName.cut.exec(e),e.setEmacsMark(null)},readOnly:!0,multiSelectAction:\"forEach\"},killRingSave:{exec:function(e){e.$handlesEmacsOnCopy=!0;var n=e.session.$emacsMarkRing.slice(),r=[];t.killRing.add(e.getCopyText()),setTimeout(function(){function t(){var t=e.selection,n=t.getRange(),i=t.isBackwards()?n.end:n.start;r.push({row:i.row,column:i.column}),t.clearSelection()}e.$handlesEmacsOnCopy=!1,e.inMultiSelectMode?e.forEachSelection({exec:t}):t(),e.session.$emacsMarkRing=n.concat(r.reverse())},0)},readOnly:!0},keyboardQuit:function(e){e.selection.clearSelection(),e.setEmacsMark(null),e.keyBinding.$data.count=null},focusCommandLine:function(e,t){e.showCommandLine&&e.showCommandLine(t)}}),t.handler.addCommands(i.iSearchStartCommands);var v=t.handler.commands;v.yank.isYank=!0,v.yankRotate.isYank=!0,t.killRing={$data:[],add:function(e){e&&this.$data.push(e),this.$data.length>30&&this.$data.shift()},append:function(e){var t=this.$data.length-1,n=this.$data[t]||\"\";e&&(n+=e),n&&(this.$data[t]=n)},get:function(e){return e=e||1,this.$data.slice(this.$data.length-e,this.$data.length).reverse().join(\"\\n\")},pop:function(){return this.$data.length>1&&this.$data.pop(),this.get()},rotate:function(){return this.$data.unshift(this.$data.pop()),this.get()}}})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/keybinding-vim.js",
    "content": "define(\"ace/keyboard/vim\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/lib/event_emitter\",\"ace/lib/dom\",\"ace/lib/oop\",\"ace/lib/keys\",\"ace/lib/event\",\"ace/search\",\"ace/lib/useragent\",\"ace/search_highlight\",\"ace/commands/multi_select_commands\",\"ace/mode/text\",\"ace/multi_select\"],function(e,t,n){\"use strict\";function r(){function t(e){return typeof e!=\"object\"?e+\"\":\"line\"in e?e.line+\":\"+e.ch:\"anchor\"in e?t(e.anchor)+\"->\"+t(e.head):Array.isArray(e)?\"[\"+e.map(function(e){return t(e)})+\"]\":JSON.stringify(e)}var e=\"\";for(var n=0;n<arguments.length;n++){var r=arguments[n],i=t(r);e+=i+\"  \"}console.log(e)}function m(e){return{row:e.line,column:e.ch}}function g(e){return new E(e.row,e.column)}function x(e){e.setOption(\"disableInput\",!0),e.setOption(\"showCursorWhenSelecting\",!1),v.signal(e,\"vim-mode-change\",{mode:\"normal\"}),e.on(\"cursorActivity\",Jn),tt(e),v.on(e.getInputField(),\"paste\",M(e))}function T(e){e.setOption(\"disableInput\",!1),e.off(\"cursorActivity\",Jn),v.off(e.getInputField(),\"paste\",M(e)),e.state.vim=null}function N(e,t){this==v.keyMap.vim&&v.rmClass(e.getWrapperElement(),\"cm-fat-cursor\"),(!t||t.attach!=C)&&T(e,!1)}function C(e,t){this==v.keyMap.vim&&v.addClass(e.getWrapperElement(),\"cm-fat-cursor\"),(!t||t.attach!=C)&&x(e)}function k(e,t){if(!t)return undefined;var n=O(e);if(!n)return!1;var r=v.Vim.findKey(t,n);return typeof r==\"function\"&&v.signal(t,\"vim-keypress\",n),r}function O(e){if(e.charAt(0)==\"'\")return e.charAt(1);var t=e.split(/-(?!$)/),n=t[t.length-1];if(t.length==1&&t[0].length==1)return!1;if(t.length==2&&t[0]==\"Shift\"&&n.length==1)return!1;var r=!1;for(var i=0;i<t.length;i++){var s=t[i];s in L?t[i]=L[s]:r=!0,s in A&&(t[i]=A[s])}return r?(X(n)&&(t[t.length-1]=n.toLowerCase()),\"<\"+t.join(\"-\")+\">\"):!1}function M(e){var t=e.state.vim;return t.onPasteFn||(t.onPasteFn=function(){t.insertMode||(e.setCursor(St(e.getCursor(),0,1)),yt.enterInsertMode(e,{},t))}),t.onPasteFn}function H(e,t){var n=[];for(var r=e;r<e+t;r++)n.push(String.fromCharCode(r));return n}function R(e,t){return t>=e.firstLine()&&t<=e.lastLine()}function U(e){return/^[a-z]$/.test(e)}function z(e){return\"()[]{}\".indexOf(e)!=-1}function W(e){return _.test(e)}function X(e){return/^[A-Z]$/.test(e)}function V(e){return/^\\s*$/.test(e)}function $(e,t){for(var n=0;n<t.length;n++)if(t[n]==e)return!0;return!1}function K(e,t,n,r,i){if(t===undefined&&!i)throw Error(\"defaultValue is required unless callback is provided\");n||(n=\"string\"),J[e]={type:n,defaultValue:t,callback:i};if(r)for(var s=0;s<r.length;s++)J[r[s]]=J[e];t&&Q(e,t)}function Q(e,t,n,r){var i=J[e];r=r||{};var s=r.scope;if(!i)throw Error(\"Unknown option: \"+e);if(i.type==\"boolean\"){if(t&&t!==!0)throw Error(\"Invalid argument: \"+e+\"=\"+t);t!==!1&&(t=!0)}i.callback?(s!==\"local\"&&i.callback(t,undefined),s!==\"global\"&&n&&i.callback(t,n)):(s!==\"local\"&&(i.value=i.type==\"boolean\"?!!t:t),s!==\"global\"&&n&&(n.state.vim.options[e]={value:t}))}function G(e,t,n){var r=J[e];n=n||{};var i=n.scope;if(!r)throw Error(\"Unknown option: \"+e);if(r.callback){var s=t&&r.callback(undefined,t);if(i!==\"global\"&&s!==undefined)return s;if(i!==\"local\")return r.callback();return}var s=i!==\"global\"&&t&&t.state.vim.options[e];return(s||i!==\"local\"&&r||{}).value}function et(){this.latestRegister=undefined,this.isPlaying=!1,this.isRecording=!1,this.replaySearchQueries=[],this.onRecordingDone=undefined,this.lastInsertModeChanges=Z()}function tt(e){return e.state.vim||(e.state.vim={inputState:new ot,lastEditInputState:undefined,lastEditActionCommand:undefined,lastHPos:-1,lastHSPos:-1,lastMotion:null,marks:{},fakeCursor:null,insertMode:!1,insertModeRepeat:undefined,visualMode:!1,visualLine:!1,visualBlock:!1,lastSelection:null,lastPastedText:null,sel:{},options:{}}),e.state.vim}function rt(){nt={searchQuery:null,searchIsReversed:!1,lastSubstituteReplacePart:undefined,jumpList:Y(),macroModeState:new et,lastChararacterSearch:{increment:0,forward:!0,selectedCharacter:\"\"},registerController:new lt({}),searchHistoryController:new ct({}),exCommandHistoryController:new ct({})};for(var e in J){var t=J[e];t.value=t.defaultValue}}function ot(){this.prefixRepeat=[],this.motionRepeat=[],this.operator=null,this.operatorArgs=null,this.motion=null,this.motionArgs=null,this.keyBuffer=[],this.registerName=null}function ut(e,t){e.state.vim.inputState=new ot,v.signal(e,\"vim-command-done\",t)}function at(e,t,n){this.clear(),this.keyBuffer=[e||\"\"],this.insertModeChanges=[],this.searchQueries=[],this.linewise=!!t,this.blockwise=!!n}function ft(e,t){var n=nt.registerController.registers[e];if(!e||e.length!=1)throw Error(\"Register name must be 1 character\");n[e]=t,q.push(e)}function lt(e){this.registers=e,this.unnamedRegister=e['\"']=new at,e[\".\"]=new at,e[\":\"]=new at,e[\"/\"]=new at}function ct(){this.historyBuffer=[],this.iterator,this.initialPrefix=null}function dt(e,t){pt[e]=t}function vt(e,t){var n=[];for(var r=0;r<t;r++)n.push(e);return n}function gt(e,t){mt[e]=t}function bt(e,t){yt[e]=t}function wt(e,t,n){var r=Math.min(Math.max(e.firstLine(),t.line),e.lastLine()),i=Pt(e,r)-1;i=n?i+1:i;var s=Math.min(Math.max(0,t.ch),i);return E(r,s)}function Et(e){var t={};for(var n in e)e.hasOwnProperty(n)&&(t[n]=e[n]);return t}function St(e,t,n){return typeof t==\"object\"&&(n=t.ch,t=t.line),E(e.line+t,e.ch+n)}function xt(e,t){return{line:t.line-e.line,ch:t.line-e.line}}function Tt(e,t,n,r){var i,s=[],o=[];for(var u=0;u<t.length;u++){var a=t[u];if(n==\"insert\"&&a.context!=\"insert\"||a.context&&a.context!=n||r.operator&&a.type==\"action\"||!(i=Nt(e,a.keys)))continue;i==\"partial\"&&s.push(a),i==\"full\"&&o.push(a)}return{partial:s.length&&s,full:o.length&&o}}function Nt(e,t){if(t.slice(-11)==\"<character>\"){var n=t.length-11,r=e.slice(0,n),i=t.slice(0,n);return r==i&&e.length>n?\"full\":i.indexOf(r)==0?\"partial\":!1}return e==t?\"full\":t.indexOf(e)==0?\"partial\":!1}function Ct(e){var t=/^.*(<[\\w\\-]+>)$/.exec(e),n=t?t[1]:e.slice(-1);if(n.length>1)switch(n){case\"<CR>\":n=\"\\n\";break;case\"<Space>\":n=\" \";break;default:}return n}function kt(e,t,n){return function(){for(var r=0;r<n;r++)t(e)}}function Lt(e){return E(e.line,e.ch)}function At(e,t){return e.ch==t.ch&&e.line==t.line}function Ot(e,t){return e.line<t.line?!0:e.line==t.line&&e.ch<t.ch?!0:!1}function Mt(e,t){return arguments.length>2&&(t=Mt.apply(undefined,Array.prototype.slice.call(arguments,1))),Ot(e,t)?e:t}function _t(e,t){return arguments.length>2&&(t=_t.apply(undefined,Array.prototype.slice.call(arguments,1))),Ot(e,t)?t:e}function Dt(e,t,n){var r=Ot(e,t),i=Ot(t,n);return r&&i}function Pt(e,t){return e.getLine(t).length}function Ht(e){return e.trim?e.trim():e.replace(/^\\s+|\\s+$/g,\"\")}function Bt(e){return e.replace(/([.?*+$\\[\\]\\/\\\\(){}|\\-])/g,\"\\\\$1\")}function jt(e,t,n){var r=Pt(e,t),i=(new Array(n-r+1)).join(\" \");e.setCursor(E(t,r)),e.replaceRange(i,e.getCursor())}function Ft(e,t){var n=[],r=e.listSelections(),i=Lt(e.clipPos(t)),s=!At(t,i),o=e.getCursor(\"head\"),u=qt(r,o),a=At(r[u].head,r[u].anchor),f=r.length-1,l=f-u>u?f:0,c=r[l].anchor,h=Math.min(c.line,i.line),p=Math.max(c.line,i.line),d=c.ch,v=i.ch,m=r[l].head.ch-d,g=v-d;m>0&&g<=0?(d++,s||v--):m<0&&g>=0?(d--,a||v++):m<0&&g==-1&&(d--,v++);for(var y=h;y<=p;y++){var b={anchor:new E(y,d),head:new E(y,v)};n.push(b)}return u=i.line==p?n.length-1:0,e.setSelections(n),t.ch=v,c.ch=d,c}function It(e,t,n){var r=[];for(var i=0;i<n;i++){var s=St(t,i,0);r.push({anchor:s,head:s})}e.setSelections(r,0)}function qt(e,t,n){for(var r=0;r<e.length;r++){var i=n!=\"head\"&&At(e[r].anchor,t),s=n!=\"anchor\"&&At(e[r].head,t);if(i||s)return r}return-1}function Rt(e,t){var n=t.lastSelection,r=function(){var t=e.listSelections(),n=t[0],r=t[t.length-1],i=Ot(n.anchor,n.head)?n.anchor:n.head,s=Ot(r.anchor,r.head)?r.head:r.anchor;return[i,s]},i=function(){var t=e.getCursor(),r=e.getCursor(),i=n.visualBlock;if(i){var s=i.width,o=i.height;r=E(t.line+o,t.ch+s);var u=[];for(var a=t.line;a<r.line;a++){var f=E(a,t.ch),l=E(a,r.ch),c={anchor:f,head:l};u.push(c)}e.setSelections(u)}else{var h=n.anchorMark.find(),p=n.headMark.find(),d=p.line-h.line,v=p.ch-h.ch;r={line:r.line+d,ch:d?r.ch:v+r.ch},n.visualLine&&(t=E(t.line,0),r=E(r.line,Pt(e,r.line))),e.setSelection(t,r)}return[t,r]};return t.visualMode?r():i()}function Ut(e,t){var n=t.sel.anchor,r=t.sel.head;t.lastPastedText&&(r=e.posFromIndex(e.indexFromPos(n)+t.lastPastedText.length),t.lastPastedText=null),t.lastSelection={anchorMark:e.setBookmark(n),headMark:e.setBookmark(r),anchor:Lt(n),head:Lt(r),visualMode:t.visualMode,visualLine:t.visualLine,visualBlock:t.visualBlock}}function zt(e,t,n){var r=e.state.vim.sel,i=r.head,s=r.anchor,o;return Ot(n,t)&&(o=n,n=t,t=o),Ot(i,s)?(i=Mt(t,i),s=_t(s,n)):(s=Mt(t,s),i=_t(i,n),i=St(i,0,-1),i.ch==-1&&i.line!=e.firstLine()&&(i=E(i.line-1,Pt(e,i.line-1)))),[s,i]}function Wt(e,t,n){var r=e.state.vim;t=t||r.sel;var n=n||r.visualLine?\"line\":r.visualBlock?\"block\":\"char\",i=Xt(e,t,n);e.setSelections(i.ranges,i.primary),Kn(e)}function Xt(e,t,n,r){var i=Lt(t.head),s=Lt(t.anchor);if(n==\"char\"){var o=!r&&!Ot(t.head,t.anchor)?1:0,u=Ot(t.head,t.anchor)?1:0;return i=St(t.head,0,o),s=St(t.anchor,0,u),{ranges:[{anchor:s,head:i}],primary:0}}if(n==\"line\"){if(!Ot(t.head,t.anchor)){s.ch=0;var a=e.lastLine();i.line>a&&(i.line=a),i.ch=Pt(e,i.line)}else i.ch=0,s.ch=Pt(e,s.line);return{ranges:[{anchor:s,head:i}],primary:0}}if(n==\"block\"){var f=Math.min(s.line,i.line),l=Math.min(s.ch,i.ch),c=Math.max(s.line,i.line),h=Math.max(s.ch,i.ch)+1,p=c-f+1,d=i.line==f?0:p-1,v=[];for(var m=0;m<p;m++)v.push({anchor:E(f+m,l),head:E(f+m,h)});return{ranges:v,primary:d}}}function Vt(e){var t=e.getCursor(\"head\");return e.getSelection().length==1&&(t=Mt(t,e.getCursor(\"anchor\"))),t}function $t(e,t){var n=e.state.vim;t!==!1&&e.setCursor(wt(e,n.sel.head)),Ut(e,n),n.visualMode=!1,n.visualLine=!1,n.visualBlock=!1,v.signal(e,\"vim-mode-change\",{mode:\"normal\"}),n.fakeCursor&&n.fakeCursor.clear()}function Jt(e,t,n){var r=e.getRange(t,n);if(/\\n\\s*$/.test(r)){var i=r.split(\"\\n\");i.pop();var s;for(var s=i.pop();i.length>0&&s&&V(s);s=i.pop())n.line--,n.ch=0;s?(n.line--,n.ch=Pt(e,n.line)):n.ch=0}}function Kt(e,t,n){t.ch=0,n.ch=0,n.line++}function Qt(e){if(!e)return 0;var t=e.search(/\\S/);return t==-1?e.length:t}function Gt(e,t,n,r,i){var s=Vt(e),o=e.getLine(s.line),u=s.ch,a=i?D[0]:P[0];while(!a(o.charAt(u))){u++;if(u>=o.length)return null}r?a=P[0]:(a=D[0],a(o.charAt(u))||(a=D[1]));var f=u,l=u;while(a(o.charAt(f))&&f<o.length)f++;while(a(o.charAt(l))&&l>=0)l--;l++;if(t){var c=f;while(/\\s/.test(o.charAt(f))&&f<o.length)f++;if(c==f){var h=l;while(/\\s/.test(o.charAt(l-1))&&l>0)l--;l||(l=h)}}return{start:E(s.line,l),end:E(s.line,f)}}function Yt(e,t,n){At(t,n)||nt.jumpList.add(e,t,n)}function Zt(e,t){nt.lastChararacterSearch.increment=e,nt.lastChararacterSearch.forward=t.forward,nt.lastChararacterSearch.selectedCharacter=t.selectedCharacter}function nn(e,t,n,r){var i=Lt(e.getCursor()),s=n?1:-1,o=n?e.lineCount():-1,u=i.ch,a=i.line,f=e.getLine(a),l={lineText:f,nextCh:f.charAt(u),lastCh:null,index:u,symb:r,reverseSymb:(n?{\")\":\"(\",\"}\":\"{\"}:{\"(\":\")\",\"{\":\"}\"})[r],forward:n,depth:0,curMoveThrough:!1},c=en[r];if(!c)return i;var h=tn[c].init,p=tn[c].isComplete;h&&h(l);while(a!==o&&t){l.index+=s,l.nextCh=l.lineText.charAt(l.index);if(!l.nextCh){a+=s,l.lineText=e.getLine(a)||\"\";if(s>0)l.index=0;else{var d=l.lineText.length;l.index=d>0?d-1:0}l.nextCh=l.lineText.charAt(l.index)}p(l)&&(i.line=a,i.ch=l.index,t--)}return l.nextCh||l.curMoveThrough?E(a,l.index):i}function rn(e,t,n,r,i){var s=t.line,o=t.ch,u=e.getLine(s),a=n?1:-1,f=r?P:D;if(i&&u==\"\"){s+=a,u=e.getLine(s);if(!R(e,s))return null;o=n?0:u.length}for(;;){if(i&&u==\"\")return{from:0,to:0,line:s};var l=a>0?u.length:-1,c=l,h=l;while(o!=l){var p=!1;for(var d=0;d<f.length&&!p;++d)if(f[d](u.charAt(o))){c=o;while(o!=l&&f[d](u.charAt(o)))o+=a;h=o,p=c!=h;if(c==t.ch&&s==t.line&&h==c+a)continue;return{from:Math.min(c,h+1),to:Math.max(c,h),line:s}}p||(o+=a)}s+=a;if(!R(e,s))return null;u=e.getLine(s),o=a>0?0:u.length}throw new Error(\"The impossible happened.\")}function sn(e,t,n,r,i,s){var o=Lt(t),u=[];(r&&!i||!r&&i)&&n++;var a=!r||!i;for(var f=0;f<n;f++){var l=rn(e,t,r,s,a);if(!l){var c=Pt(e,e.lastLine());u.push(r?{line:e.lastLine(),from:c,to:c}:{line:0,from:0,to:0});break}u.push(l),t=E(l.line,r?l.to-1:l.from)}var h=u.length!=n,p=u[0],d=u.pop();return r&&!i?(!h&&(p.from!=o.ch||p.line!=o.line)&&(d=u.pop()),E(d.line,d.from)):r&&i?E(d.line,d.to-1):!r&&i?(!h&&(p.to!=o.ch||p.line!=o.line)&&(d=u.pop()),E(d.line,d.to)):E(d.line,d.from)}function on(e,t,n,r){var i=e.getCursor(),s=i.ch,o;for(var u=0;u<t;u++){var a=e.getLine(i.line);o=fn(s,a,r,n,!0);if(o==-1)return null;s=o}return E(e.getCursor().line,o)}function un(e,t){var n=e.getCursor().line;return wt(e,E(n,t-1))}function an(e,t,n,r){if(!$(n,I))return;t.marks[n]&&t.marks[n].clear(),t.marks[n]=e.setBookmark(r)}function fn(e,t,n,r,i){var s;return r?(s=t.indexOf(n,e+1),s!=-1&&!i&&(s-=1)):(s=t.lastIndexOf(n,e-1),s!=-1&&!i&&(s+=1)),s}function ln(e,t,n,r,i){function c(t){return!/\\S/.test(e.getLine(t))}function h(e,t,n){return n?c(e)!=c(e+t):!c(e)&&c(e+t)}function p(t){r=r>0?1:-1;var n=e.ace.session.getFoldLine(t);n&&t+r>n.start.row&&t+r<n.end.row&&(r=(r>0?n.end.row:n.start.row)-t)}var s=t.line,o=e.firstLine(),u=e.lastLine(),a,f,l=s;if(r){while(o<=l&&l<=u&&n>0)p(l),h(l,r)&&n--,l+=r;return new E(l,0)}var d=e.state.vim;if(d.visualLine&&h(s,1,!0)){var v=d.sel.anchor;h(v.line,-1,!0)&&(!i||v.line!=s)&&(s+=1)}var m=c(s);for(l=s;l<=u&&n;l++)h(l,1,!0)&&(!i||c(l)!=m)&&n--;f=new E(l,0),l>u&&!m?m=!0:i=!1;for(l=s;l>o;l--)if(!i||c(l)==m||l==s)if(h(l,-1,!0))break;return a=new E(l,0),{start:a,end:f}}function cn(e,t,n,r){var i=t,s,o,u={\"(\":/[()]/,\")\":/[()]/,\"[\":/[[\\]]/,\"]\":/[[\\]]/,\"{\":/[{}]/,\"}\":/[{}]/}[n],a={\"(\":\"(\",\")\":\"(\",\"[\":\"[\",\"]\":\"[\",\"{\":\"{\",\"}\":\"{\"}[n],f=e.getLine(i.line).charAt(i.ch),l=f===a?1:0;s=e.scanForBracket(E(i.line,i.ch+l),-1,null,{bracketRegex:u}),o=e.scanForBracket(E(i.line,i.ch+l),1,null,{bracketRegex:u});if(!s||!o)return{start:i,end:i};s=s.pos,o=o.pos;if(s.line==o.line&&s.ch>o.ch||s.line>o.line){var c=s;s=o,o=c}return r?o.ch+=1:s.ch+=1,{start:s,end:o}}function hn(e,t,n,r){var i=Lt(t),s=e.getLine(i.line),o=s.split(\"\"),u,a,f,l,c=o.indexOf(n);i.ch<c?i.ch=c:c<i.ch&&o[i.ch]==n&&(a=i.ch,--i.ch);if(o[i.ch]==n&&!a)u=i.ch+1;else for(f=i.ch;f>-1&&!u;f--)o[f]==n&&(u=f+1);if(u&&!a)for(f=u,l=o.length;f<l&&!a;f++)o[f]==n&&(a=f);return!u||!a?{start:i,end:i}:(r&&(--u,++a),{start:E(i.line,u),end:E(i.line,a)})}function pn(){}function dn(e){var t=e.state.vim;return t.searchState_||(t.searchState_=new pn)}function vn(e,t,n,r,i){e.openDialog?e.openDialog(t,r,{bottom:!0,value:i.value,onKeyDown:i.onKeyDown,onKeyUp:i.onKeyUp,selectValueOnOpen:!1}):r(prompt(n,\"\"))}function mn(e){var t=gn(e)||[];if(!t.length)return[];var n=[];if(t[0]!==0)return;for(var r=0;r<t.length;r++)typeof t[r]==\"number\"&&n.push(e.substring(t[r]+1,t[r+1]));return n}function gn(e){var t=!1,n=[];for(var r=0;r<e.length;r++){var i=e.charAt(r);!t&&i==\"/\"&&n.push(r),t=!t&&i==\"\\\\\"}return n}function yn(e){var t=\"|(){\",n=\"}\",r=!1,i=[];for(var s=-1;s<e.length;s++){var o=e.charAt(s)||\"\",u=e.charAt(s+1)||\"\",a=u&&t.indexOf(u)!=-1;r?((o!==\"\\\\\"||!a)&&i.push(o),r=!1):o===\"\\\\\"?(r=!0,u&&n.indexOf(u)!=-1&&(a=!0),(!a||u===\"\\\\\")&&i.push(o)):(i.push(o),a&&u!==\"\\\\\"&&i.push(\"\\\\\"))}return i.join(\"\")}function wn(e){var t=!1,n=[];for(var r=-1;r<e.length;r++){var i=e.charAt(r)||\"\",s=e.charAt(r+1)||\"\";bn[i+s]?(n.push(bn[i+s]),r++):t?(n.push(i),t=!1):i===\"\\\\\"?(t=!0,W(s)||s===\"$\"?n.push(\"$\"):s!==\"/\"&&s!==\"\\\\\"&&n.push(\"\\\\\")):(i===\"$\"&&n.push(\"$\"),n.push(i),s===\"/\"&&n.push(\"\\\\\"))}return n.join(\"\")}function Sn(e){var t=new v.StringStream(e),n=[];while(!t.eol()){while(t.peek()&&t.peek()!=\"\\\\\")n.push(t.next());var r=!1;for(var i in En)if(t.match(i,!0)){r=!0,n.push(En[i]);break}r||n.push(t.next())}return n.join(\"\")}function xn(e,t,n){var r=nt.registerController.getRegister(\"/\");r.setText(e);if(e instanceof RegExp)return e;var i=gn(e),s,o;if(!i.length)s=e;else{s=e.substring(0,i[0]);var u=e.substring(i[0]);o=u.indexOf(\"i\")!=-1}if(!s)return null;G(\"pcre\")||(s=yn(s)),n&&(t=/^[^A-Z]*$/.test(s));var a=new RegExp(s,t||o?\"i\":undefined);return a}function Tn(e,t){e.openNotification?e.openNotification('<span style=\"color: red\">'+t+\"</span>\",{bottom:!0,duration:5e3}):alert(t)}function Nn(e,t){var n=\"\";return e&&(n+='<span style=\"font-family: monospace\">'+e+\"</span>\"),n+='<input type=\"text\"/> <span style=\"color: #888\">',t&&(n+='<span style=\"color: #888\">',n+=t,n+=\"</span>\"),n}function kn(e,t){var n=(t.prefix||\"\")+\" \"+(t.desc||\"\"),r=Nn(t.prefix,t.desc);vn(e,r,n,t.onClose,t)}function Ln(e,t){if(e instanceof RegExp&&t instanceof RegExp){var n=[\"global\",\"multiline\",\"ignoreCase\",\"source\"];for(var r=0;r<n.length;r++){var i=n[r];if(e[i]!==t[i])return!1}return!0}return!1}function An(e,t,n,r){if(!t)return;var i=dn(e),s=xn(t,!!n,!!r);if(!s)return;return Mn(e,s),Ln(s,i.getQuery())?s:(i.setQuery(s),s)}function On(e){if(e.source.charAt(0)==\"^\")var t=!0;return{token:function(n){if(t&&!n.sol()){n.skipToEnd();return}var r=n.match(e,!1);if(r){if(r[0].length==0)return n.next(),\"searching\";if(!n.sol()){n.backUp(1);if(!e.exec(n.next()+r[0]))return n.next(),null}return n.match(e),\"searching\"}while(!n.eol()){n.next();if(n.match(e,!1))break}},query:e}}function Mn(e,t){var n=dn(e),r=n.getOverlay();if(!r||t!=r.query)r&&e.removeOverlay(r),r=On(t),e.addOverlay(r),e.showMatchesOnScrollbar&&(n.getScrollbarAnnotate()&&n.getScrollbarAnnotate().clear(),n.setScrollbarAnnotate(e.showMatchesOnScrollbar(t))),n.setOverlay(r)}function _n(e,t,n,r){return r===undefined&&(r=1),e.operation(function(){var i=e.getCursor(),s=e.getSearchCursor(n,i);for(var o=0;o<r;o++){var u=s.find(t);o==0&&u&&At(s.from(),i)&&(u=s.find(t));if(!u){s=e.getSearchCursor(n,t?E(e.lastLine()):E(e.firstLine(),0));if(!s.find(t))return}}return s.from()})}function Dn(e){var t=dn(e);e.removeOverlay(dn(e).getOverlay()),t.setOverlay(null),t.getScrollbarAnnotate()&&(t.getScrollbarAnnotate().clear(),t.setScrollbarAnnotate(null))}function Pn(e,t,n){return typeof e!=\"number\"&&(e=e.line),t instanceof Array?$(e,t):n?e>=t&&e<=n:e==t}function Hn(e){var t=e.ace.renderer;return{top:t.getFirstFullyVisibleRow(),bottom:t.getLastFullyVisibleRow()}}function In(e,t,n,r,i,s,o,u,a){function c(){e.operation(function(){while(!f)h(),p();d()})}function h(){var t=e.getRange(s.from(),s.to()),n=t.replace(o,u);s.replace(n)}function p(){while(s.findNext()&&Pn(s.from(),r,i)){if(!n&&l&&s.from().line==l.line)continue;e.scrollIntoView(s.from(),30),e.setSelection(s.from(),s.to()),l=s.from(),f=!1;return}f=!0}function d(t){t&&t(),e.focus();if(l){e.setCursor(l);var n=e.state.vim;n.exMode=!1,n.lastHPos=n.lastHSPos=l.ch}a&&a()}function m(t,n,r){v.e_stop(t);var i=v.keyName(t);switch(i){case\"Y\":h(),p();break;case\"N\":p();break;case\"A\":var s=a;a=undefined,e.operation(c),a=s;break;case\"L\":h();case\"Q\":case\"Esc\":case\"Ctrl-C\":case\"Ctrl-[\":d(r)}return f&&d(r),!0}e.state.vim.exMode=!0;var f=!1,l=s.from();p();if(f){Tn(e,\"No matches for \"+o.source);return}if(!t){c(),a&&a();return}kn(e,{prefix:\"replace with <strong>\"+u+\"</strong> (y/n/a/q/l)\",onKeyDown:m})}function qn(e){var t=e.state.vim,n=nt.macroModeState,r=nt.registerController.getRegister(\".\"),i=n.isPlaying,s=n.lastInsertModeChanges,o=[];if(!i){var u=s.inVisualBlock?t.lastSelection.visualBlock.height:1,a=s.changes,o=[],f=0;while(f<a.length)o.push(a[f]),a[f]instanceof Gn?f++:f+=u;s.changes=o,e.off(\"change\",$n),v.off(e.getInputField(),\"keydown\",Yn)}!i&&t.insertModeRepeat>1&&(Zn(e,t,t.insertModeRepeat-1,!0),t.lastEditInputState.repeatOverride=t.insertModeRepeat),delete t.insertModeRepeat,t.insertMode=!1,e.setCursor(e.getCursor().line,e.getCursor().ch-1),e.setOption(\"keyMap\",\"vim\"),e.setOption(\"disableInput\",!0),e.toggleOverwrite(!1),r.setText(s.changes.join(\"\")),v.signal(e,\"vim-mode-change\",{mode:\"normal\"}),n.isRecording&&Xn(n)}function Rn(e){b.unshift(e)}function Un(e,t,n,r,i){var s={keys:e,type:t};s[t]=n,s[t+\"Args\"]=r;for(var o in i)s[o]=i[o];Rn(s)}function zn(e,t,n,r){var i=nt.registerController.getRegister(r);if(r==\":\"){i.keyBuffer[0]&&Fn.processCommand(e,i.keyBuffer[0]),n.isPlaying=!1;return}var s=i.keyBuffer,o=0;n.isPlaying=!0,n.replaySearchQueries=i.searchQueries.slice(0);for(var u=0;u<s.length;u++){var a=s[u],f,l;while(a){f=/<\\w+-.+?>|<\\w+>|./.exec(a),l=f[0],a=a.substring(f.index+l.length),v.Vim.handleKey(e,l,\"macro\");if(t.insertMode){var c=i.insertModeChanges[o++].changes;nt.macroModeState.lastInsertModeChanges.changes=c,er(e,c,1),qn(e)}}}n.isPlaying=!1}function Wn(e,t){if(e.isPlaying)return;var n=e.latestRegister,r=nt.registerController.getRegister(n);r&&r.pushText(t)}function Xn(e){if(e.isPlaying)return;var t=e.latestRegister,n=nt.registerController.getRegister(t);n&&n.pushInsertModeChanges&&n.pushInsertModeChanges(e.lastInsertModeChanges)}function Vn(e,t){if(e.isPlaying)return;var n=e.latestRegister,r=nt.registerController.getRegister(n);r&&r.pushSearchQuery&&r.pushSearchQuery(t)}function $n(e,t){var n=nt.macroModeState,r=n.lastInsertModeChanges;if(!n.isPlaying)while(t){r.expectCursorActivityForChange=!0;if(t.origin==\"+input\"||t.origin==\"paste\"||t.origin===undefined){var i=t.text.join(\"\\n\");r.maybeReset&&(r.changes=[],r.maybeReset=!1),r.changes.push(i)}t=t.next}}function Jn(e){var t=e.state.vim;if(t.insertMode){var n=nt.macroModeState;if(n.isPlaying)return;var r=n.lastInsertModeChanges;r.expectCursorActivityForChange?r.expectCursorActivityForChange=!1:r.maybeReset=!0}else e.curOp.isVimOp||Qn(e,t);t.visualMode&&Kn(e)}function Kn(e){var t=e.state.vim,n=wt(e,Lt(t.sel.head)),r=St(n,0,1);t.fakeCursor&&t.fakeCursor.clear(),t.fakeCursor=e.markText(n,r,{className:\"cm-animate-fat-cursor\"})}function Qn(e,t){var n=e.getCursor(\"anchor\"),r=e.getCursor(\"head\");t.visualMode&&!e.somethingSelected()?$t(e,!1):!t.visualMode&&!t.insertMode&&e.somethingSelected()&&(t.visualMode=!0,t.visualLine=!1,v.signal(e,\"vim-mode-change\",{mode:\"visual\"}));if(t.visualMode){var i=Ot(r,n)?0:-1,s=Ot(r,n)?-1:0;r=St(r,0,i),n=St(n,0,s),t.sel={anchor:n,head:r},an(e,t,\"<\",Mt(r,n)),an(e,t,\">\",_t(r,n))}else t.insertMode||(t.lastHPos=e.getCursor().ch)}function Gn(e){this.keyName=e}function Yn(e){function i(){return n.maybeReset&&(n.changes=[],n.maybeReset=!1),n.changes.push(new Gn(r)),!0}var t=nt.macroModeState,n=t.lastInsertModeChanges,r=v.keyName(e);if(!r)return;(r.indexOf(\"Delete\")!=-1||r.indexOf(\"Backspace\")!=-1)&&v.lookupKey(r,\"vim-insert\",i)}function Zn(e,t,n,r){function u(){s?ht.processAction(e,t,t.lastEditActionCommand):ht.evalInput(e,t)}function a(n){if(i.lastInsertModeChanges.changes.length>0){n=t.lastEditActionCommand?n:1;var r=i.lastInsertModeChanges;er(e,r.changes,n)}}var i=nt.macroModeState;i.isPlaying=!0;var s=!!t.lastEditActionCommand,o=t.inputState;t.inputState=t.lastEditInputState;if(s&&t.lastEditActionCommand.interlaceInsertRepeat)for(var f=0;f<n;f++)u(),a(1);else r||u(),a(n);t.inputState=o,t.insertMode&&!r&&qn(e),i.isPlaying=!1}function er(e,t,n){function r(t){return typeof t==\"string\"?v.commands[t](e):t(e),!0}var i=e.getCursor(\"head\"),s=nt.macroModeState.lastInsertModeChanges.inVisualBlock;if(s){var o=e.state.vim,u=o.lastSelection,a=xt(u.anchor,u.head);It(e,i,a.line+1),n=e.listSelections().length,e.setCursor(i)}for(var f=0;f<n;f++){s&&e.setCursor(St(i,f,0));for(var l=0;l<t.length;l++){var c=t[l];if(c instanceof Gn)v.lookupKey(c.keyName,\"vim-insert\",r);else{var h=e.getCursor();e.replaceRange(c,h,h)}}}s&&e.setCursor(St(i,0,1))}function nr(e,t,n){t.length>1&&t[0]==\"n\"&&(t=t.replace(\"numpad\",\"\")),t=tr[t]||t;var r=\"\";return n.ctrlKey&&(r+=\"C-\"),n.altKey&&(r+=\"A-\"),n.shiftKey&&(r+=\"S-\"),r+=t,r.length>1&&(r=\"<\"+r+\">\"),r}function ir(e){var t=new e.constructor;return Object.keys(e).forEach(function(n){var r=e[n];Array.isArray(r)?r=r.slice():r&&typeof r==\"object\"&&r.constructor!=Object&&(r=ir(r)),t[n]=r}),e.sel&&(t.sel={head:e.sel.head&&Lt(e.sel.head),anchor:e.sel.anchor&&Lt(e.sel.anchor)}),t}function sr(e,t,n){var r=!1,i=S.maybeInitVimState_(e),s=i.visualBlock||i.wasInVisualBlock;i.wasInVisualBlock&&!e.ace.inMultiSelectMode?i.wasInVisualBlock=!1:e.ace.inMultiSelectMode&&i.visualBlock&&(i.wasInVisualBlock=!0);if(t==\"<Esc>\"&&!i.insertMode&&!i.visualMode&&e.ace.inMultiSelectMode)e.ace.exitMultiSelectMode();else if(s||!e.ace.inMultiSelectMode||e.ace.inVirtualSelectionMode)r=S.handleKey(e,t,n);else{var o=ir(i);e.operation(function(){e.ace.forEachSelection(function(){var i=e.ace.selection;e.state.vim.lastHPos=i.$desiredColumn==null?i.lead.column:i.$desiredColumn;var s=e.getCursor(\"head\"),u=e.getCursor(\"anchor\"),a=Ot(s,u)?0:-1,f=Ot(s,u)?-1:0;s=St(s,0,a),u=St(u,0,f),e.state.vim.sel.head=s,e.state.vim.sel.anchor=u,r=rr(e,t,n),i.$desiredColumn=e.state.vim.lastHPos==-1?null:e.state.vim.lastHPos,e.virtualSelectionMode()&&(e.state.vim=ir(o))}),e.curOp.cursorActivity&&!r&&(e.curOp.cursorActivity=!1)},!0)}return r}function ar(e,t){t.off(\"beforeEndOperation\",ar);var n=t.state.cm.vimCmd;n&&t.execCommand(n.exec?n:n.name,n.args),t.curOp=t.prevOp}var i=e(\"../range\").Range,s=e(\"../lib/event_emitter\").EventEmitter,o=e(\"../lib/dom\"),u=e(\"../lib/oop\"),a=e(\"../lib/keys\"),f=e(\"../lib/event\"),l=e(\"../search\").Search,c=e(\"../lib/useragent\"),h=e(\"../search_highlight\").SearchHighlight,p=e(\"../commands/multi_select_commands\"),d=e(\"../mode/text\").Mode.prototype.tokenRe;e(\"../multi_select\");var v=function(e){this.ace=e,this.state={},this.marks={},this.$uid=0,this.onChange=this.onChange.bind(this),this.onSelectionChange=this.onSelectionChange.bind(this),this.onBeforeEndOperation=this.onBeforeEndOperation.bind(this),this.ace.on(\"change\",this.onChange),this.ace.on(\"changeSelection\",this.onSelectionChange),this.ace.on(\"beforeEndOperation\",this.onBeforeEndOperation)};v.Pos=function(e,t){if(!(this instanceof E))return new E(e,t);this.line=e,this.ch=t},v.defineOption=function(e,t,n){},v.commands={redo:function(e){e.ace.redo()},undo:function(e){e.ace.undo()},newlineAndIndent:function(e){e.ace.insert(\"\\n\")}},v.keyMap={},v.addClass=v.rmClass=v.e_stop=function(){},v.keyName=function(e){if(e.key)return e.key;var t=a[e.keyCode]||\"\";return t.length==1&&(t=t.toUpperCase()),t=f.getModifierString(e).replace(/(^|-)\\w/g,function(e){return e.toUpperCase()})+t,t},v.keyMap[\"default\"]=function(e){return function(t){var n=t.ace.commands.commandKeyBinding[e.toLowerCase()];return n&&t.ace.execCommand(n)!==!1}},v.lookupKey=function fr(e,t,n){typeof t==\"string\"&&(t=v.keyMap[t]);var r=typeof t==\"function\"?t(e):t[e];if(r===!1)return\"nothing\";if(r===\"...\")return\"multi\";if(r!=null&&n(r))return\"handled\";if(t.fallthrough){if(!Array.isArray(t.fallthrough))return fr(e,t.fallthrough,n);for(var i=0;i<t.fallthrough.length;i++){var s=fr(e,t.fallthrough[i],n);if(s)return s}}},v.signal=function(e,t,n){return e._signal(t,n)},v.on=f.addListener,v.off=f.removeListener,v.isWordChar=function(e){return e<\"\"?/^\\w$/.test(e):(d.lastIndex=0,d.test(e))},function(){u.implement(v.prototype,s),this.destroy=function(){this.ace.off(\"change\",this.onChange),this.ace.off(\"changeSelection\",this.onSelectionChange),this.ace.off(\"beforeEndOperation\",this.onBeforeEndOperation),this.removeOverlay()},this.virtualSelectionMode=function(){return this.ace.inVirtualSelectionMode&&this.ace.selection.index},this.onChange=function(e){var t={text:e.action[0]==\"i\"?e.lines:[]},n=this.curOp=this.curOp||{};n.changeHandlers||(n.changeHandlers=this._eventRegistry.change&&this._eventRegistry.change.slice());if(this.virtualSelectionMode())return;n.lastChange?n.lastChange.next=n.lastChange=t:n.lastChange=n.change=t,this.$updateMarkers(e)},this.onSelectionChange=function(){var e=this.curOp=this.curOp||{};e.cursorActivityHandlers||(e.cursorActivityHandlers=this._eventRegistry.cursorActivity&&this._eventRegistry.cursorActivity.slice()),this.curOp.cursorActivity=!0,this.ace.inMultiSelectMode&&this.ace.keyBinding.removeKeyboardHandler(p.keyboardHandler)},this.operation=function(e,t){if(!t&&this.curOp||t&&this.curOp&&this.curOp.force)return e();(t||!this.ace.curOp)&&this.curOp&&this.onBeforeEndOperation();if(!this.ace.curOp){var n=this.ace.prevOp;this.ace.startOperation({command:{name:\"vim\",scrollIntoView:\"cursor\"}})}var r=this.curOp=this.curOp||{};this.curOp.force=t;var i=e();return this.ace.curOp&&this.ace.curOp.command.name==\"vim\"&&(this.ace.endOperation(),!r.cursorActivity&&!r.lastChange&&n&&(this.ace.prevOp=n)),(t||!this.ace.curOp)&&this.curOp&&this.onBeforeEndOperation(),i},this.onBeforeEndOperation=function(){var e=this.curOp;e&&(e.change&&this.signal(\"change\",e.change,e),e&&e.cursorActivity&&this.signal(\"cursorActivity\",null,e),this.curOp=null)},this.signal=function(e,t,n){var r=n?n[e+\"Handlers\"]:(this._eventRegistry||{})[e];if(!r)return;r=r.slice();for(var i=0;i<r.length;i++)r[i](this,t)},this.firstLine=function(){return 0},this.lastLine=function(){return this.ace.session.getLength()-1},this.lineCount=function(){return this.ace.session.getLength()},this.setCursor=function(e,t){typeof e==\"object\"&&(t=e.ch,e=e.line),this.ace.inVirtualSelectionMode||this.ace.exitMultiSelectMode(),this.ace.session.unfold({row:e,column:t}),this.ace.selection.moveTo(e,t)},this.getCursor=function(e){var t=this.ace.selection,n=e==\"anchor\"?t.isEmpty()?t.lead:t.anchor:e==\"head\"||!e?t.lead:t.getRange()[e];return g(n)},this.listSelections=function(e){var t=this.ace.multiSelect.rangeList.ranges;return!t.length||this.ace.inVirtualSelectionMode?[{anchor:this.getCursor(\"anchor\"),head:this.getCursor(\"head\")}]:t.map(function(e){return{anchor:this.clipPos(g(e.cursor==e.end?e.start:e.end)),head:this.clipPos(g(e.cursor))}},this)},this.setSelections=function(e,t){var n=this.ace.multiSelect,r=e.map(function(e){var t=m(e.anchor),n=m(e.head),r=i.comparePoints(t,n)<0?new i.fromPoints(t,n):new i.fromPoints(n,t);return r.cursor=i.comparePoints(r.start,n)?r.end:r.start,r});if(this.ace.inVirtualSelectionMode){this.ace.selection.fromOrientedRange(r[0]);return}t?r[t]&&r.push(r.splice(t,1)[0]):r=r.reverse(),n.toSingleRange(r[0].clone());var s=this.ace.session;for(var o=0;o<r.length;o++){var u=s.$clipRangeToDocument(r[o]);n.addRange(u)}},this.setSelection=function(e,t,n){var r=this.ace.selection;r.moveTo(e.line,e.ch),r.selectTo(t.line,t.ch),n&&n.origin==\"*mouse\"&&this.onBeforeEndOperation()},this.somethingSelected=function(e){return!this.ace.selection.isEmpty()},this.clipPos=function(e){var t=this.ace.session.$clipPositionToDocument(e.line,e.ch);return g(t)},this.markText=function(e){return{clear:function(){},find:function(){}}},this.$updateMarkers=function(e){var t=e.action==\"insert\",n=e.start,r=e.end,s=(r.row-n.row)*(t?1:-1),o=(r.column-n.column)*(t?1:-1);t&&(r=n);for(var u in this.marks){var a=this.marks[u],f=i.comparePoints(a,n);if(f<0)continue;if(f===0&&t){if(a.bias!=1){a.bias==-1;continue}f=1}var l=t?f:i.comparePoints(a,r);if(l>0){a.row+=s,a.column+=a.row==r.row?o:0;continue}!t&&l<=0&&(a.row=n.row,a.column=n.column,l===0&&(a.bias=1))}};var e=function(e,t,n,r){this.cm=e,this.id=t,this.row=n,this.column=r,e.marks[this.id]=this};e.prototype.clear=function(){delete this.cm.marks[this.id]},e.prototype.find=function(){return g(this)},this.setBookmark=function(t,n){var r=new e(this,this.$uid++,t.line,t.ch);if(!n||!n.insertLeft)r.$insertRight=!0;return this.marks[r.id]=r,r},this.moveH=function(e,t){if(t==\"char\"){var n=this.ace.selection;n.clearSelection(),n.moveCursorBy(0,e)}},this.findPosV=function(e,t,n,r){if(n==\"page\"){var i=this.ace.renderer,s=i.layerConfig;t*=Math.floor(s.height/s.lineHeight),n=\"line\"}if(n==\"line\"){var o=this.ace.session.documentToScreenPosition(e.line,e.ch);r!=null&&(o.column=r),o.row+=t,o.row=Math.min(Math.max(0,o.row),this.ace.session.getScreenLength()-1);var u=this.ace.session.screenToDocumentPosition(o.row,o.column);return g(u)}debugger},this.charCoords=function(e,t){if(t==\"div\"||!t){var n=this.ace.session.documentToScreenPosition(e.line,e.ch);return{left:n.column,top:n.row}}if(t==\"local\"){var r=this.ace.renderer,n=this.ace.session.documentToScreenPosition(e.line,e.ch),i=r.layerConfig.lineHeight,s=r.layerConfig.characterWidth,o=i*n.row;return{left:n.column*s,top:o,bottom:o+i}}},this.coordsChar=function(e,t){var n=this.ace.renderer;if(t==\"local\"){var r=Math.max(0,Math.floor(e.top/n.lineHeight)),i=Math.max(0,Math.floor(e.left/n.characterWidth)),s=n.session.screenToDocumentPosition(r,i);return g(s)}if(t==\"div\")throw\"not implemented\"},this.getSearchCursor=function(e,t,n){var r=!1,i=!1;e instanceof RegExp&&!e.global&&(r=!e.ignoreCase,e=e.source,i=!0);var s=new l;t.ch==undefined&&(t.ch=Number.MAX_VALUE);var o={row:t.line,column:t.ch},u=this,a=null;return{findNext:function(){return this.find(!1)},findPrevious:function(){return this.find(!0)},find:function(t){s.setOptions({needle:e,caseSensitive:r,wrap:!1,backwards:t,regExp:i,start:a||o});var n=s.find(u.ace.session);return n&&n.isEmpty()&&u.getLine(n.start.row).length==n.start.column&&(s.$options.start=n,n=s.find(u.ace.session)),a=n,a},from:function(){return a&&g(a.start)},to:function(){return a&&g(a.end)},replace:function(e){a&&(a.end=u.ace.session.doc.replace(a,e))}}},this.scrollTo=function(e,t){var n=this.ace.renderer,r=n.layerConfig,i=r.maxHeight;i-=(n.$size.scrollerHeight-n.lineHeight)*n.$scrollPastEnd,t!=null&&this.ace.session.setScrollTop(Math.max(0,Math.min(t,i))),e!=null&&this.ace.session.setScrollLeft(Math.max(0,Math.min(e,r.width)))},this.scrollInfo=function(){return 0},this.scrollIntoView=function(e,t){if(e){var n=this.ace.renderer,r={top:0,bottom:t};n.scrollCursorIntoView(m(e),n.lineHeight*2/n.$size.scrollerHeight,r)}},this.getLine=function(e){return this.ace.session.getLine(e)},this.getRange=function(e,t){return this.ace.session.getTextRange(new i(e.line,e.ch,t.line,t.ch))},this.replaceRange=function(e,t,n){return n||(n=t),this.ace.session.replace(new i(t.line,t.ch,n.line,n.ch),e)},this.replaceSelections=function(e){var t=this.ace.selection;if(this.ace.inVirtualSelectionMode){this.ace.session.replace(t.getRange(),e[0]||\"\");return}t.inVirtualSelectionMode=!0;var n=t.rangeList.ranges;n.length||(n=[this.ace.multiSelect.getRange()]);for(var r=n.length;r--;)this.ace.session.replace(n[r],e[r]||\"\");t.inVirtualSelectionMode=!1},this.getSelection=function(){return this.ace.getSelectedText()},this.getSelections=function(){return this.listSelections().map(function(e){return this.getRange(e.anchor,e.head)},this)},this.getInputField=function(){return this.ace.textInput.getElement()},this.getWrapperElement=function(){return this.ace.containter};var t={indentWithTabs:\"useSoftTabs\",indentUnit:\"tabSize\",tabSize:\"tabSize\",firstLineNumber:\"firstLineNumber\",readOnly:\"readOnly\"};this.setOption=function(e,n){this.state[e]=n;switch(e){case\"indentWithTabs\":e=t[e],n=!n;break;default:e=t[e]}e&&this.ace.setOption(e,n)},this.getOption=function(e,n){var r=t[e];r&&(n=this.ace.getOption(r));switch(e){case\"indentWithTabs\":return e=t[e],!n}return r?n:this.state[e]},this.toggleOverwrite=function(e){return this.state.overwrite=e,this.ace.setOverwrite(e)},this.addOverlay=function(e){if(!this.$searchHighlight||!this.$searchHighlight.session){var t=new h(null,\"ace_highlight-marker\",\"text\"),n=this.ace.session.addDynamicMarker(t);t.id=n.id,t.session=this.ace.session,t.destroy=function(e){t.session.off(\"change\",t.updateOnChange),t.session.off(\"changeEditor\",t.destroy),t.session.removeMarker(t.id),t.session=null},t.updateOnChange=function(e){var n=e.start.row;n==e.end.row?t.cache[n]=undefined:t.cache.splice(n,t.cache.length)},t.session.on(\"changeEditor\",t.destroy),t.session.on(\"change\",t.updateOnChange)}var r=new RegExp(e.query.source,\"gmi\");this.$searchHighlight=e.highlight=t,this.$searchHighlight.setRegexp(r),this.ace.renderer.updateBackMarkers()},this.removeOverlay=function(e){this.$searchHighlight&&this.$searchHighlight.session&&this.$searchHighlight.destroy()},this.getScrollInfo=function(){var e=this.ace.renderer,t=e.layerConfig;return{left:e.scrollLeft,top:e.scrollTop,height:t.maxHeight,width:t.width,clientHeight:t.height,clientWidth:t.width}},this.getValue=function(){return this.ace.getValue()},this.setValue=function(e){return this.ace.setValue(e)},this.getTokenTypeAt=function(e){var t=this.ace.session.getTokenAt(e.line,e.ch);return t&&/comment|string/.test(t.type)?\"string\":\"\"},this.findMatchingBracket=function(e){var t=this.ace.session.findMatchingBracket(m(e));return{to:t&&g(t)}},this.indentLine=function(e,t){t===!0?this.ace.session.indentRows(e,e,\"\t\"):t===!1&&this.ace.session.outdentRows(new i(e,0,e,0))},this.indexFromPos=function(e){return this.ace.session.doc.positionToIndex(m(e))},this.posFromIndex=function(e){return g(this.ace.session.doc.indexToPosition(e))},this.focus=function(e){return this.ace.focus()},this.blur=function(e){return this.ace.blur()},this.defaultTextHeight=function(e){return this.ace.renderer.layerConfig.lineHeight},this.scanForBracket=function(e,t,n,r){var i=r.bracketRegex.source;if(t==1)var s=this.ace.session.$findClosingBracket(i.slice(1,2),m(e),/paren|text/);else var s=this.ace.session.$findOpeningBracket(i.slice(-2,-1),{row:e.line,column:e.ch+1},/paren|text/);return s&&{pos:g(s)}},this.refresh=function(){return this.ace.resize(!0)},this.getMode=function(){return{name:this.getOption(\"mode\")}}}.call(v.prototype);var y=v.StringStream=function(e,t){this.pos=this.start=0,this.string=e,this.tabSize=t||8,this.lastColumnPos=this.lastColumnValue=0,this.lineStart=0};y.prototype={eol:function(){return this.pos>=this.string.length},sol:function(){return this.pos==this.lineStart},peek:function(){return this.string.charAt(this.pos)||undefined},next:function(){if(this.pos<this.string.length)return this.string.charAt(this.pos++)},eat:function(e){var t=this.string.charAt(this.pos);if(typeof e==\"string\")var n=t==e;else var n=t&&(e.test?e.test(t):e(t));if(n)return++this.pos,t},eatWhile:function(e){var t=this.pos;while(this.eat(e));return this.pos>t},eatSpace:function(){var e=this.pos;while(/[\\s\\u00a0]/.test(this.string.charAt(this.pos)))++this.pos;return this.pos>e},skipToEnd:function(){this.pos=this.string.length},skipTo:function(e){var t=this.string.indexOf(e,this.pos);if(t>-1)return this.pos=t,!0},backUp:function(e){this.pos-=e},column:function(){throw\"not implemented\"},indentation:function(){throw\"not implemented\"},match:function(e,t,n){if(typeof e!=\"string\"){var s=this.string.slice(this.pos).match(e);return s&&s.index>0?null:(s&&t!==!1&&(this.pos+=s[0].length),s)}var r=function(e){return n?e.toLowerCase():e},i=this.string.substr(this.pos,e.length);if(r(i)==r(e))return t!==!1&&(this.pos+=e.length),!0},current:function(){return this.string.slice(this.start,this.pos)},hideFirstChars:function(e,t){this.lineStart+=e;try{return t()}finally{this.lineStart-=e}}},v.defineExtension=function(e,t){v.prototype[e]=t},o.importCssString(\".normal-mode .ace_cursor{  border: 1px solid red;  background-color: red;  opacity: 0.5;}.normal-mode .ace_hidden-cursors .ace_cursor{  background-color: transparent;}.ace_dialog {  position: absolute;  left: 0; right: 0;  background: white;  z-index: 15;  padding: .1em .8em;  overflow: hidden;  color: #333;}.ace_dialog-top {  border-bottom: 1px solid #eee;  top: 0;}.ace_dialog-bottom {  border-top: 1px solid #eee;  bottom: 0;}.ace_dialog input {  border: none;  outline: none;  background: transparent;  width: 20em;  color: inherit;  font-family: monospace;}\",\"vimMode\"),function(){function e(e,t,n){var r=e.ace.container,i;return i=r.appendChild(document.createElement(\"div\")),n?i.className=\"ace_dialog ace_dialog-bottom\":i.className=\"ace_dialog ace_dialog-top\",typeof t==\"string\"?i.innerHTML=t:i.appendChild(t),i}function t(e,t){e.state.currentNotificationClose&&e.state.currentNotificationClose(),e.state.currentNotificationClose=t}v.defineExtension(\"openDialog\",function(n,r,i){function a(e){if(typeof e==\"string\")f.value=e;else{if(o)return;o=!0,s.parentNode.removeChild(s),u.focus(),i.onClose&&i.onClose(s)}}if(this.virtualSelectionMode())return;i||(i={}),t(this,null);var s=e(this,n,i.bottom),o=!1,u=this,f=s.getElementsByTagName(\"input\")[0],l;if(f)i.value&&(f.value=i.value,i.select!==!1&&f.select()),i.onInput&&v.on(f,\"input\",function(e){i.onInput(e,f.value,a)}),i.onKeyUp&&v.on(f,\"keyup\",function(e){i.onKeyUp(e,f.value,a)}),v.on(f,\"keydown\",function(e){if(i&&i.onKeyDown&&i.onKeyDown(e,f.value,a))return;if(e.keyCode==27||i.closeOnEnter!==!1&&e.keyCode==13)f.blur(),v.e_stop(e),a();e.keyCode==13&&r(f.value)}),i.closeOnBlur!==!1&&v.on(f,\"blur\",a),f.focus();else if(l=s.getElementsByTagName(\"button\")[0])v.on(l,\"click\",function(){a(),u.focus()}),i.closeOnBlur!==!1&&v.on(l,\"blur\",a),l.focus();return a}),v.defineExtension(\"openNotification\",function(n,r){function a(){if(s)return;s=!0,clearTimeout(o),i.parentNode.removeChild(i)}if(this.virtualSelectionMode())return;t(this,a);var i=e(this,n,r&&r.bottom),s=!1,o,u=r&&typeof r.duration!=\"undefined\"?r.duration:5e3;return v.on(i,\"click\",function(e){v.e_preventDefault(e),a()}),u&&(o=setTimeout(a,u)),a})}();var b=[{keys:\"<Left>\",type:\"keyToKey\",toKeys:\"h\"},{keys:\"<Right>\",type:\"keyToKey\",toKeys:\"l\"},{keys:\"<Up>\",type:\"keyToKey\",toKeys:\"k\"},{keys:\"<Down>\",type:\"keyToKey\",toKeys:\"j\"},{keys:\"<Space>\",type:\"keyToKey\",toKeys:\"l\"},{keys:\"<BS>\",type:\"keyToKey\",toKeys:\"h\",context:\"normal\"},{keys:\"<C-Space>\",type:\"keyToKey\",toKeys:\"W\"},{keys:\"<C-BS>\",type:\"keyToKey\",toKeys:\"B\",context:\"normal\"},{keys:\"<S-Space>\",type:\"keyToKey\",toKeys:\"w\"},{keys:\"<S-BS>\",type:\"keyToKey\",toKeys:\"b\",context:\"normal\"},{keys:\"<C-n>\",type:\"keyToKey\",toKeys:\"j\"},{keys:\"<C-p>\",type:\"keyToKey\",toKeys:\"k\"},{keys:\"<C-[>\",type:\"keyToKey\",toKeys:\"<Esc>\"},{keys:\"<C-c>\",type:\"keyToKey\",toKeys:\"<Esc>\"},{keys:\"<C-[>\",type:\"keyToKey\",toKeys:\"<Esc>\",context:\"insert\"},{keys:\"<C-c>\",type:\"keyToKey\",toKeys:\"<Esc>\",context:\"insert\"},{keys:\"s\",type:\"keyToKey\",toKeys:\"cl\",context:\"normal\"},{keys:\"s\",type:\"keyToKey\",toKeys:\"c\",context:\"visual\"},{keys:\"S\",type:\"keyToKey\",toKeys:\"cc\",context:\"normal\"},{keys:\"S\",type:\"keyToKey\",toKeys:\"VdO\",context:\"visual\"},{keys:\"<Home>\",type:\"keyToKey\",toKeys:\"0\"},{keys:\"<End>\",type:\"keyToKey\",toKeys:\"$\"},{keys:\"<PageUp>\",type:\"keyToKey\",toKeys:\"<C-b>\"},{keys:\"<PageDown>\",type:\"keyToKey\",toKeys:\"<C-f>\"},{keys:\"<CR>\",type:\"keyToKey\",toKeys:\"j^\",context:\"normal\"},{keys:\"H\",type:\"motion\",motion:\"moveToTopLine\",motionArgs:{linewise:!0,toJumplist:!0}},{keys:\"M\",type:\"motion\",motion:\"moveToMiddleLine\",motionArgs:{linewise:!0,toJumplist:!0}},{keys:\"L\",type:\"motion\",motion:\"moveToBottomLine\",motionArgs:{linewise:!0,toJumplist:!0}},{keys:\"h\",type:\"motion\",motion:\"moveByCharacters\",motionArgs:{forward:!1}},{keys:\"l\",type:\"motion\",motion:\"moveByCharacters\",motionArgs:{forward:!0}},{keys:\"j\",type:\"motion\",motion:\"moveByLines\",motionArgs:{forward:!0,linewise:!0}},{keys:\"k\",type:\"motion\",motion:\"moveByLines\",motionArgs:{forward:!1,linewise:!0}},{keys:\"gj\",type:\"motion\",motion:\"moveByDisplayLines\",motionArgs:{forward:!0}},{keys:\"gk\",type:\"motion\",motion:\"moveByDisplayLines\",motionArgs:{forward:!1}},{keys:\"w\",type:\"motion\",motion:\"moveByWords\",motionArgs:{forward:!0,wordEnd:!1}},{keys:\"W\",type:\"motion\",motion:\"moveByWords\",motionArgs:{forward:!0,wordEnd:!1,bigWord:!0}},{keys:\"e\",type:\"motion\",motion:\"moveByWords\",motionArgs:{forward:!0,wordEnd:!0,inclusive:!0}},{keys:\"E\",type:\"motion\",motion:\"moveByWords\",motionArgs:{forward:!0,wordEnd:!0,bigWord:!0,inclusive:!0}},{keys:\"b\",type:\"motion\",motion:\"moveByWords\",motionArgs:{forward:!1,wordEnd:!1}},{keys:\"B\",type:\"motion\",motion:\"moveByWords\",motionArgs:{forward:!1,wordEnd:!1,bigWord:!0}},{keys:\"ge\",type:\"motion\",motion:\"moveByWords\",motionArgs:{forward:!1,wordEnd:!0,inclusive:!0}},{keys:\"gE\",type:\"motion\",motion:\"moveByWords\",motionArgs:{forward:!1,wordEnd:!0,bigWord:!0,inclusive:!0}},{keys:\"{\",type:\"motion\",motion:\"moveByParagraph\",motionArgs:{forward:!1,toJumplist:!0}},{keys:\"}\",type:\"motion\",motion:\"moveByParagraph\",motionArgs:{forward:!0,toJumplist:!0}},{keys:\"<C-f>\",type:\"motion\",motion:\"moveByPage\",motionArgs:{forward:!0}},{keys:\"<C-b>\",type:\"motion\",motion:\"moveByPage\",motionArgs:{forward:!1}},{keys:\"<C-d>\",type:\"motion\",motion:\"moveByScroll\",motionArgs:{forward:!0,explicitRepeat:!0}},{keys:\"<C-u>\",type:\"motion\",motion:\"moveByScroll\",motionArgs:{forward:!1,explicitRepeat:!0}},{keys:\"gg\",type:\"motion\",motion:\"moveToLineOrEdgeOfDocument\",motionArgs:{forward:!1,explicitRepeat:!0,linewise:!0,toJumplist:!0}},{keys:\"G\",type:\"motion\",motion:\"moveToLineOrEdgeOfDocument\",motionArgs:{forward:!0,explicitRepeat:!0,linewise:!0,toJumplist:!0}},{keys:\"0\",type:\"motion\",motion:\"moveToStartOfLine\"},{keys:\"^\",type:\"motion\",motion:\"moveToFirstNonWhiteSpaceCharacter\"},{keys:\"+\",type:\"motion\",motion:\"moveByLines\",motionArgs:{forward:!0,toFirstChar:!0}},{keys:\"-\",type:\"motion\",motion:\"moveByLines\",motionArgs:{forward:!1,toFirstChar:!0}},{keys:\"_\",type:\"motion\",motion:\"moveByLines\",motionArgs:{forward:!0,toFirstChar:!0,repeatOffset:-1}},{keys:\"$\",type:\"motion\",motion:\"moveToEol\",motionArgs:{inclusive:!0}},{keys:\"%\",type:\"motion\",motion:\"moveToMatchedSymbol\",motionArgs:{inclusive:!0,toJumplist:!0}},{keys:\"f<character>\",type:\"motion\",motion:\"moveToCharacter\",motionArgs:{forward:!0,inclusive:!0}},{keys:\"F<character>\",type:\"motion\",motion:\"moveToCharacter\",motionArgs:{forward:!1}},{keys:\"t<character>\",type:\"motion\",motion:\"moveTillCharacter\",motionArgs:{forward:!0,inclusive:!0}},{keys:\"T<character>\",type:\"motion\",motion:\"moveTillCharacter\",motionArgs:{forward:!1}},{keys:\";\",type:\"motion\",motion:\"repeatLastCharacterSearch\",motionArgs:{forward:!0}},{keys:\",\",type:\"motion\",motion:\"repeatLastCharacterSearch\",motionArgs:{forward:!1}},{keys:\"'<character>\",type:\"motion\",motion:\"goToMark\",motionArgs:{toJumplist:!0,linewise:!0}},{keys:\"`<character>\",type:\"motion\",motion:\"goToMark\",motionArgs:{toJumplist:!0}},{keys:\"]`\",type:\"motion\",motion:\"jumpToMark\",motionArgs:{forward:!0}},{keys:\"[`\",type:\"motion\",motion:\"jumpToMark\",motionArgs:{forward:!1}},{keys:\"]'\",type:\"motion\",motion:\"jumpToMark\",motionArgs:{forward:!0,linewise:!0}},{keys:\"['\",type:\"motion\",motion:\"jumpToMark\",motionArgs:{forward:!1,linewise:!0}},{keys:\"]p\",type:\"action\",action:\"paste\",isEdit:!0,actionArgs:{after:!0,isEdit:!0,matchIndent:!0}},{keys:\"[p\",type:\"action\",action:\"paste\",isEdit:!0,actionArgs:{after:!1,isEdit:!0,matchIndent:!0}},{keys:\"]<character>\",type:\"motion\",motion:\"moveToSymbol\",motionArgs:{forward:!0,toJumplist:!0}},{keys:\"[<character>\",type:\"motion\",motion:\"moveToSymbol\",motionArgs:{forward:!1,toJumplist:!0}},{keys:\"|\",type:\"motion\",motion:\"moveToColumn\"},{keys:\"o\",type:\"motion\",motion:\"moveToOtherHighlightedEnd\",context:\"visual\"},{keys:\"O\",type:\"motion\",motion:\"moveToOtherHighlightedEnd\",motionArgs:{sameLine:!0},context:\"visual\"},{keys:\"d\",type:\"operator\",operator:\"delete\"},{keys:\"y\",type:\"operator\",operator:\"yank\"},{keys:\"c\",type:\"operator\",operator:\"change\"},{keys:\">\",type:\"operator\",operator:\"indent\",operatorArgs:{indentRight:!0}},{keys:\"<\",type:\"operator\",operator:\"indent\",operatorArgs:{indentRight:!1}},{keys:\"g~\",type:\"operator\",operator:\"changeCase\"},{keys:\"gu\",type:\"operator\",operator:\"changeCase\",operatorArgs:{toLower:!0},isEdit:!0},{keys:\"gU\",type:\"operator\",operator:\"changeCase\",operatorArgs:{toLower:!1},isEdit:!0},{keys:\"n\",type:\"motion\",motion:\"findNext\",motionArgs:{forward:!0,toJumplist:!0}},{keys:\"N\",type:\"motion\",motion:\"findNext\",motionArgs:{forward:!1,toJumplist:!0}},{keys:\"x\",type:\"operatorMotion\",operator:\"delete\",motion:\"moveByCharacters\",motionArgs:{forward:!0},operatorMotionArgs:{visualLine:!1}},{keys:\"X\",type:\"operatorMotion\",operator:\"delete\",motion:\"moveByCharacters\",motionArgs:{forward:!1},operatorMotionArgs:{visualLine:!0}},{keys:\"D\",type:\"operatorMotion\",operator:\"delete\",motion:\"moveToEol\",motionArgs:{inclusive:!0},context:\"normal\"},{keys:\"D\",type:\"operator\",operator:\"delete\",operatorArgs:{linewise:!0},context:\"visual\"},{keys:\"Y\",type:\"operatorMotion\",operator:\"yank\",motion:\"moveToEol\",motionArgs:{inclusive:!0},context:\"normal\"},{keys:\"Y\",type:\"operator\",operator:\"yank\",operatorArgs:{linewise:!0},context:\"visual\"},{keys:\"C\",type:\"operatorMotion\",operator:\"change\",motion:\"moveToEol\",motionArgs:{inclusive:!0},context:\"normal\"},{keys:\"C\",type:\"operator\",operator:\"change\",operatorArgs:{linewise:!0},context:\"visual\"},{keys:\"~\",type:\"operatorMotion\",operator:\"changeCase\",motion:\"moveByCharacters\",motionArgs:{forward:!0},operatorArgs:{shouldMoveCursor:!0},context:\"normal\"},{keys:\"~\",type:\"operator\",operator:\"changeCase\",context:\"visual\"},{keys:\"<C-w>\",type:\"operatorMotion\",operator:\"delete\",motion:\"moveByWords\",motionArgs:{forward:!1,wordEnd:!1},context:\"insert\"},{keys:\"<C-i>\",type:\"action\",action:\"jumpListWalk\",actionArgs:{forward:!0}},{keys:\"<C-o>\",type:\"action\",action:\"jumpListWalk\",actionArgs:{forward:!1}},{keys:\"<C-e>\",type:\"action\",action:\"scroll\",actionArgs:{forward:!0,linewise:!0}},{keys:\"<C-y>\",type:\"action\",action:\"scroll\",actionArgs:{forward:!1,linewise:!0}},{keys:\"a\",type:\"action\",action:\"enterInsertMode\",isEdit:!0,actionArgs:{insertAt:\"charAfter\"},context:\"normal\"},{keys:\"A\",type:\"action\",action:\"enterInsertMode\",isEdit:!0,actionArgs:{insertAt:\"eol\"},context:\"normal\"},{keys:\"A\",type:\"action\",action:\"enterInsertMode\",isEdit:!0,actionArgs:{insertAt:\"endOfSelectedArea\"},context:\"visual\"},{keys:\"i\",type:\"action\",action:\"enterInsertMode\",isEdit:!0,actionArgs:{insertAt:\"inplace\"},context:\"normal\"},{keys:\"I\",type:\"action\",action:\"enterInsertMode\",isEdit:!0,actionArgs:{insertAt:\"firstNonBlank\"},context:\"normal\"},{keys:\"I\",type:\"action\",action:\"enterInsertMode\",isEdit:!0,actionArgs:{insertAt:\"startOfSelectedArea\"},context:\"visual\"},{keys:\"o\",type:\"action\",action:\"newLineAndEnterInsertMode\",isEdit:!0,interlaceInsertRepeat:!0,actionArgs:{after:!0},context:\"normal\"},{keys:\"O\",type:\"action\",action:\"newLineAndEnterInsertMode\",isEdit:!0,interlaceInsertRepeat:!0,actionArgs:{after:!1},context:\"normal\"},{keys:\"v\",type:\"action\",action:\"toggleVisualMode\"},{keys:\"V\",type:\"action\",action:\"toggleVisualMode\",actionArgs:{linewise:!0}},{keys:\"<C-v>\",type:\"action\",action:\"toggleVisualMode\",actionArgs:{blockwise:!0}},{keys:\"<C-q>\",type:\"action\",action:\"toggleVisualMode\",actionArgs:{blockwise:!0}},{keys:\"gv\",type:\"action\",action:\"reselectLastSelection\"},{keys:\"J\",type:\"action\",action:\"joinLines\",isEdit:!0},{keys:\"p\",type:\"action\",action:\"paste\",isEdit:!0,actionArgs:{after:!0,isEdit:!0}},{keys:\"P\",type:\"action\",action:\"paste\",isEdit:!0,actionArgs:{after:!1,isEdit:!0}},{keys:\"r<character>\",type:\"action\",action:\"replace\",isEdit:!0},{keys:\"@<character>\",type:\"action\",action:\"replayMacro\"},{keys:\"q<character>\",type:\"action\",action:\"enterMacroRecordMode\"},{keys:\"R\",type:\"action\",action:\"enterInsertMode\",isEdit:!0,actionArgs:{replace:!0}},{keys:\"u\",type:\"action\",action:\"undo\",context:\"normal\"},{keys:\"u\",type:\"operator\",operator:\"changeCase\",operatorArgs:{toLower:!0},context:\"visual\",isEdit:!0},{keys:\"U\",type:\"operator\",operator:\"changeCase\",operatorArgs:{toLower:!1},context:\"visual\",isEdit:!0},{keys:\"<C-r>\",type:\"action\",action:\"redo\"},{keys:\"m<character>\",type:\"action\",action:\"setMark\"},{keys:'\"<character>',type:\"action\",action:\"setRegister\"},{keys:\"zz\",type:\"action\",action:\"scrollToCursor\",actionArgs:{position:\"center\"}},{keys:\"z.\",type:\"action\",action:\"scrollToCursor\",actionArgs:{position:\"center\"},motion:\"moveToFirstNonWhiteSpaceCharacter\"},{keys:\"zt\",type:\"action\",action:\"scrollToCursor\",actionArgs:{position:\"top\"}},{keys:\"z<CR>\",type:\"action\",action:\"scrollToCursor\",actionArgs:{position:\"top\"},motion:\"moveToFirstNonWhiteSpaceCharacter\"},{keys:\"z-\",type:\"action\",action:\"scrollToCursor\",actionArgs:{position:\"bottom\"}},{keys:\"zb\",type:\"action\",action:\"scrollToCursor\",actionArgs:{position:\"bottom\"},motion:\"moveToFirstNonWhiteSpaceCharacter\"},{keys:\".\",type:\"action\",action:\"repeatLastEdit\"},{keys:\"<C-a>\",type:\"action\",action:\"incrementNumberToken\",isEdit:!0,actionArgs:{increase:!0,backtrack:!1}},{keys:\"<C-x>\",type:\"action\",action:\"incrementNumberToken\",isEdit:!0,actionArgs:{increase:!1,backtrack:!1}},{keys:\"a<character>\",type:\"motion\",motion:\"textObjectManipulation\"},{keys:\"i<character>\",type:\"motion\",motion:\"textObjectManipulation\",motionArgs:{textObjectInner:!0}},{keys:\"/\",type:\"search\",searchArgs:{forward:!0,querySrc:\"prompt\",toJumplist:!0}},{keys:\"?\",type:\"search\",searchArgs:{forward:!1,querySrc:\"prompt\",toJumplist:!0}},{keys:\"*\",type:\"search\",searchArgs:{forward:!0,querySrc:\"wordUnderCursor\",wholeWordOnly:!0,toJumplist:!0}},{keys:\"#\",type:\"search\",searchArgs:{forward:!1,querySrc:\"wordUnderCursor\",wholeWordOnly:!0,toJumplist:!0}},{keys:\"g*\",type:\"search\",searchArgs:{forward:!0,querySrc:\"wordUnderCursor\",toJumplist:!0}},{keys:\"g#\",type:\"search\",searchArgs:{forward:!1,querySrc:\"wordUnderCursor\",toJumplist:!0}},{keys:\":\",type:\"ex\"}],w=[{name:\"colorscheme\",shortName:\"colo\"},{name:\"map\"},{name:\"imap\",shortName:\"im\"},{name:\"nmap\",shortName:\"nm\"},{name:\"vmap\",shortName:\"vm\"},{name:\"unmap\"},{name:\"write\",shortName:\"w\"},{name:\"undo\",shortName:\"u\"},{name:\"redo\",shortName:\"red\"},{name:\"set\",shortName:\"se\"},{name:\"set\",shortName:\"se\"},{name:\"setlocal\",shortName:\"setl\"},{name:\"setglobal\",shortName:\"setg\"},{name:\"sort\",shortName:\"sor\"},{name:\"substitute\",shortName:\"s\",possiblyAsync:!0},{name:\"nohlsearch\",shortName:\"noh\"},{name:\"delmarks\",shortName:\"delm\"},{name:\"registers\",shortName:\"reg\",excludeFromCommandHistory:!0},{name:\"global\",shortName:\"g\"}],E=v.Pos,S=function(){return st};v.defineOption(\"vimMode\",!1,function(e,t,n){t&&e.getOption(\"keyMap\")!=\"vim\"?e.setOption(\"keyMap\",\"vim\"):!t&&n!=v.Init&&/^vim/.test(e.getOption(\"keyMap\"))&&e.setOption(\"keyMap\",\"default\")});var L={Shift:\"S\",Ctrl:\"C\",Alt:\"A\",Cmd:\"D\",Mod:\"A\"},A={Enter:\"CR\",Backspace:\"BS\",Delete:\"Del\"},_=/[\\d]/,D=[v.isWordChar,function(e){return e&&!v.isWordChar(e)&&!/\\s/.test(e)}],P=[function(e){return/\\S/.test(e)}],B=H(65,26),j=H(97,26),F=H(48,10),I=[].concat(B,j,F,[\"<\",\">\"]),q=[].concat(B,j,F,[\"-\",'\"',\".\",\":\",\"/\"]),J={};K(\"filetype\",undefined,\"string\",[\"ft\"],function(e,t){if(t===undefined)return;if(e===undefined){var n=t.getOption(\"mode\");return n==\"null\"?\"\":n}var n=e==\"\"?\"null\":e;t.setOption(\"mode\",n)});var Y=function(){function s(s,o,u){function l(n){var r=++t%e,o=i[r];o&&o.clear(),i[r]=s.setBookmark(n)}var a=t%e,f=i[a];if(f){var c=f.find();c&&!At(c,o)&&l(o)}else l(o);l(u),n=t,r=t-e+1,r<0&&(r=0)}function o(s,o){t+=o,t>n?t=n:t<r&&(t=r);var u=i[(e+t)%e];if(u&&!u.find()){var a=o>0?1:-1,f,l=s.getCursor();do{t+=a,u=i[(e+t)%e];if(u&&(f=u.find())&&!At(l,f))break}while(t<n&&t>r)}return u}var e=100,t=-1,n=0,r=0,i=new Array(e);return{cachedCursor:undefined,add:s,move:o}},Z=function(e){return e?{changes:e.changes,expectCursorActivityForChange:e.expectCursorActivityForChange}:{changes:[],expectCursorActivityForChange:!1}};et.prototype={exitMacroRecordMode:function(){var e=nt.macroModeState;e.onRecordingDone&&e.onRecordingDone(),e.onRecordingDone=undefined,e.isRecording=!1},enterMacroRecordMode:function(e,t){var n=nt.registerController.getRegister(t);n&&(n.clear(),this.latestRegister=t,e.openDialog&&(this.onRecordingDone=e.openDialog(\"(recording)[\"+t+\"]\",null,{bottom:!0})),this.isRecording=!0)}};var nt,it,st={buildKeyMap:function(){},getRegisterController:function(){return nt.registerController},resetVimGlobalState_:rt,getVimGlobalState_:function(){return nt},maybeInitVimState_:tt,suppressErrorLogging:!1,InsertModeKey:Gn,map:function(e,t,n){Fn.map(e,t,n)},unmap:function(e,t){Fn.unmap(e,t)},setOption:Q,getOption:G,defineOption:K,defineEx:function(e,t,n){if(!t)t=e;else if(e.indexOf(t)!==0)throw new Error('(Vim.defineEx) \"'+t+'\" is not a prefix of \"'+e+'\", command not registered');jn[e]=n,Fn.commandMap_[t]={name:e,shortName:t,type:\"api\"}},handleKey:function(e,t,n){var r=this.findKey(e,t,n);if(typeof r==\"function\")return r()},findKey:function(e,t,n){function i(){var r=nt.macroModeState;if(r.isRecording){if(t==\"q\")return r.exitMacroRecordMode(),ut(e),!0;n!=\"mapping\"&&Wn(r,t)}}function s(){if(t==\"<Esc>\")return ut(e),r.visualMode?$t(e):r.insertMode&&qn(e),!0}function o(n){var r;while(n)r=/<\\w+-.+?>|<\\w+>|./.exec(n),t=r[0],n=n.substring(r.index+t.length),v.Vim.handleKey(e,t,\"mapping\")}function u(){if(s())return!0;var n=r.inputState.keyBuffer=r.inputState.keyBuffer+t,i=t.length==1,o=ht.matchCommand(n,b,r.inputState,\"insert\");while(n.length>1&&o.type!=\"full\"){var n=r.inputState.keyBuffer=n.slice(1),u=ht.matchCommand(n,b,r.inputState,\"insert\");u.type!=\"none\"&&(o=u)}if(o.type==\"none\")return ut(e),!1;if(o.type==\"partial\")return it&&window.clearTimeout(it),it=window.setTimeout(function(){r.insertMode&&r.inputState.keyBuffer&&ut(e)},G(\"insertModeEscKeysTimeout\")),!i;it&&window.clearTimeout(it);if(i){var a=e.listSelections();for(var f=0;f<a.length;f++){var l=a[f].head;e.replaceRange(\"\",St(l,0,-(n.length-1)),l,\"+input\")}nt.macroModeState.lastInsertModeChanges.changes.pop()}return ut(e),o.command}function a(){if(i()||s())return!0;var n=r.inputState.keyBuffer=r.inputState.keyBuffer+t;if(/^[1-9]\\d*$/.test(n))return!0;var o=/^(\\d*)(.*)$/.exec(n);if(!o)return ut(e),!1;var u=r.visualMode?\"visual\":\"normal\",a=ht.matchCommand(o[2]||o[1],b,r.inputState,u);if(a.type==\"none\")return ut(e),!1;if(a.type==\"partial\")return!0;r.inputState.keyBuffer=\"\";var o=/^(\\d*)(.*)$/.exec(n);return o[1]&&o[1]!=\"0\"&&r.inputState.pushRepeatDigit(o[1]),a.command}var r=tt(e),f;return r.insertMode?f=u():f=a(),f===!1?undefined:f===!0?function(){return!0}:function(){if((f.operator||f.isEdit)&&e.getOption(\"readOnly\"))return;return e.operation(function(){e.curOp.isVimOp=!0;try{f.type==\"keyToKey\"?o(f.toKeys):ht.processCommand(e,r,f)}catch(t){throw e.state.vim=undefined,tt(e),v.Vim.suppressErrorLogging||console.log(t),t}return!0})}},handleEx:function(e,t){Fn.processCommand(e,t)},defineMotion:dt,defineAction:bt,defineOperator:gt,mapCommand:Un,_mapCommand:Rn,defineRegister:ft,exitVisualMode:$t,exitInsertMode:qn};ot.prototype.pushRepeatDigit=function(e){this.operator?this.motionRepeat=this.motionRepeat.concat(e):this.prefixRepeat=this.prefixRepeat.concat(e)},ot.prototype.getRepeat=function(){var e=0;if(this.prefixRepeat.length>0||this.motionRepeat.length>0)e=1,this.prefixRepeat.length>0&&(e*=parseInt(this.prefixRepeat.join(\"\"),10)),this.motionRepeat.length>0&&(e*=parseInt(this.motionRepeat.join(\"\"),10));return e},at.prototype={setText:function(e,t,n){this.keyBuffer=[e||\"\"],this.linewise=!!t,this.blockwise=!!n},pushText:function(e,t){t&&(this.linewise||this.keyBuffer.push(\"\\n\"),this.linewise=!0),this.keyBuffer.push(e)},pushInsertModeChanges:function(e){this.insertModeChanges.push(Z(e))},pushSearchQuery:function(e){this.searchQueries.push(e)},clear:function(){this.keyBuffer=[],this.insertModeChanges=[],this.searchQueries=[],this.linewise=!1},toString:function(){return this.keyBuffer.join(\"\")}},lt.prototype={pushText:function(e,t,n,r,i){r&&n.charAt(0)==\"\\n\"&&(n=n.slice(1)+\"\\n\"),r&&n.charAt(n.length-1)!==\"\\n\"&&(n+=\"\\n\");var s=this.isValidRegister(e)?this.getRegister(e):null;if(!s){switch(t){case\"yank\":this.registers[0]=new at(n,r,i);break;case\"delete\":case\"change\":n.indexOf(\"\\n\")==-1?this.registers[\"-\"]=new at(n,r):(this.shiftNumericRegisters_(),this.registers[1]=new at(n,r))}this.unnamedRegister.setText(n,r,i);return}var o=X(e);o?s.pushText(n,r):s.setText(n,r,i),this.unnamedRegister.setText(s.toString(),r)},getRegister:function(e){return this.isValidRegister(e)?(e=e.toLowerCase(),this.registers[e]||(this.registers[e]=new at),this.registers[e]):this.unnamedRegister},isValidRegister:function(e){return e&&$(e,q)},shiftNumericRegisters_:function(){for(var e=9;e>=2;e--)this.registers[e]=this.getRegister(\"\"+(e-1))}},ct.prototype={nextMatch:function(e,t){var n=this.historyBuffer,r=t?-1:1;this.initialPrefix===null&&(this.initialPrefix=e);for(var i=this.iterator+r;t?i>=0:i<n.length;i+=r){var s=n[i];for(var o=0;o<=s.length;o++)if(this.initialPrefix==s.substring(0,o))return this.iterator=i,s}if(i>=n.length)return this.iterator=n.length,this.initialPrefix;if(i<0)return e},pushInput:function(e){var t=this.historyBuffer.indexOf(e);t>-1&&this.historyBuffer.splice(t,1),e.length&&this.historyBuffer.push(e)},reset:function(){this.initialPrefix=null,this.iterator=this.historyBuffer.length}};var ht={matchCommand:function(e,t,n,r){var i=Tt(e,t,r,n);if(!i.full&&!i.partial)return{type:\"none\"};if(!i.full&&i.partial)return{type:\"partial\"};var s;for(var o=0;o<i.full.length;o++){var u=i.full[o];s||(s=u)}return s.keys.slice(-11)==\"<character>\"&&(n.selectedCharacter=Ct(e)),{type:\"full\",command:s}},processCommand:function(e,t,n){t.inputState.repeatOverride=n.repeatOverride;switch(n.type){case\"motion\":this.processMotion(e,t,n);break;case\"operator\":this.processOperator(e,t,n);break;case\"operatorMotion\":this.processOperatorMotion(e,t,n);break;case\"action\":this.processAction(e,t,n);break;case\"search\":this.processSearch(e,t,n);break;case\"ex\":case\"keyToEx\":this.processEx(e,t,n);break;default:}},processMotion:function(e,t,n){t.inputState.motion=n.motion,t.inputState.motionArgs=Et(n.motionArgs),this.evalInput(e,t)},processOperator:function(e,t,n){var r=t.inputState;if(r.operator){if(r.operator==n.operator){r.motion=\"expandToLine\",r.motionArgs={linewise:!0},this.evalInput(e,t);return}ut(e)}r.operator=n.operator,r.operatorArgs=Et(n.operatorArgs),t.visualMode&&this.evalInput(e,t)},processOperatorMotion:function(e,t,n){var r=t.visualMode,i=Et(n.operatorMotionArgs);i&&r&&i.visualLine&&(t.visualLine=!0),this.processOperator(e,t,n),r||this.processMotion(e,t,n)},processAction:function(e,t,n){var r=t.inputState,i=r.getRepeat(),s=!!i,o=Et(n.actionArgs)||{};r.selectedCharacter&&(o.selectedCharacter=r.selectedCharacter),n.operator&&this.processOperator(e,t,n),n.motion&&this.processMotion(e,t,n),(n.motion||n.operator)&&this.evalInput(e,t),o.repeat=i||1,o.repeatIsExplicit=s,o.registerName=r.registerName,ut(e),t.lastMotion=null,n.isEdit&&this.recordLastEdit(t,r,n),yt[n.action](e,o,t)},processSearch:function(e,t,n){function a(r,i,s){nt.searchHistoryController.pushInput(r),nt.searchHistoryController.reset();try{An(e,r,i,s)}catch(o){Tn(e,\"Invalid regex: \"+r),ut(e);return}ht.processMotion(e,t,{type:\"motion\",motion:\"findNext\",motionArgs:{forward:!0,toJumplist:n.searchArgs.toJumplist}})}function f(t){e.scrollTo(u.left,u.top),a(t,!0,!0);var n=nt.macroModeState;n.isRecording&&Vn(n,t)}function l(t,n,i){var s=v.keyName(t),o;s==\"Up\"||s==\"Down\"?(o=s==\"Up\"?!0:!1,n=nt.searchHistoryController.nextMatch(n,o)||\"\",i(n)):s!=\"Left\"&&s!=\"Right\"&&s!=\"Ctrl\"&&s!=\"Alt\"&&s!=\"Shift\"&&nt.searchHistoryController.reset();var a;try{a=An(e,n,!0,!0)}catch(t){}a?e.scrollIntoView(_n(e,!r,a),30):(Dn(e),e.scrollTo(u.left,u.top))}function c(t,n,r){var i=v.keyName(t);i==\"Esc\"||i==\"Ctrl-C\"||i==\"Ctrl-[\"||i==\"Backspace\"&&n==\"\"?(nt.searchHistoryController.pushInput(n),nt.searchHistoryController.reset(),An(e,o),Dn(e),e.scrollTo(u.left,u.top),v.e_stop(t),ut(e),r(),e.focus()):i==\"Ctrl-U\"&&(v.e_stop(t),r(\"\"))}if(!e.getSearchCursor)return;var r=n.searchArgs.forward,i=n.searchArgs.wholeWordOnly;dn(e).setReversed(!r);var s=r?\"/\":\"?\",o=dn(e).getQuery(),u=e.getScrollInfo();switch(n.searchArgs.querySrc){case\"prompt\":var h=nt.macroModeState;if(h.isPlaying){var p=h.replaySearchQueries.shift();a(p,!0,!1)}else kn(e,{onClose:f,prefix:s,desc:Cn,onKeyUp:l,onKeyDown:c});break;case\"wordUnderCursor\":var d=Gt(e,!1,!0,!1,!0),m=!0;d||(d=Gt(e,!1,!0,!1,!1),m=!1);if(!d)return;var p=e.getLine(d.start.line).substring(d.start.ch,d.end.ch);m&&i?p=\"\\\\b\"+p+\"\\\\b\":p=Bt(p),nt.jumpList.cachedCursor=e.getCursor(),e.setCursor(d.start),a(p,!0,!1)}},processEx:function(e,t,n){function r(t){nt.exCommandHistoryController.pushInput(t),nt.exCommandHistoryController.reset(),Fn.processCommand(e,t)}function i(t,n,r){var i=v.keyName(t),s;if(i==\"Esc\"||i==\"Ctrl-C\"||i==\"Ctrl-[\"||i==\"Backspace\"&&n==\"\")nt.exCommandHistoryController.pushInput(n),nt.exCommandHistoryController.reset(),v.e_stop(t),ut(e),r(),e.focus();i==\"Up\"||i==\"Down\"?(s=i==\"Up\"?!0:!1,n=nt.exCommandHistoryController.nextMatch(n,s)||\"\",r(n)):i==\"Ctrl-U\"?(v.e_stop(t),r(\"\")):i!=\"Left\"&&i!=\"Right\"&&i!=\"Ctrl\"&&i!=\"Alt\"&&i!=\"Shift\"&&nt.exCommandHistoryController.reset()}n.type==\"keyToEx\"?Fn.processCommand(e,n.exArgs.input):t.visualMode?kn(e,{onClose:r,prefix:\":\",value:\"'<,'>\",onKeyDown:i}):kn(e,{onClose:r,prefix:\":\",onKeyDown:i})},evalInput:function(e,t){var n=t.inputState,r=n.motion,i=n.motionArgs||{},s=n.operator,o=n.operatorArgs||{},u=n.registerName,a=t.sel,f=Lt(t.visualMode?wt(e,a.head):e.getCursor(\"head\")),l=Lt(t.visualMode?wt(e,a.anchor):e.getCursor(\"anchor\")),c=Lt(f),h=Lt(l),p,d,v;s&&this.recordLastEdit(t,n),n.repeatOverride!==undefined?v=n.repeatOverride:v=n.getRepeat();if(v>0&&i.explicitRepeat)i.repeatIsExplicit=!0;else if(i.noRepeat||!i.explicitRepeat&&v===0)v=1,i.repeatIsExplicit=!1;n.selectedCharacter&&(i.selectedCharacter=o.selectedCharacter=n.selectedCharacter),i.repeat=v,ut(e);if(r){var m=pt[r](e,f,i,t);t.lastMotion=pt[r];if(!m)return;if(i.toJumplist){!s&&e.ace.curOp!=null&&(e.ace.curOp.command.scrollIntoView=\"center-animate\");var g=nt.jumpList,y=g.cachedCursor;y?(Yt(e,y,m),delete g.cachedCursor):Yt(e,f,m)}m instanceof Array?(d=m[0],p=m[1]):p=m,p||(p=Lt(f));if(t.visualMode){if(!t.visualBlock||p.ch!==Infinity)p=wt(e,p,t.visualBlock);d&&(d=wt(e,d,!0)),d=d||h,a.anchor=d,a.head=p,Wt(e),an(e,t,\"<\",Ot(d,p)?d:p),an(e,t,\">\",Ot(d,p)?p:d)}else s||(p=wt(e,p),e.setCursor(p.line,p.ch))}if(s){if(o.lastSel){d=h;var b=o.lastSel,w=Math.abs(b.head.line-b.anchor.line),S=Math.abs(b.head.ch-b.anchor.ch);b.visualLine?p=E(h.line+w,h.ch):b.visualBlock?p=E(h.line+w,h.ch+S):b.head.line==b.anchor.line?p=E(h.line,h.ch+S):p=E(h.line+w,h.ch),t.visualMode=!0,t.visualLine=b.visualLine,t.visualBlock=b.visualBlock,a=t.sel={anchor:d,head:p},Wt(e)}else t.visualMode&&(o.lastSel={anchor:Lt(a.anchor),head:Lt(a.head),visualBlock:t.visualBlock,visualLine:t.visualLine});var x,T,N,C,k;if(t.visualMode){x=Mt(a.head,a.anchor),T=_t(a.head,a.anchor),N=t.visualLine||o.linewise,C=t.visualBlock?\"block\":N?\"line\":\"char\",k=Xt(e,{anchor:x,head:T},C);if(N){var L=k.ranges;if(C==\"block\")for(var A=0;A<L.length;A++)L[A].head.ch=Pt(e,L[A].head.line);else C==\"line\"&&(L[0].head=E(L[0].head.line+1,0))}}else{x=Lt(d||h),T=Lt(p||c);if(Ot(T,x)){var O=x;x=T,T=O}N=i.linewise||o.linewise,N?Kt(e,x,T):i.forward&&Jt(e,x,T),C=\"char\";var M=!i.inclusive||N;k=Xt(e,{anchor:x,head:T},C,M)}e.setSelections(k.ranges,k.primary),t.lastMotion=null,o.repeat=v,o.registerName=u,o.linewise=N;var _=mt[s](e,o,k.ranges,h,p);t.visualMode&&$t(e,_!=null),_&&e.setCursor(_)}},recordLastEdit:function(e,t,n){var r=nt.macroModeState;if(r.isPlaying)return;e.lastEditInputState=t,e.lastEditActionCommand=n,r.lastInsertModeChanges.changes=[],r.lastInsertModeChanges.expectCursorActivityForChange=!1}},pt={moveToTopLine:function(e,t,n){var r=Hn(e).top+n.repeat-1;return E(r,Qt(e.getLine(r)))},moveToMiddleLine:function(e){var t=Hn(e),n=Math.floor((t.top+t.bottom)*.5);return E(n,Qt(e.getLine(n)))},moveToBottomLine:function(e,t,n){var r=Hn(e).bottom-n.repeat+1;return E(r,Qt(e.getLine(r)))},expandToLine:function(e,t,n){var r=t;return E(r.line+n.repeat-1,Infinity)},findNext:function(e,t,n){var r=dn(e),i=r.getQuery();if(!i)return;var s=!n.forward;return s=r.isReversed()?!s:s,Mn(e,i),_n(e,s,i,n.repeat)},goToMark:function(e,t,n,r){var i=r.marks[n.selectedCharacter];if(i){var s=i.find();return n.linewise?{line:s.line,ch:Qt(e.getLine(s.line))}:s}return null},moveToOtherHighlightedEnd:function(e,t,n,r){if(r.visualBlock&&n.sameLine){var i=r.sel;return[wt(e,E(i.anchor.line,i.head.ch)),wt(e,E(i.head.line,i.anchor.ch))]}return[r.sel.head,r.sel.anchor]},jumpToMark:function(e,t,n,r){var i=t;for(var s=0;s<n.repeat;s++){var o=i;for(var u in r.marks){if(!U(u))continue;var a=r.marks[u].find(),f=n.forward?Ot(a,o):Ot(o,a);if(f)continue;if(n.linewise&&a.line==o.line)continue;var l=At(o,i),c=n.forward?Dt(o,a,i):Dt(i,a,o);if(l||c)i=a}}return n.linewise&&(i=E(i.line,Qt(e.getLine(i.line)))),i},moveByCharacters:function(e,t,n){var r=t,i=n.repeat,s=n.forward?r.ch+i:r.ch-i;return E(r.line,s)},moveByLines:function(e,t,n,r){var i=t,s=i.ch;switch(r.lastMotion){case this.moveByLines:case this.moveByDisplayLines:case this.moveByScroll:case this.moveToColumn:case this.moveToEol:s=r.lastHPos;break;default:r.lastHPos=s}var o=n.repeat+(n.repeatOffset||0),u=n.forward?i.line+o:i.line-o,a=e.firstLine(),f=e.lastLine();if(u<a&&i.line==a||u>f&&i.line==f)return;var l=e.ace.session.getFoldLine(u);return l&&(n.forward?u>l.start.row&&(u=l.end.row+1):u=l.start.row),n.toFirstChar&&(s=Qt(e.getLine(u)),r.lastHPos=s),r.lastHSPos=e.charCoords(E(u,s),\"div\").left,E(u,s)},moveByDisplayLines:function(e,t,n,r){var i=t;switch(r.lastMotion){case this.moveByDisplayLines:case this.moveByScroll:case this.moveByLines:case this.moveToColumn:case this.moveToEol:break;default:r.lastHSPos=e.charCoords(i,\"div\").left}var s=n.repeat,o=e.findPosV(i,n.forward?s:-s,\"line\",r.lastHSPos);if(o.hitSide)if(n.forward)var u=e.charCoords(o,\"div\"),a={top:u.top+8,left:r.lastHSPos},o=e.coordsChar(a,\"div\");else{var f=e.charCoords(E(e.firstLine(),0),\"div\");f.left=r.lastHSPos,o=e.coordsChar(f,\"div\")}return r.lastHPos=o.ch,o},moveByPage:function(e,t,n){var r=t,i=n.repeat;return e.findPosV(r,n.forward?i:-i,\"page\")},moveByParagraph:function(e,t,n){var r=n.forward?1:-1;return ln(e,t,n.repeat,r)},moveByScroll:function(e,t,n,r){var i=e.getScrollInfo(),s=null,o=n.repeat;o||(o=i.clientHeight/(2*e.defaultTextHeight()));var u=e.charCoords(t,\"local\");n.repeat=o;var s=pt.moveByDisplayLines(e,t,n,r);if(!s)return null;var a=e.charCoords(s,\"local\");return e.scrollTo(null,i.top+a.top-u.top),s},moveByWords:function(e,t,n){return sn(e,t,n.repeat,!!n.forward,!!n.wordEnd,!!n.bigWord)},moveTillCharacter:function(e,t,n){var r=n.repeat,i=on(e,r,n.forward,n.selectedCharacter),s=n.forward?-1:1;return Zt(s,n),i?(i.ch+=s,i):null},moveToCharacter:function(e,t,n){var r=n.repeat;return Zt(0,n),on(e,r,n.forward,n.selectedCharacter)||t},moveToSymbol:function(e,t,n){var r=n.repeat;return nn(e,r,n.forward,n.selectedCharacter)||t},moveToColumn:function(e,t,n,r){var i=n.repeat;return r.lastHPos=i-1,r.lastHSPos=e.charCoords(t,\"div\").left,un(e,i)},moveToEol:function(e,t,n,r){var i=t;r.lastHPos=Infinity;var s=E(i.line+n.repeat-1,Infinity),o=e.clipPos(s);return o.ch--,r.lastHSPos=e.charCoords(o,\"div\").left,s},moveToFirstNonWhiteSpaceCharacter:function(e,t){var n=t;return E(n.line,Qt(e.getLine(n.line)))},moveToMatchedSymbol:function(e,t){var n=t,r=n.line,i=n.ch,s=e.getLine(r),o;do{o=s.charAt(i++);if(o&&z(o)){var u=e.getTokenTypeAt(E(r,i));if(u!==\"string\"&&u!==\"comment\")break}}while(o);if(o){var a=e.findMatchingBracket(E(r,i));return a.to}return n},moveToStartOfLine:function(e,t){return E(t.line,0)},moveToLineOrEdgeOfDocument:function(e,t,n){var r=n.forward?e.lastLine():e.firstLine();return n.repeatIsExplicit&&(r=n.repeat-e.getOption(\"firstLineNumber\")),E(r,Qt(e.getLine(r)))},textObjectManipulation:function(e,t,n,r){var i={\"(\":\")\",\")\":\"(\",\"{\":\"}\",\"}\":\"{\",\"[\":\"]\",\"]\":\"[\"},s={\"'\":!0,'\"':!0},o=n.selectedCharacter;o==\"b\"?o=\"(\":o==\"B\"&&(o=\"{\");var u=!n.textObjectInner,a;if(i[o])a=cn(e,t,o,u);else if(s[o])a=hn(e,t,o,u);else if(o===\"W\")a=Gt(e,u,!0,!0);else if(o===\"w\")a=Gt(e,u,!0,!1);else{if(o!==\"p\")return null;a=ln(e,t,n.repeat,0,u),n.linewise=!0;if(r.visualMode)r.visualLine||(r.visualLine=!0);else{var f=r.inputState.operatorArgs;f&&(f.linewise=!0),a.end.line--}}return e.state.vim.visualMode?zt(e,a.start,a.end):[a.start,a.end]},repeatLastCharacterSearch:function(e,t,n){var r=nt.lastChararacterSearch,i=n.repeat,s=n.forward===r.forward,o=(r.increment?1:0)*(s?-1:1);e.moveH(-o,\"char\"),n.inclusive=s?!0:!1;var u=on(e,i,s,r.selectedCharacter);return u?(u.ch+=o,u):(e.moveH(o,\"char\"),t)}},mt={change:function(e,t,n){var r,i,s=e.state.vim;nt.macroModeState.lastInsertModeChanges.inVisualBlock=s.visualBlock;if(!s.visualMode){var o=n[0].anchor,u=n[0].head;i=e.getRange(o,u);var a=s.lastEditInputState||{};if(a.motion==\"moveByWords\"&&!V(i)){var f=/\\s+$/.exec(i);f&&a.motionArgs&&a.motionArgs.forward&&(u=St(u,0,-f[0].length),i=i.slice(0,-f[0].length))}var l=new E(o.line-1,Number.MAX_VALUE),c=e.firstLine()==e.lastLine();u.line>e.lastLine()&&t.linewise&&!c?e.replaceRange(\"\",l,u):e.replaceRange(\"\",o,u),t.linewise&&(c||(e.setCursor(l),v.commands.newlineAndIndent(e)),o.ch=Number.MAX_VALUE),r=o}else{i=e.getSelection();var h=vt(\"\",n.length);e.replaceSelections(h),r=Mt(n[0].head,n[0].anchor)}nt.registerController.pushText(t.registerName,\"change\",i,t.linewise,n.length>1),yt.enterInsertMode(e,{head:r},e.state.vim)},\"delete\":function(e,t,n){var r,i,s=e.state.vim;if(!s.visualBlock){var o=n[0].anchor,u=n[0].head;t.linewise&&u.line!=e.firstLine()&&o.line==e.lastLine()&&o.line==u.line-1&&(o.line==e.firstLine()?o.ch=0:o=E(o.line-1,Pt(e,o.line-1))),i=e.getRange(o,u),e.replaceRange(\"\",o,u),r=o,t.linewise&&(r=pt.moveToFirstNonWhiteSpaceCharacter(e,o))}else{i=e.getSelection();var a=vt(\"\",n.length);e.replaceSelections(a),r=n[0].anchor}return nt.registerController.pushText(t.registerName,\"delete\",i,t.linewise,s.visualBlock),wt(e,r)},indent:function(e,t,n){var r=e.state.vim,i=n[0].anchor.line,s=r.visualBlock?n[n.length-1].anchor.line:n[0].head.line,o=r.visualMode?t.repeat:1;t.linewise&&s--;for(var u=i;u<=s;u++)for(var a=0;a<o;a++)e.indentLine(u,t.indentRight);return pt.moveToFirstNonWhiteSpaceCharacter(e,n[0].anchor)},changeCase:function(e,t,n,r,i){var s=e.getSelections(),o=[],u=t.toLower;for(var a=0;a<s.length;a++){var f=s[a],l=\"\";if(u===!0)l=f.toLowerCase();else if(u===!1)l=f.toUpperCase();else for(var c=0;c<f.length;c++){var h=f.charAt(c);l+=X(h)?h.toLowerCase():h.toUpperCase()}o.push(l)}return e.replaceSelections(o),t.shouldMoveCursor?i:!e.state.vim.visualMode&&t.linewise&&n[0].anchor.line+1==n[0].head.line?pt.moveToFirstNonWhiteSpaceCharacter(e,r):t.linewise?r:Mt(n[0].anchor,n[0].head)},yank:function(e,t,n,r){var i=e.state.vim,s=e.getSelection(),o=i.visualMode?Mt(i.sel.anchor,i.sel.head,n[0].head,n[0].anchor):r;return nt.registerController.pushText(t.registerName,\"yank\",s,t.linewise,i.visualBlock),o}},yt={jumpListWalk:function(e,t,n){if(n.visualMode)return;var r=t.repeat,i=t.forward,s=nt.jumpList,o=s.move(e,i?r:-r),u=o?o.find():undefined;u=u?u:e.getCursor(),e.setCursor(u),e.ace.curOp.command.scrollIntoView=\"center-animate\"},scroll:function(e,t,n){if(n.visualMode)return;var r=t.repeat||1,i=e.defaultTextHeight(),s=e.getScrollInfo().top,o=i*r,u=t.forward?s+o:s-o,a=Lt(e.getCursor()),f=e.charCoords(a,\"local\");if(t.forward)u>f.top?(a.line+=(u-f.top)/i,a.line=Math.ceil(a.line),e.setCursor(a),f=e.charCoords(a,\"local\"),e.scrollTo(null,f.top)):e.scrollTo(null,u);else{var l=u+e.getScrollInfo().clientHeight;l<f.bottom?(a.line-=(f.bottom-l)/i,a.line=Math.floor(a.line),e.setCursor(a),f=e.charCoords(a,\"local\"),e.scrollTo(null,f.bottom-e.getScrollInfo().clientHeight)):e.scrollTo(null,u)}},scrollToCursor:function(e,t){var n=e.getCursor().line,r=e.charCoords(E(n,0),\"local\"),i=e.getScrollInfo().clientHeight,s=r.top,o=r.bottom-s;switch(t.position){case\"center\":s=s-i/2+o;break;case\"bottom\":s=s-i+o*1.4;break;case\"top\":s+=o*.4}e.scrollTo(null,s)},replayMacro:function(e,t,n){var r=t.selectedCharacter,i=t.repeat,s=nt.macroModeState;r==\"@\"&&(r=s.latestRegister);while(i--)zn(e,n,s,r)},enterMacroRecordMode:function(e,t){var n=nt.macroModeState,r=t.selectedCharacter;n.enterMacroRecordMode(e,r)},enterInsertMode:function(e,t,n){if(e.getOption(\"readOnly\"))return;n.insertMode=!0,n.insertModeRepeat=t&&t.repeat||1;var r=t?t.insertAt:null,i=n.sel,s=t.head||e.getCursor(\"head\"),o=e.listSelections().length;if(r==\"eol\")s=E(s.line,Pt(e,s.line));else if(r==\"charAfter\")s=St(s,0,1);else if(r==\"firstNonBlank\")s=pt.moveToFirstNonWhiteSpaceCharacter(e,s);else if(r==\"startOfSelectedArea\")n.visualBlock?(s=E(Math.min(i.head.line,i.anchor.line),Math.min(i.head.ch,i.anchor.ch)),o=Math.abs(i.head.line-i.anchor.line)+1):i.head.line<i.anchor.line?s=i.head:s=E(i.anchor.line,0);else if(r==\"endOfSelectedArea\")n.visualBlock?(s=E(Math.min(i.head.line,i.anchor.line),Math.max(i.head.ch+1,i.anchor.ch)),o=Math.abs(i.head.line-i.anchor.line)+1):i.head.line>=i.anchor.line?s=St(i.head,0,1):s=E(i.anchor.line,0);else if(r==\"inplace\"&&n.visualMode)return;e.setOption(\"keyMap\",\"vim-insert\"),e.setOption(\"disableInput\",!1),t&&t.replace?(e.toggleOverwrite(!0),e.setOption(\"keyMap\",\"vim-replace\"),v.signal(e,\"vim-mode-change\",{mode:\"replace\"})):(e.setOption(\"keyMap\",\"vim-insert\"),v.signal(e,\"vim-mode-change\",{mode:\"insert\"})),nt.macroModeState.isPlaying||(e.on(\"change\",$n),v.on(e.getInputField(),\"keydown\",Yn)),n.visualMode&&$t(e),It(e,s,o)},toggleVisualMode:function(e,t,n){var r=t.repeat,i=e.getCursor(),s;n.visualMode?n.visualLine^t.linewise||n.visualBlock^t.blockwise?(n.visualLine=!!t.linewise,n.visualBlock=!!t.blockwise,v.signal(e,\"vim-mode-change\",{mode:\"visual\",subMode:n.visualLine?\"linewise\":n.visualBlock?\"blockwise\":\"\"}),Wt(e)):$t(e):(n.visualMode=!0,n.visualLine=!!t.linewise,n.visualBlock=!!t.blockwise,s=wt(e,E(i.line,i.ch+r-1),!0),n.sel={anchor:i,head:s},v.signal(e,\"vim-mode-change\",{mode:\"visual\",subMode:n.visualLine?\"linewise\":n.visualBlock?\"blockwise\":\"\"}),Wt(e),an(e,n,\"<\",Mt(i,s)),an(e,n,\">\",_t(i,s)))},reselectLastSelection:function(e,t,n){var r=n.lastSelection;n.visualMode&&Ut(e,n);if(r){var i=r.anchorMark.find(),s=r.headMark.find();if(!i||!s)return;n.sel={anchor:i,head:s},n.visualMode=!0,n.visualLine=r.visualLine,n.visualBlock=r.visualBlock,Wt(e),an(e,n,\"<\",Mt(i,s)),an(e,n,\">\",_t(i,s)),v.signal(e,\"vim-mode-change\",{mode:\"visual\",subMode:n.visualLine?\"linewise\":n.visualBlock?\"blockwise\":\"\"})}},joinLines:function(e,t,n){var r,i;if(n.visualMode){r=e.getCursor(\"anchor\"),i=e.getCursor(\"head\");if(Ot(i,r)){var s=i;i=r,r=s}i.ch=Pt(e,i.line)-1}else{var o=Math.max(t.repeat,2);r=e.getCursor(),i=wt(e,E(r.line+o-1,Infinity))}var u=0;for(var a=r.line;a<i.line;a++){u=Pt(e,r.line);var s=E(r.line+1,Pt(e,r.line+1)),f=e.getRange(r,s);f=f.replace(/\\n\\s*/g,\" \"),e.replaceRange(f,r,s)}var l=E(r.line,u);n.visualMode&&$t(e,!1),e.setCursor(l)},newLineAndEnterInsertMode:function(e,t,n){n.insertMode=!0;var r=Lt(e.getCursor());if(r.line===e.firstLine()&&!t.after)e.replaceRange(\"\\n\",E(e.firstLine(),0)),e.setCursor(e.firstLine(),0);else{r.line=t.after?r.line:r.line-1,r.ch=Pt(e,r.line),e.setCursor(r);var i=v.commands.newlineAndIndentContinueComment||v.commands.newlineAndIndent;i(e)}this.enterInsertMode(e,{repeat:t.repeat},n)},paste:function(e,t,n){var r=Lt(e.getCursor()),i=nt.registerController.getRegister(t.registerName),s=i.toString();if(!s)return;if(t.matchIndent){var o=e.getOption(\"tabSize\"),u=function(e){var t=e.split(\"\t\").length-1,n=e.split(\" \").length-1;return t*o+n*1},a=e.getLine(e.getCursor().line),f=u(a.match(/^\\s*/)[0]),l=s.replace(/\\n$/,\"\"),c=s!==l,h=u(s.match(/^\\s*/)[0]),s=l.replace(/^\\s*/gm,function(t){var n=f+(u(t)-h);if(n<0)return\"\";if(e.getOption(\"indentWithTabs\")){var r=Math.floor(n/o);return Array(r+1).join(\"\t\")}return Array(n+1).join(\" \")});s+=c?\"\\n\":\"\"}if(t.repeat>1)var s=Array(t.repeat+1).join(s);var p=i.linewise,d=i.blockwise;if(p&&!d)n.visualMode?s=n.visualLine?s.slice(0,-1):\"\\n\"+s.slice(0,s.length-1)+\"\\n\":t.after?(s=\"\\n\"+s.slice(0,s.length-1),r.ch=Pt(e,r.line)):r.ch=0;else{if(d){s=s.split(\"\\n\");for(var v=0;v<s.length;v++)s[v]=s[v]==\"\"?\" \":s[v]}r.ch+=t.after?1:0}var m,g;if(n.visualMode){n.lastPastedText=s;var y,b=Rt(e,n),w=b[0],S=b[1],x=e.getSelection(),T=e.listSelections(),N=(new Array(T.length)).join(\"1\").split(\"1\");n.lastSelection&&(y=n.lastSelection.headMark.find()),nt.registerController.unnamedRegister.setText(x),d?(e.replaceSelections(N),S=E(w.line+s.length-1,w.ch),e.setCursor(w),Ft(e,S),e.replaceSelections(s),m=w):n.visualBlock?(e.replaceSelections(N),e.setCursor(w),e.replaceRange(s,w,w),m=w):(e.replaceRange(s,w,S),m=e.posFromIndex(e.indexFromPos(w)+s.length-1)),y&&(n.lastSelection.headMark=e.setBookmark(y)),p&&(m.ch=0)}else if(d){e.setCursor(r);for(var v=0;v<s.length;v++){var C=r.line+v;C>e.lastLine()&&e.replaceRange(\"\\n\",E(C,0));var k=Pt(e,C);k<r.ch&&jt(e,C,r.ch)}e.setCursor(r),Ft(e,E(r.line+s.length-1,r.ch)),e.replaceSelections(s),m=r}else e.replaceRange(s,r),p&&t.after?m=E(r.line+1,Qt(e.getLine(r.line+1))):p&&!t.after?m=E(r.line,Qt(e.getLine(r.line))):!p&&t.after?(g=e.indexFromPos(r),m=e.posFromIndex(g+s.length-1)):(g=e.indexFromPos(r),m=e.posFromIndex(g+s.length));n.visualMode&&$t(e,!1),e.setCursor(m)},undo:function(e,t){e.operation(function(){kt(e,v.commands.undo,t.repeat)(),e.setCursor(e.getCursor(\"anchor\"))})},redo:function(e,t){kt(e,v.commands.redo,t.repeat)()},setRegister:function(e,t,n){n.inputState.registerName=t.selectedCharacter},setMark:function(e,t,n){var r=t.selectedCharacter;an(e,n,r,e.getCursor())},replace:function(e,t,n){var r=t.selectedCharacter,i=e.getCursor(),s,o,u=e.listSelections();if(n.visualMode)i=e.getCursor(\"start\"),o=e.getCursor(\"end\");else{var a=e.getLine(i.line);s=i.ch+t.repeat,s>a.length&&(s=a.length),o=E(i.line,s)}if(r==\"\\n\")n.visualMode||e.replaceRange(\"\",i,o),(v.commands.newlineAndIndentContinueComment||v.commands.newlineAndIndent)(e);else{var f=e.getRange(i,o);f=f.replace(/[^\\n]/g,r);if(n.visualBlock){var l=(new Array(e.getOption(\"tabSize\")+1)).join(\" \");f=e.getSelection(),f=f.replace(/\\t/g,l).replace(/[^\\n]/g,r).split(\"\\n\"),e.replaceSelections(f)}else e.replaceRange(f,i,o);n.visualMode?(i=Ot(u[0].anchor,u[0].head)?u[0].anchor:u[0].head,e.setCursor(i),$t(e,!1)):e.setCursor(St(o,0,-1))}},incrementNumberToken:function(e,t){var n=e.getCursor(),r=e.getLine(n.line),i=/-?\\d+/g,s,o,u,a,f;while((s=i.exec(r))!==null){f=s[0],o=s.index,u=o+f.length;if(n.ch<u)break}if(!t.backtrack&&u<=n.ch)return;if(!f)return;var l=t.increase?1:-1,c=parseInt(f)+l*t.repeat,h=E(n.line,o),p=E(n.line,u);a=c.toString(),e.replaceRange(a,h,p),e.setCursor(E(n.line,o+a.length-1))},repeatLastEdit:function(e,t,n){var r=n.lastEditInputState;if(!r)return;var i=t.repeat;i&&t.repeatIsExplicit?n.lastEditInputState.repeatOverride=i:i=n.lastEditInputState.repeatOverride||i,Zn(e,n,i,!1)},exitInsertMode:qn},en={\"(\":\"bracket\",\")\":\"bracket\",\"{\":\"bracket\",\"}\":\"bracket\",\"[\":\"section\",\"]\":\"section\",\"*\":\"comment\",\"/\":\"comment\",m:\"method\",M:\"method\",\"#\":\"preprocess\"},tn={bracket:{isComplete:function(e){if(e.nextCh===e.symb){e.depth++;if(e.depth>=1)return!0}else e.nextCh===e.reverseSymb&&e.depth--;return!1}},section:{init:function(e){e.curMoveThrough=!0,e.symb=(e.forward?\"]\":\"[\")===e.symb?\"{\":\"}\"},isComplete:function(e){return e.index===0&&e.nextCh===e.symb}},comment:{isComplete:function(e){var t=e.lastCh===\"*\"&&e.nextCh===\"/\";return e.lastCh=e.nextCh,t}},method:{init:function(e){e.symb=e.symb===\"m\"?\"{\":\"}\",e.reverseSymb=e.symb===\"{\"?\"}\":\"{\"},isComplete:function(e){return e.nextCh===e.symb?!0:!1}},preprocess:{init:function(e){e.index=0},isComplete:function(e){if(e.nextCh===\"#\"){var t=e.lineText.match(/#(\\w+)/)[1];if(t===\"endif\"){if(e.forward&&e.depth===0)return!0;e.depth++}else if(t===\"if\"){if(!e.forward&&e.depth===0)return!0;e.depth--}if(t===\"else\"&&e.depth===0)return!0}return!1}}};K(\"pcre\",!0,\"boolean\"),pn.prototype={getQuery:function(){return nt.query},setQuery:function(e){nt.query=e},getOverlay:function(){return this.searchOverlay},setOverlay:function(e){this.searchOverlay=e},isReversed:function(){return nt.isReversed},setReversed:function(e){nt.isReversed=e},getScrollbarAnnotate:function(){return this.annotate},setScrollbarAnnotate:function(e){this.annotate=e}};var bn={\"\\\\n\":\"\\n\",\"\\\\r\":\"\\r\",\"\\\\t\":\"\t\"},En={\"\\\\/\":\"/\",\"\\\\\\\\\":\"\\\\\",\"\\\\n\":\"\\n\",\"\\\\r\":\"\\r\",\"\\\\t\":\"\t\"},Cn=\"(Javascript regexp)\",Bn=function(){this.buildCommandMap_()};Bn.prototype={processCommand:function(e,t,n){var r=this;e.operation(function(){e.curOp.isVimOp=!0,r._processCommand(e,t,n)})},_processCommand:function(e,t,n){var r=e.state.vim,i=nt.registerController.getRegister(\":\"),s=i.toString();r.visualMode&&$t(e);var o=new v.StringStream(t);i.setText(t);var u=n||{};u.input=t;try{this.parseInput_(e,o,u)}catch(a){throw Tn(e,a),a}var f,l;if(!u.commandName)u.line!==undefined&&(l=\"move\");else{f=this.matchCommand_(u.commandName);if(f){l=f.name,f.excludeFromCommandHistory&&i.setText(s),this.parseCommandArgs_(o,u,f);if(f.type==\"exToKey\"){for(var c=0;c<f.toKeys.length;c++)v.Vim.handleKey(e,f.toKeys[c],\"mapping\");return}if(f.type==\"exToEx\"){this.processCommand(e,f.toInput);return}}}if(!l){Tn(e,'Not an editor command \":'+t+'\"');return}try{jn[l](e,u),(!f||!f.possiblyAsync)&&u.callback&&u.callback()}catch(a){throw Tn(e,a),a}},parseInput_:function(e,t,n){t.eatWhile(\":\"),t.eat(\"%\")?(n.line=e.firstLine(),n.lineEnd=e.lastLine()):(n.line=this.parseLineSpec_(e,t),n.line!==undefined&&t.eat(\",\")&&(n.lineEnd=this.parseLineSpec_(e,t)));var r=t.match(/^(\\w+)/);return r?n.commandName=r[1]:n.commandName=t.match(/.*/)[0],n},parseLineSpec_:function(e,t){var n=t.match(/^(\\d+)/);if(n)return parseInt(n[1],10)-1;switch(t.next()){case\".\":return e.getCursor().line;case\"$\":return e.lastLine();case\"'\":var r=e.state.vim.marks[t.next()];if(r&&r.find())return r.find().line;throw new Error(\"Mark not set\");default:return t.backUp(1),undefined}},parseCommandArgs_:function(e,t,n){if(e.eol())return;t.argString=e.match(/.*/)[0];var r=n.argDelimiter||/\\s+/,i=Ht(t.argString).split(r);i.length&&i[0]&&(t.args=i)},matchCommand_:function(e){for(var t=e.length;t>0;t--){var n=e.substring(0,t);if(this.commandMap_[n]){var r=this.commandMap_[n];if(r.name.indexOf(e)===0)return r}}return null},buildCommandMap_:function(){this.commandMap_={};for(var e=0;e<w.length;e++){var t=w[e],n=t.shortName||t.name;this.commandMap_[n]=t}},map:function(e,t,n){if(e!=\":\"&&e.charAt(0)==\":\"){if(n)throw Error(\"Mode not supported for ex mappings\");var r=e.substring(1);t!=\":\"&&t.charAt(0)==\":\"?this.commandMap_[r]={name:r,type:\"exToEx\",toInput:t.substring(1),user:!0}:this.commandMap_[r]={name:r,type:\"exToKey\",toKeys:t,user:!0}}else if(t!=\":\"&&t.charAt(0)==\":\"){var i={keys:e,type:\"keyToEx\",exArgs:{input:t.substring(1)},user:!0};n&&(i.context=n),b.unshift(i)}else{var i={keys:e,type:\"keyToKey\",toKeys:t,user:!0};n&&(i.context=n),b.unshift(i)}},unmap:function(e,t){if(e!=\":\"&&e.charAt(0)==\":\"){if(t)throw Error(\"Mode not supported for ex mappings\");var n=e.substring(1);if(this.commandMap_[n]&&this.commandMap_[n].user){delete this.commandMap_[n];return}}else{var r=e;for(var i=0;i<b.length;i++)if(r==b[i].keys&&b[i].context===t&&b[i].user){b.splice(i,1);return}}}};var jn={colorscheme:function(e,t){if(!t.args||t.args.length<1){Tn(e,e.getOption(\"theme\"));return}e.setOption(\"theme\",t.args[0])},map:function(e,t,n){var r=t.args;if(!r||r.length<2){e&&Tn(e,\"Invalid mapping: \"+t.input);return}Fn.map(r[0],r[1],n)},imap:function(e,t){this.map(e,t,\"insert\")},nmap:function(e,t){this.map(e,t,\"normal\")},vmap:function(e,t){this.map(e,t,\"visual\")},unmap:function(e,t,n){var r=t.args;if(!r||r.length<1){e&&Tn(e,\"No such mapping: \"+t.input);return}Fn.unmap(r[0],n)},move:function(e,t){ht.processCommand(e,e.state.vim,{type:\"motion\",motion:\"moveToLineOrEdgeOfDocument\",motionArgs:{forward:!1,explicitRepeat:!0,linewise:!0},repeatOverride:t.line+1})},set:function(e,t){var n=t.args,r=t.setCfg||{};if(!n||n.length<1){e&&Tn(e,\"Invalid mapping: \"+t.input);return}var i=n[0].split(\"=\"),s=i[0],o=i[1],u=!1;if(s.charAt(s.length-1)==\"?\"){if(o)throw Error(\"Trailing characters: \"+t.argString);s=s.substring(0,s.length-1),u=!0}o===undefined&&s.substring(0,2)==\"no\"&&(s=s.substring(2),o=!1);var a=J[s]&&J[s].type==\"boolean\";a&&o==undefined&&(o=!0);if(!a&&o===undefined||u){var f=G(s,e,r);f===!0||f===!1?Tn(e,\" \"+(f?\"\":\"no\")+s):Tn(e,\"  \"+s+\"=\"+f)}else Q(s,o,e,r)},setlocal:function(e,t){t.setCfg={scope:\"local\"},this.set(e,t)},setglobal:function(e,t){t.setCfg={scope:\"global\"},this.set(e,t)},registers:function(e,t){var n=t.args,r=nt.registerController.registers,i=\"----------Registers----------<br><br>\";if(!n)for(var s in r){var o=r[s].toString();o.length&&(i+='\"'+s+\"    \"+o+\"<br>\")}else{var s;n=n.join(\"\");for(var u=0;u<n.length;u++){s=n.charAt(u);if(!nt.registerController.isValidRegister(s))continue;var a=r[s]||new at;i+='\"'+s+\"    \"+a.toString()+\"<br>\"}}Tn(e,i)},sort:function(e,t){function o(){if(t.argString){var e=new v.StringStream(t.argString);e.eat(\"!\")&&(n=!0);if(e.eol())return;if(!e.eatSpace())return\"Invalid arguments\";var o=e.match(/[a-z]+/);if(o){o=o[0],r=o.indexOf(\"i\")!=-1,i=o.indexOf(\"u\")!=-1;var u=o.indexOf(\"d\")!=-1&&1,a=o.indexOf(\"x\")!=-1&&1,f=o.indexOf(\"o\")!=-1&&1;if(u+a+f>1)return\"Invalid arguments\";s=u&&\"decimal\"||a&&\"hex\"||f&&\"octal\"}if(e.match(/\\/.*\\//))return\"patterns not supported\"}}function b(e,t){if(n){var i;i=e,e=t,t=i}r&&(e=e.toLowerCase(),t=t.toLowerCase());var o=s&&p.exec(e),u=s&&p.exec(t);return o?(o=parseInt((o[1]+o[2]).toLowerCase(),d),u=parseInt((u[1]+u[2]).toLowerCase(),d),o-u):e<t?-1:1}var n,r,i,s,u=o();if(u){Tn(e,u+\": \"+t.argString);return}var a=t.line||e.firstLine(),f=t.lineEnd||t.line||e.lastLine();if(a==f)return;var l=E(a,0),c=E(f,Pt(e,f)),h=e.getRange(l,c).split(\"\\n\"),p=s==\"decimal\"?/(-?)([\\d]+)/:s==\"hex\"?/(-?)(?:0x)?([0-9a-f]+)/i:s==\"octal\"?/([0-7]+)/:null,d=s==\"decimal\"?10:s==\"hex\"?16:s==\"octal\"?8:null,m=[],g=[];if(s)for(var y=0;y<h.length;y++)p.exec(h[y])?m.push(h[y]):g.push(h[y]);else g=h;m.sort(b),g.sort(b),h=n?m.concat(g):g.concat(m);if(i){var w=h,S;h=[];for(var y=0;y<w.length;y++)w[y]!=S&&h.push(w[y]),S=w[y]}e.replaceRange(h.join(\"\\n\"),l,c)},global:function(e,t){var n=t.argString;if(!n){Tn(e,\"Regular Expression missing from global\");return}var r=t.line!==undefined?t.line:e.firstLine(),i=t.lineEnd||t.line||e.lastLine(),s=mn(n),o=n,u;s.length&&(o=s[0],u=s.slice(1,s.length).join(\"/\"));if(o)try{An(e,o,!0,!0)}catch(a){Tn(e,\"Invalid regex: \"+o);return}var f=dn(e).getQuery(),l=[],c=\"\";for(var h=r;h<=i;h++){var p=f.test(e.getLine(h));p&&(l.push(h+1),c+=e.getLine(h)+\"<br>\")}if(!u){Tn(e,c);return}var d=0,v=function(){if(d<l.length){var t=l[d]+u;Fn.processCommand(e,t,{callback:v})}d++};v()},substitute:function(e,t){if(!e.getSearchCursor)throw new Error(\"Search feature not available. Requires searchcursor.js or any other getSearchCursor implementation.\");var n=t.argString,r=n?mn(n):[],i,s=\"\",o,u,a,f=!1,l=!1;if(r.length)i=r[0],s=r[1],s!==undefined&&(G(\"pcre\")?s=Sn(s):s=wn(s),nt.lastSubstituteReplacePart=s),o=r[2]?r[2].split(\" \"):[];else if(n&&n.length){Tn(e,\"Substitutions should be of the form :s/pattern/replace/\");return}o&&(u=o[0],a=parseInt(o[1]),u&&(u.indexOf(\"c\")!=-1&&(f=!0,u.replace(\"c\",\"\")),u.indexOf(\"g\")!=-1&&(l=!0,u.replace(\"g\",\"\")),i=i+\"/\"+u));if(i)try{An(e,i,!0,!0)}catch(c){Tn(e,\"Invalid regex: \"+i);return}s=s||nt.lastSubstituteReplacePart;if(s===undefined){Tn(e,\"No previous substitute regular expression\");return}var h=dn(e),p=h.getQuery(),d=t.line!==undefined?t.line:e.getCursor().line,v=t.lineEnd||d;d==e.firstLine()&&v==e.lastLine()&&(v=Infinity),a&&(d=v,v=d+a-1);var m=wt(e,E(d,0)),g=e.getSearchCursor(p,m);In(e,f,l,d,v,g,p,s,t.callback)},redo:v.commands.redo,undo:v.commands.undo,write:function(e){v.commands.save?v.commands.save(e):e.save()},nohlsearch:function(e){Dn(e)},delmarks:function(e,t){if(!t.argString||!Ht(t.argString)){Tn(e,\"Argument required\");return}var n=e.state.vim,r=new v.StringStream(Ht(t.argString));while(!r.eol()){r.eatSpace();var i=r.pos;if(!r.match(/[a-zA-Z]/,!1)){Tn(e,\"Invalid argument: \"+t.argString.substring(i));return}var s=r.next();if(r.match(\"-\",!0)){if(!r.match(/[a-zA-Z]/,!1)){Tn(e,\"Invalid argument: \"+t.argString.substring(i));return}var o=s,u=r.next();if(!(U(o)&&U(u)||X(o)&&X(u))){Tn(e,\"Invalid argument: \"+o+\"-\");return}var a=o.charCodeAt(0),f=u.charCodeAt(0);if(a>=f){Tn(e,\"Invalid argument: \"+t.argString.substring(i));return}for(var l=0;l<=f-a;l++){var c=String.fromCharCode(a+l);delete n.marks[c]}}else delete n.marks[s]}}},Fn=new Bn;v.keyMap.vim={attach:C,detach:N,call:k},K(\"insertModeEscKeysTimeout\",200,\"number\"),v.keyMap[\"vim-insert\"]={\"Ctrl-N\":\"autocomplete\",\"Ctrl-P\":\"autocomplete\",Enter:function(e){var t=v.commands.newlineAndIndentContinueComment||v.commands.newlineAndIndent;t(e)},fallthrough:[\"default\"],attach:C,detach:N,call:k},v.keyMap[\"vim-replace\"]={Backspace:\"goCharLeft\",fallthrough:[\"vim-insert\"],attach:C,detach:N,call:k},rt(),v.Vim=S(),S=v.Vim;var tr={\"return\":\"CR\",backspace:\"BS\",\"delete\":\"Del\",esc:\"Esc\",left:\"Left\",right:\"Right\",up:\"Up\",down:\"Down\",space:\"Space\",home:\"Home\",end:\"End\",pageup:\"PageUp\",pagedown:\"PageDown\",enter:\"CR\"},rr=S.handleKey.bind(S);S.handleKey=function(e,t,n){return e.operation(function(){return rr(e,t,n)},!0)},t.CodeMirror=v;var or=S.maybeInitVimState_;t.handler={$id:\"ace/keyboard/vim\",drawCursor:function(e,t,n,r,s){var o=this.state.vim||{},u=n.characterWidth,a=n.lineHeight,f=t.top,l=t.left;if(!o.insertMode){var c=r.cursor?i.comparePoints(r.cursor,r.start)<=0:s.selection.isBackwards()||s.selection.isEmpty();!c&&l>u&&(l-=u)}!o.insertMode&&o.status&&(a/=2,f+=a),e.left=l+\"px\",e.top=f+\"px\",e.width=u+\"px\",e.height=a+\"px\"},handleKeyboard:function(e,t,n,r,i){var s=e.editor,o=s.state.cm,u=or(o);if(r==-1)return;if(n==\"c\"&&t==1){if(!c.isMac&&s.getCopyText())return s.once(\"copy\",function(){s.selection.clearSelection()}),{command:\"null\",passEvent:!0}}else u.insertMode||c.isMac&&this.handleMacRepeat(e,t,n)&&(t=-1,n=e.inputChar);if(t==-1||t&1||t===0&&n.length>1){var a=u.insertMode,f=nr(t,n,i||{});u.status==null&&(u.status=\"\");var l=sr(o,f,\"user\");u=or(o),l&&u.status!=null?u.status+=f:u.status==null&&(u.status=\"\"),o._signal(\"changeStatus\");if(!l&&(t!=-1||a))return;return{command:\"null\",passEvent:!l}}},attach:function(e){e.state||(e.state={});var t=new v(e);e.state.cm=t,e.$vimModeHandler=this,v.keyMap.vim.attach(t),or(t).status=null,t.on(\"vim-command-done\",function(){if(t.virtualSelectionMode())return;or(t).status=null,t.ace._signal(\"changeStatus\"),t.ace.session.markUndoGroup()}),t.on(\"changeStatus\",function(){t.ace.renderer.updateCursor(),t.ace._signal(\"changeStatus\")}),t.on(\"vim-mode-change\",function(){if(t.virtualSelectionMode())return;t.ace.renderer.setStyle(\"normal-mode\",!or(t).insertMode),t._signal(\"changeStatus\")}),t.ace.renderer.setStyle(\"normal-mode\",!or(t).insertMode),e.renderer.$cursorLayer.drawCursor=this.drawCursor.bind(t),this.updateMacCompositionHandlers(e,!0)},detach:function(e){var t=e.state.cm;v.keyMap.vim.detach(t),t.destroy(),e.state.cm=null,e.$vimModeHandler=null,e.renderer.$cursorLayer.drawCursor=null,e.renderer.setStyle(\"normal-mode\",!1),this.updateMacCompositionHandlers(e,!1)},getStatusText:function(e){var t=e.state.cm,n=or(t);if(n.insertMode)return\"INSERT\";var r=\"\";return n.visualMode&&(r+=\"VISUAL\",n.visualLine&&(r+=\" LINE\"),n.visualBlock&&(r+=\" BLOCK\")),n.status&&(r+=(r?\" \":\"\")+n.status),r},handleMacRepeat:function(e,t,n){if(t==-1)e.inputChar=n,e.lastEvent=\"input\";else if(e.inputChar&&e.$lastHash==t&&e.$lastKey==n){if(e.lastEvent==\"input\")e.lastEvent=\"input1\";else if(e.lastEvent==\"input1\")return!0}else e.$lastHash=t,e.$lastKey=n,e.lastEvent=\"keypress\"},updateMacCompositionHandlers:function(e,t){var n=function(t){var n=e.state.cm,r=or(n);if(!r.insertMode){var i=this.textInput.getElement();i.blur(),i.focus(),i.value=t}else this.onCompositionUpdateOrig(t)},r=function(t){var n=e.state.cm,r=or(n);r.insertMode||this.onCompositionStartOrig(t)};t?e.onCompositionUpdateOrig||(e.onCompositionUpdateOrig=e.onCompositionUpdate,e.onCompositionUpdate=n,e.onCompositionStartOrig=e.onCompositionStart,e.onCompositionStart=r):e.onCompositionUpdateOrig&&(e.onCompositionUpdate=e.onCompositionUpdateOrig,e.onCompositionUpdateOrig=null,e.onCompositionStart=e.onCompositionStartOrig,e.onCompositionStartOrig=null)}};var ur={getText:function(e,t){return(Math.abs(e.selection.lead.row-t)||t+1+(t<9?\"\\u00b7\":\"\"))+\"\"},getWidth:function(e,t,n){return e.getLength().toString().length*n.characterWidth},update:function(e,t){t.renderer.$loop.schedule(t.renderer.CHANGE_GUTTER)},attach:function(e){e.renderer.$gutterLayer.$renderer=this,e.on(\"changeSelection\",this.update)},detach:function(e){e.renderer.$gutterLayer.$renderer=null,e.off(\"changeSelection\",this.update)}};S.defineOption({name:\"wrap\",set:function(e,t){t&&t.ace.setOption(\"wrap\",e)},type:\"boolean\"},!1),S.defineEx(\"write\",\"w\",function(){console.log(\":write is not implemented\")}),b.push({keys:\"zc\",type:\"action\",action:\"fold\",actionArgs:{open:!1}},{keys:\"zC\",type:\"action\",action:\"fold\",actionArgs:{open:!1,all:!0}},{keys:\"zo\",type:\"action\",action:\"fold\",actionArgs:{open:!0}},{keys:\"zO\",type:\"action\",action:\"fold\",actionArgs:{open:!0,all:!0}},{keys:\"za\",type:\"action\",action:\"fold\",actionArgs:{toggle:!0}},{keys:\"zA\",type:\"action\",action:\"fold\",actionArgs:{toggle:!0,all:!0}},{keys:\"zf\",type:\"action\",action:\"fold\",actionArgs:{open:!0,all:!0}},{keys:\"zd\",type:\"action\",action:\"fold\",actionArgs:{open:!0,all:!0}},{keys:\"<C-A-k>\",type:\"action\",action:\"aceCommand\",actionArgs:{name:\"addCursorAbove\"}},{keys:\"<C-A-j>\",type:\"action\",action:\"aceCommand\",actionArgs:{name:\"addCursorBelow\"}},{keys:\"<C-A-S-k>\",type:\"action\",action:\"aceCommand\",actionArgs:{name:\"addCursorAboveSkipCurrent\"}},{keys:\"<C-A-S-j>\",type:\"action\",action:\"aceCommand\",actionArgs:{name:\"addCursorBelowSkipCurrent\"}},{keys:\"<C-A-h>\",type:\"action\",action:\"aceCommand\",actionArgs:{name:\"selectMoreBefore\"}},{keys:\"<C-A-l>\",type:\"action\",action:\"aceCommand\",actionArgs:{name:\"selectMoreAfter\"}},{keys:\"<C-A-S-h>\",type:\"action\",action:\"aceCommand\",actionArgs:{name:\"selectNextBefore\"}},{keys:\"<C-A-S-l>\",type:\"action\",action:\"aceCommand\",actionArgs:{name:\"selectNextAfter\"}}),yt.aceCommand=function(e,t,n){e.vimCmd=t,e.ace.inVirtualSelectionMode?e.ace.on(\"beforeEndOperation\",ar):ar(null,e.ace)},yt.fold=function(e,t,n){e.ace.execCommand([\"toggleFoldWidget\",\"toggleFoldWidget\",\"foldOther\",\"unfoldall\"][(t.all?2:0)+(t.open?1:0)])},t.handler.defaultKeymap=b,t.handler.actions=yt,t.Vim=S,S.map(\"Y\",\"yy\",\"normal\")})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-assembly_x86.js",
    "content": "define(\"ace/mode/assembly_x86_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"keyword.control.assembly\",regex:\"\\\\b(?:aaa|aad|aam|aas|adc|add|addpd|addps|addsd|addss|addsubpd|addsubps|aesdec|aesdeclast|aesenc|aesenclast|aesimc|aeskeygenassist|and|andpd|andps|andnpd|andnps|arpl|blendpd|blendps|blendvpd|blendvps|bound|bsf|bsr|bswap|bt|btc|btr|bts|cbw|cwde|cdqe|clc|cld|cflush|clts|cmc|cmov(?:n?e|ge?|ae?|le?|be?|n?o|n?z)|cmp|cmppd|cmpps|cmps|cnpsb|cmpsw|cmpsd|cmpsq|cmpss|cmpxchg|cmpxchg8b|cmpxchg16b|comisd|comiss|cpuid|crc32|cvtdq2pd|cvtdq2ps|cvtpd2dq|cvtpd2pi|cvtpd2ps|cvtpi2pd|cvtpi2ps|cvtps2dq|cvtps2pd|cvtps2pi|cvtsd2si|cvtsd2ss|cvts2sd|cvtsi2ss|cvtss2sd|cvtss2si|cvttpd2dq|cvtpd2pi|cvttps2dq|cvttps2pi|cvttps2dq|cvttps2pi|cvttsd2si|cvttss2si|cwd|cdq|cqo|daa|das|dec|div|divpd|divps|divsd|divss|dppd|dpps|emms|enter|extractps|f2xm1|fabs|fadd|faddp|fiadd|fbld|fbstp|fchs|fclex|fnclex|fcmov(?:n?e|ge?|ae?|le?|be?|n?o|n?z)|fcom|fcmop|fcompp|fcomi|fcomip|fucomi|fucomip|fcos|fdecstp|fdiv|fdivp|fidiv|fdivr|fdivrp|fidivr|ffree|ficom|ficomp|fild|fincstp|finit|fnint|fist|fistp|fisttp|fld|fld1|fldl2t|fldl2e|fldpi|fldlg2|fldln2|fldz|fldcw|fldenv|fmul|fmulp|fimul|fnop|fpatan|fprem|fprem1|fptan|frndint|frstor|fsave|fnsave|fscale|fsin|fsincos|fsqrt|fst|fstp|fstcw|fnstcw|fstenv|fnstenv|fsts|fnstsw|fsub|fsubp|fisub|fsubr|fsubrp|fisubr|ftst|fucom|fucomp|fucompp|fxam|fxch|fxrstor|fxsave|fxtract|fyl2x|fyl2xp1|haddpd|haddps|husbpd|hsubps|idiv|imul|in|inc|ins|insb|insw|insd|insertps|int|into|invd|invplg|invpcid|iret|iretd|iretq|lahf|lar|lddqu|ldmxcsr|lds|les|lfs|lgs|lss|lea|leave|lfence|lgdt|lidt|llgdt|lmsw|lock|lods|lodsb|lodsw|lodsd|lodsq|lsl|ltr|maskmovdqu|maskmovq|maxpd|maxps|maxsd|maxss|mfence|minpd|minps|minsd|minss|monitor|mov|movapd|movaps|movbe|movd|movq|movddup|movdqa|movdqu|movq2q|movhlps|movhpd|movhps|movlhps|movlpd|movlps|movmskpd|movmskps|movntdqa|movntdq|movnti|movntpd|movntps|movntq|movq|movq2dq|movs|movsb|movsw|movsd|movsq|movsd|movshdup|movsldup|movss|movsx|movsxd|movupd|movups|movzx|mpsadbw|mul|mulpd|mulps|mulsd|mulss|mwait|neg|not|or|orpd|orps|out|outs|outsb|outsw|outsd|pabsb|pabsw|pabsd|packsswb|packssdw|packusdw|packuswbpaddb|paddw|paddd|paddq|paddsb|paddsw|paddusb|paddusw|palignr|pand|pandn|pause|pavgb|pavgw|pblendvb|pblendw|pclmulqdq|pcmpeqb|pcmpeqw|pcmpeqd|pcmpeqq|pcmpestri|pcmpestrm|pcmptb|pcmptgw|pcmpgtd|pcmpgtq|pcmpistri|pcmpisrm|pextrb|pextrd|pextrq|pextrw|phaddw|phaddd|phaddsw|phinposuw|phsubw|phsubd|phsubsw|pinsrb|pinsrd|pinsrq|pinsrw|pmaddubsw|pmadddwd|pmaxsb|pmaxsd|pmaxsw|pmaxsw|pmaxub|pmaxud|pmaxuw|pminsb|pminsd|pminsw|pminub|pminud|pminuw|pmovmskb|pmovsx|pmovzx|pmuldq|pmulhrsw|pmulhuw|pmulhw|pmulld|pmullw|pmuludw|pop|popa|popad|popcnt|popf|popfd|popfq|por|prefetch|psadbw|pshufb|pshufd|pshufhw|pshuflw|pshufw|psignb|psignw|psignd|pslldq|psllw|pslld|psllq|psraw|psrad|psrldq|psrlw|psrld|psrlq|psubb|psubw|psubd|psubq|psubsb|psubsw|psubusb|psubusw|test|ptest|punpckhbw|punpckhwd|punpckhdq|punpckhddq|punpcklbw|punpcklwd|punpckldq|punpckldqd|push|pusha|pushad|pushf|pushfd|pxor|prcl|rcr|rol|ror|rcpps|rcpss|rdfsbase|rdgsbase|rdmsr|rdpmc|rdrand|rdtsc|rdtscp|rep|repe|repz|repne|repnz|roundpd|roundps|roundsd|roundss|rsm|rsqrps|rsqrtss|sahf|sal|sar|shl|shr|sbb|scas|scasb|scasw|scasd|set(?:n?e|ge?|ae?|le?|be?|n?o|n?z)|sfence|sgdt|shld|shrd|shufpd|shufps|sidt|sldt|smsw|sqrtpd|sqrtps|sqrtsd|sqrtss|stc|std|stmxcsr|stos|stosb|stosw|stosd|stosq|str|sub|subpd|subps|subsd|subss|swapgs|syscall|sysenter|sysexit|sysret|teset|ucomisd|ucomiss|ud2|unpckhpd|unpckhps|unpcklpd|unpcklps|vbroadcast|vcvtph2ps|vcvtp2sph|verr|verw|vextractf128|vinsertf128|vmaskmov|vpermilpd|vpermilps|vperm2f128|vtestpd|vtestps|vzeroall|vzeroupper|wait|fwait|wbinvd|wrfsbase|wrgsbase|wrmsr|xadd|xchg|xgetbv|xlat|xlatb|xor|xorpd|xorps|xrstor|xsave|xsaveopt|xsetbv|lzcnt|extrq|insertq|movntsd|movntss|vfmaddpd|vfmaddps|vfmaddsd|vfmaddss|vfmaddsubbpd|vfmaddsubps|vfmsubaddpd|vfmsubaddps|vfmsubpd|vfmsubps|vfmsubsd|vfnmaddpd|vfnmaddps|vfnmaddsd|vfnmaddss|vfnmsubpd|vfnmusbps|vfnmusbsd|vfnmusbss|cvt|xor|cli|sti|hlt|nop|lock|wait|enter|leave|ret|loop(?:n?e|n?z)?|call|j(?:mp|n?e|ge?|ae?|le?|be?|n?o|n?z))\\\\b\",caseInsensitive:!0},{token:\"variable.parameter.register.assembly\",regex:\"\\\\b(?:CS|DS|ES|FS|GS|SS|RAX|EAX|RBX|EBX|RCX|ECX|RDX|EDX|RCX|RIP|EIP|IP|RSP|ESP|SP|RSI|ESI|SI|RDI|EDI|DI|RFLAGS|EFLAGS|FLAGS|R8-15|(?:Y|X)MM(?:[0-9]|10|11|12|13|14|15)|(?:A|B|C|D)(?:X|H|L)|CR(?:[0-4]|DR(?:[0-7]|TR6|TR7|EFER)))\\\\b\",caseInsensitive:!0},{token:\"constant.character.decimal.assembly\",regex:\"\\\\b[0-9]+\\\\b\"},{token:\"constant.character.hexadecimal.assembly\",regex:\"\\\\b0x[A-F0-9]+\\\\b\",caseInsensitive:!0},{token:\"constant.character.hexadecimal.assembly\",regex:\"\\\\b[A-F0-9]+h\\\\b\",caseInsensitive:!0},{token:\"string.assembly\",regex:/'([^\\\\']|\\\\.)*'/},{token:\"string.assembly\",regex:/\"([^\\\\\"]|\\\\.)*\"/},{token:\"support.function.directive.assembly\",regex:\"^\\\\[\",push:[{token:\"support.function.directive.assembly\",regex:\"\\\\]$\",next:\"pop\"},{defaultToken:\"support.function.directive.assembly\"}]},{token:[\"support.function.directive.assembly\",\"support.function.directive.assembly\",\"entity.name.function.assembly\"],regex:\"(^struc)( )([_a-zA-Z][_a-zA-Z0-9]*)\"},{token:\"support.function.directive.assembly\",regex:\"^endstruc\\\\b\"},{token:[\"support.function.directive.assembly\",\"entity.name.function.assembly\",\"support.function.directive.assembly\",\"constant.character.assembly\"],regex:\"^(%macro )([_a-zA-Z][_a-zA-Z0-9]*)( )([0-9]+)\"},{token:\"support.function.directive.assembly\",regex:\"^%endmacro\"},{token:[\"text\",\"support.function.directive.assembly\",\"text\",\"entity.name.function.assembly\"],regex:\"(\\\\s*)(%define|%xdefine|%idefine|%undef|%assign|%defstr|%strcat|%strlen|%substr|%00|%0|%rotate|%rep|%endrep|%include|\\\\$\\\\$|\\\\$|%unmacro|%if|%elif|%else|%endif|%(?:el)?ifdef|%(?:el)?ifmacro|%(?:el)?ifctx|%(?:el)?ifidn|%(?:el)?ifidni|%(?:el)?ifid|%(?:el)?ifnum|%(?:el)?ifstr|%(?:el)?iftoken|%(?:el)?ifempty|%(?:el)?ifenv|%pathsearch|%depend|%use|%push|%pop|%repl|%arg|%stacksize|%local|%error|%warning|%fatal|%line|%!|%comment|%endcomment|__NASM_VERSION_ID__|__NASM_VER__|__FILE__|__LINE__|__BITS__|__OUTPUT_FORMAT__|__DATE__|__TIME__|__DATE_NUM__|_TIME__NUM__|__UTC_DATE__|__UTC_TIME__|__UTC_DATE_NUM__|__UTC_TIME_NUM__|__POSIX_TIME__|__PASS__|ISTRUC|AT|IEND|BITS 16|BITS 32|BITS 64|USE16|USE32|__SECT__|ABSOLUTE|EXTERN|GLOBAL|COMMON|CPU|FLOAT)\\\\b( ?)((?:[_a-zA-Z][_a-zA-Z0-9]*)?)\",caseInsensitive:!0},{token:\"support.function.directive.assembly\",regex:\"\\\\b(?:d[bwdqtoy]|res[bwdqto]|equ|times|align|alignb|sectalign|section|ptr|byte|word|dword|qword|incbin)\\\\b\",caseInsensitive:!0},{token:\"entity.name.function.assembly\",regex:\"^\\\\s*%%[\\\\w.]+?:$\"},{token:\"entity.name.function.assembly\",regex:\"^\\\\s*%\\\\$[\\\\w.]+?:$\"},{token:\"entity.name.function.assembly\",regex:\"^[\\\\w.]+?:\"},{token:\"entity.name.function.assembly\",regex:\"^[\\\\w.]+?\\\\b\"},{token:\"comment.assembly\",regex:\";.*$\"}]},this.normalizeRules()};s.metaData={fileTypes:[\"asm\"],name:\"Assembly x86\",scopeName:\"source.assembly\"},r.inherits(s,i),t.AssemblyX86HighlightRules=s}),define(\"ace/mode/folding/coffee\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=e(\"../../range\").Range,o=t.FoldMode=function(){};r.inherits(o,i),function(){this.getFoldWidgetRange=function(e,t,n){var r=this.indentationBlock(e,n);if(r)return r;var i=/\\S/,o=e.getLine(n),u=o.search(i);if(u==-1||o[u]!=\"#\")return;var a=o.length,f=e.getLength(),l=n,c=n;while(++n<f){o=e.getLine(n);var h=o.search(i);if(h==-1)continue;if(o[h]!=\"#\")break;c=n}if(c>l){var p=e.getLine(c).length;return new s(l,a,c,p)}},this.getFoldWidget=function(e,t,n){var r=e.getLine(n),i=r.search(/\\S/),s=e.getLine(n+1),o=e.getLine(n-1),u=o.search(/\\S/),a=s.search(/\\S/);if(i==-1)return e.foldWidgets[n-1]=u!=-1&&u<a?\"start\":\"\",\"\";if(u==-1){if(i==a&&r[i]==\"#\"&&s[i]==\"#\")return e.foldWidgets[n-1]=\"\",e.foldWidgets[n+1]=\"\",\"start\"}else if(u==i&&r[i]==\"#\"&&o[i]==\"#\"&&e.getLine(n-2).search(/\\S/)==-1)return e.foldWidgets[n-1]=\"start\",e.foldWidgets[n+1]=\"\",\"\";return u!=-1&&u<i?e.foldWidgets[n-1]=\"start\":e.foldWidgets[n-1]=\"\",i<a?\"start\":\"\"}}.call(o.prototype)}),define(\"ace/mode/assembly_x86\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/assembly_x86_highlight_rules\",\"ace/mode/folding/coffee\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./assembly_x86_highlight_rules\").AssemblyX86HighlightRules,o=e(\"./folding/coffee\").FoldMode,u=function(){this.HighlightRules=s,this.foldingRules=new o,this.$behaviour=this.$defaultBehaviour};r.inherits(u,i),function(){this.lineCommentStart=\";\",this.$id=\"ace/mode/assembly_x86\"}.call(u.prototype),t.Mode=u})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-c_cpp.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/c_cpp_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=t.cFunctions=\"\\\\b(?:hypot(?:f|l)?|s(?:scanf|ystem|nprintf|ca(?:nf|lb(?:n(?:f|l)?|ln(?:f|l)?))|i(?:n(?:h(?:f|l)?|f|l)?|gn(?:al|bit))|tr(?:s(?:tr|pn)|nc(?:py|at|mp)|c(?:spn|hr|oll|py|at|mp)|to(?:imax|d|u(?:l(?:l)?|max)|k|f|l(?:d|l)?)|error|pbrk|ftime|len|rchr|xfrm)|printf|et(?:jmp|vbuf|locale|buf)|qrt(?:f|l)?|w(?:scanf|printf)|rand)|n(?:e(?:arbyint(?:f|l)?|xt(?:toward(?:f|l)?|after(?:f|l)?))|an(?:f|l)?)|c(?:s(?:in(?:h(?:f|l)?|f|l)?|qrt(?:f|l)?)|cos(?:h(?:f)?|f|l)?|imag(?:f|l)?|t(?:ime|an(?:h(?:f|l)?|f|l)?)|o(?:s(?:h(?:f|l)?|f|l)?|nj(?:f|l)?|pysign(?:f|l)?)|p(?:ow(?:f|l)?|roj(?:f|l)?)|e(?:il(?:f|l)?|xp(?:f|l)?)|l(?:o(?:ck|g(?:f|l)?)|earerr)|a(?:sin(?:h(?:f|l)?|f|l)?|cos(?:h(?:f|l)?|f|l)?|tan(?:h(?:f|l)?|f|l)?|lloc|rg(?:f|l)?|bs(?:f|l)?)|real(?:f|l)?|brt(?:f|l)?)|t(?:ime|o(?:upper|lower)|an(?:h(?:f|l)?|f|l)?|runc(?:f|l)?|gamma(?:f|l)?|mp(?:nam|file))|i(?:s(?:space|n(?:ormal|an)|cntrl|inf|digit|u(?:nordered|pper)|p(?:unct|rint)|finite|w(?:space|c(?:ntrl|type)|digit|upper|p(?:unct|rint)|lower|al(?:num|pha)|graph|xdigit|blank)|l(?:ower|ess(?:equal|greater)?)|al(?:num|pha)|gr(?:eater(?:equal)?|aph)|xdigit|blank)|logb(?:f|l)?|max(?:div|abs))|di(?:v|fftime)|_Exit|unget(?:c|wc)|p(?:ow(?:f|l)?|ut(?:s|c(?:har)?|wc(?:har)?)|error|rintf)|e(?:rf(?:c(?:f|l)?|f|l)?|x(?:it|p(?:2(?:f|l)?|f|l|m1(?:f|l)?)?))|v(?:s(?:scanf|nprintf|canf|printf|w(?:scanf|printf))|printf|f(?:scanf|printf|w(?:scanf|printf))|w(?:scanf|printf)|a_(?:start|copy|end|arg))|qsort|f(?:s(?:canf|e(?:tpos|ek))|close|tell|open|dim(?:f|l)?|p(?:classify|ut(?:s|c|w(?:s|c))|rintf)|e(?:holdexcept|set(?:e(?:nv|xceptflag)|round)|clearexcept|testexcept|of|updateenv|r(?:aiseexcept|ror)|get(?:e(?:nv|xceptflag)|round))|flush|w(?:scanf|ide|printf|rite)|loor(?:f|l)?|abs(?:f|l)?|get(?:s|c|pos|w(?:s|c))|re(?:open|e|ad|xp(?:f|l)?)|m(?:in(?:f|l)?|od(?:f|l)?|a(?:f|l|x(?:f|l)?)?))|l(?:d(?:iv|exp(?:f|l)?)|o(?:ngjmp|cal(?:time|econv)|g(?:1(?:p(?:f|l)?|0(?:f|l)?)|2(?:f|l)?|f|l|b(?:f|l)?)?)|abs|l(?:div|abs|r(?:int(?:f|l)?|ound(?:f|l)?))|r(?:int(?:f|l)?|ound(?:f|l)?)|gamma(?:f|l)?)|w(?:scanf|c(?:s(?:s(?:tr|pn)|nc(?:py|at|mp)|c(?:spn|hr|oll|py|at|mp)|to(?:imax|d|u(?:l(?:l)?|max)|k|f|l(?:d|l)?|mbs)|pbrk|ftime|len|r(?:chr|tombs)|xfrm)|to(?:b|mb)|rtomb)|printf|mem(?:set|c(?:hr|py|mp)|move))|a(?:s(?:sert|ctime|in(?:h(?:f|l)?|f|l)?)|cos(?:h(?:f|l)?|f|l)?|t(?:o(?:i|f|l(?:l)?)|exit|an(?:h(?:f|l)?|2(?:f|l)?|f|l)?)|b(?:s|ort))|g(?:et(?:s|c(?:har)?|env|wc(?:har)?)|mtime)|r(?:int(?:f|l)?|ound(?:f|l)?|e(?:name|alloc|wind|m(?:ove|quo(?:f|l)?|ainder(?:f|l)?))|a(?:nd|ise))|b(?:search|towc)|m(?:odf(?:f|l)?|em(?:set|c(?:hr|py|mp)|move)|ktime|alloc|b(?:s(?:init|towcs|rtowcs)|towc|len|r(?:towc|len))))\\\\b\",u=function(){var e=\"break|case|continue|default|do|else|for|goto|if|_Pragma|return|switch|while|catch|operator|try|throw|using\",t=\"asm|__asm__|auto|bool|_Bool|char|_Complex|double|enum|float|_Imaginary|int|long|short|signed|struct|typedef|union|unsigned|void|class|wchar_t|template|char16_t|char32_t\",n=\"const|extern|register|restrict|static|volatile|inline|private|protected|public|friend|explicit|virtual|export|mutable|typename|constexpr|new|delete|alignas|alignof|decltype|noexcept|thread_local\",r=\"and|and_eq|bitand|bitor|compl|not|not_eq|or|or_eq|typeid|xor|xor_eqconst_cast|dynamic_cast|reinterpret_cast|static_cast|sizeof|namespace\",s=\"NULL|true|false|TRUE|FALSE|nullptr\",u=this.$keywords=this.createKeywordMapper({\"keyword.control\":e,\"storage.type\":t,\"storage.modifier\":n,\"keyword.operator\":r,\"variable.language\":\"this\",\"constant.language\":s},\"identifier\"),a=\"[a-zA-Z\\\\$_\\u00a1-\\uffff][a-zA-Z\\\\d\\\\$_\\u00a1-\\uffff]*\\\\b\",f=/\\\\(?:['\"?\\\\abfnrtv]|[0-7]{1,3}|x[a-fA-F\\d]{2}|u[a-fA-F\\d]{4}U[a-fA-F\\d]{8}|.)/.source;this.$rules={start:[{token:\"comment\",regex:\"//$\",next:\"start\"},{token:\"comment\",regex:\"//\",next:\"singleLineComment\"},i.getStartRule(\"doc-start\"),{token:\"comment\",regex:\"\\\\/\\\\*\",next:\"comment\"},{token:\"string\",regex:\"'(?:\"+f+\"|.)?'\"},{token:\"string.start\",regex:'\"',stateName:\"qqstring\",next:[{token:\"string\",regex:/\\\\\\s*$/,next:\"qqstring\"},{token:\"constant.language.escape\",regex:f},{token:\"constant.language.escape\",regex:/%[^'\"\\\\]/},{token:\"string.end\",regex:'\"|$',next:\"start\"},{defaultToken:\"string\"}]},{token:\"string.start\",regex:'R\"\\\\(',stateName:\"rawString\",next:[{token:\"string.end\",regex:'\\\\)\"',next:\"start\"},{defaultToken:\"string\"}]},{token:\"constant.numeric\",regex:\"0[xX][0-9a-fA-F]+(L|l|UL|ul|u|U|F|f|ll|LL|ull|ULL)?\\\\b\"},{token:\"constant.numeric\",regex:\"[+-]?\\\\d+(?:(?:\\\\.\\\\d*)?(?:[eE][+-]?\\\\d+)?)?(L|l|UL|ul|u|U|F|f|ll|LL|ull|ULL)?\\\\b\"},{token:\"keyword\",regex:\"#\\\\s*(?:include|import|pragma|line|define|undef)\\\\b\",next:\"directive\"},{token:\"keyword\",regex:\"#\\\\s*(?:endif|if|ifdef|else|elif|ifndef)\\\\b\"},{token:\"support.function.C99.c\",regex:o},{token:u,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\"},{token:\"keyword.operator\",regex:/--|\\+\\+|<<=|>>=|>>>=|<>|&&|\\|\\||\\?:|[*%\\/+\\-&\\^|~!<>=]=?/},{token:\"punctuation.operator\",regex:\"\\\\?|\\\\:|\\\\,|\\\\;|\\\\.\"},{token:\"paren.lparen\",regex:\"[[({]\"},{token:\"paren.rparen\",regex:\"[\\\\])}]\"},{token:\"text\",regex:\"\\\\s+\"}],comment:[{token:\"comment\",regex:\".*?\\\\*\\\\/\",next:\"start\"},{token:\"comment\",regex:\".+\"}],singleLineComment:[{token:\"comment\",regex:/\\\\$/,next:\"singleLineComment\"},{token:\"comment\",regex:/$/,next:\"start\"},{defaultToken:\"comment\"}],directive:[{token:\"constant.other.multiline\",regex:/\\\\/},{token:\"constant.other.multiline\",regex:/.*\\\\/},{token:\"constant.other\",regex:\"\\\\s*<.+?>\",next:\"start\"},{token:\"constant.other\",regex:'\\\\s*[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]',next:\"start\"},{token:\"constant.other\",regex:\"\\\\s*['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\",next:\"start\"},{token:\"constant.other\",regex:/[^\\\\\\/]+/,next:\"start\"}]},this.embedRules(i,\"doc-\",[i.getEndRule(\"start\")]),this.normalizeRules()};r.inherits(u,s),t.c_cppHighlightRules=u}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/c_cpp\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/c_cpp_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/range\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./c_cpp_highlight_rules\").c_cppHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../range\").Range,a=e(\"./behaviour/cstyle\").CstyleBehaviour,f=e(\"./folding/cstyle\").FoldMode,l=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new a,this.foldingRules=new f};r.inherits(l,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens,o=i.state;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"){var u=t.match(/^.*[\\{\\(\\[]\\s*$/);u&&(r+=n)}else if(e==\"doc-start\"){if(o==\"start\")return\"\";var u=t.match(/^\\s*(\\/?)\\*/);u&&(u[1]&&(r+=\" \"),r+=\"* \")}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.$id=\"ace/mode/c_cpp\"}.call(l.prototype),t.Mode=l})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-coffee.js",
    "content": "define(\"ace/mode/coffee_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";function s(){var e=\"[$A-Za-z_\\\\x7f-\\\\uffff][$\\\\w\\\\x7f-\\\\uffff]*\",t=\"this|throw|then|try|typeof|super|switch|return|break|by|continue|catch|class|in|instanceof|is|isnt|if|else|extends|for|own|finally|function|while|when|new|no|not|delete|debugger|do|loop|of|off|or|on|unless|until|and|yes\",n=\"true|false|null|undefined|NaN|Infinity\",r=\"case|const|default|function|var|void|with|enum|export|implements|interface|let|package|private|protected|public|static|yield\",i=\"Array|Boolean|Date|Function|Number|Object|RegExp|ReferenceError|String|Error|EvalError|InternalError|RangeError|ReferenceError|StopIteration|SyntaxError|TypeError|URIError|ArrayBuffer|Float32Array|Float64Array|Int16Array|Int32Array|Int8Array|Uint16Array|Uint32Array|Uint8Array|Uint8ClampedArray\",s=\"Math|JSON|isNaN|isFinite|parseInt|parseFloat|encodeURI|encodeURIComponent|decodeURI|decodeURIComponent|String|\",o=\"window|arguments|prototype|document\",u=this.createKeywordMapper({keyword:t,\"constant.language\":n,\"invalid.illegal\":r,\"language.support.class\":i,\"language.support.function\":s,\"variable.language\":o},\"identifier\"),a={token:[\"paren.lparen\",\"variable.parameter\",\"paren.rparen\",\"text\",\"storage.type\"],regex:/(?:(\\()((?:\"[^\")]*?\"|'[^')]*?'|\\/[^\\/)]*?\\/|[^()\"'\\/])*?)(\\))(\\s*))?([\\-=]>)/.source},f=/\\\\(?:x[0-9a-fA-F]{2}|u[0-9a-fA-F]{4}|[0-2][0-7]{0,2}|3[0-6][0-7]?|37[0-7]?|[4-7][0-7]?|.)/;this.$rules={start:[{token:\"constant.numeric\",regex:\"(?:0x[\\\\da-fA-F]+|(?:\\\\d+(?:\\\\.\\\\d+)?|\\\\.\\\\d+)(?:[eE][+-]?\\\\d+)?)\"},{stateName:\"qdoc\",token:\"string\",regex:\"'''\",next:[{token:\"string\",regex:\"'''\",next:\"start\"},{token:\"constant.language.escape\",regex:f},{defaultToken:\"string\"}]},{stateName:\"qqdoc\",token:\"string\",regex:'\"\"\"',next:[{token:\"string\",regex:'\"\"\"',next:\"start\"},{token:\"paren.string\",regex:\"#{\",push:\"start\"},{token:\"constant.language.escape\",regex:f},{defaultToken:\"string\"}]},{stateName:\"qstring\",token:\"string\",regex:\"'\",next:[{token:\"string\",regex:\"'\",next:\"start\"},{token:\"constant.language.escape\",regex:f},{defaultToken:\"string\"}]},{stateName:\"qqstring\",token:\"string.start\",regex:'\"',next:[{token:\"string.end\",regex:'\"',next:\"start\"},{token:\"paren.string\",regex:\"#{\",push:\"start\"},{token:\"constant.language.escape\",regex:f},{defaultToken:\"string\"}]},{stateName:\"js\",token:\"string\",regex:\"`\",next:[{token:\"string\",regex:\"`\",next:\"start\"},{token:\"constant.language.escape\",regex:f},{defaultToken:\"string\"}]},{regex:\"[{}]\",onMatch:function(e,t,n){this.next=\"\";if(e==\"{\"&&n.length)return n.unshift(\"start\",t),\"paren\";if(e==\"}\"&&n.length){n.shift(),this.next=n.shift()||\"\";if(this.next.indexOf(\"string\")!=-1)return\"paren.string\"}return\"paren\"}},{token:\"string.regex\",regex:\"///\",next:\"heregex\"},{token:\"string.regex\",regex:/(?:\\/(?![\\s=])[^[\\/\\n\\\\]*(?:(?:\\\\[\\s\\S]|\\[[^\\]\\n\\\\]*(?:\\\\[\\s\\S][^\\]\\n\\\\]*)*])[^[\\/\\n\\\\]*)*\\/)(?:[imgy]{0,4})(?!\\w)/},{token:\"comment\",regex:\"###(?!#)\",next:\"comment\"},{token:\"comment\",regex:\"#.*\"},{token:[\"punctuation.operator\",\"text\",\"identifier\"],regex:\"(\\\\.)(\\\\s*)(\"+r+\")\"},{token:\"punctuation.operator\",regex:\"\\\\.{1,3}\"},{token:[\"keyword\",\"text\",\"language.support.class\",\"text\",\"keyword\",\"text\",\"language.support.class\"],regex:\"(class)(\\\\s+)(\"+e+\")(?:(\\\\s+)(extends)(\\\\s+)(\"+e+\"))?\"},{token:[\"entity.name.function\",\"text\",\"keyword.operator\",\"text\"].concat(a.token),regex:\"(\"+e+\")(\\\\s*)([=:])(\\\\s*)\"+a.regex},a,{token:\"variable\",regex:\"@(?:\"+e+\")?\"},{token:u,regex:e},{token:\"punctuation.operator\",regex:\"\\\\,|\\\\.\"},{token:\"storage.type\",regex:\"[\\\\-=]>\"},{token:\"keyword.operator\",regex:\"(?:[-+*/%<>&|^!?=]=|>>>=?|\\\\-\\\\-|\\\\+\\\\+|::|&&=|\\\\|\\\\|=|<<=|>>=|\\\\?\\\\.|\\\\.{2,3}|[!*+-=><])\"},{token:\"paren.lparen\",regex:\"[({[]\"},{token:\"paren.rparen\",regex:\"[\\\\]})]\"},{token:\"text\",regex:\"\\\\s+\"}],heregex:[{token:\"string.regex\",regex:\".*?///[imgy]{0,4}\",next:\"start\"},{token:\"comment.regex\",regex:\"\\\\s+(?:#.*)?\"},{token:\"string.regex\",regex:\"\\\\S+\"}],comment:[{token:\"comment\",regex:\"###\",next:\"start\"},{defaultToken:\"comment\"}]},this.normalizeRules()}var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules;r.inherits(s,i),t.CoffeeHighlightRules=s}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/coffee\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=e(\"../../range\").Range,o=t.FoldMode=function(){};r.inherits(o,i),function(){this.getFoldWidgetRange=function(e,t,n){var r=this.indentationBlock(e,n);if(r)return r;var i=/\\S/,o=e.getLine(n),u=o.search(i);if(u==-1||o[u]!=\"#\")return;var a=o.length,f=e.getLength(),l=n,c=n;while(++n<f){o=e.getLine(n);var h=o.search(i);if(h==-1)continue;if(o[h]!=\"#\")break;c=n}if(c>l){var p=e.getLine(c).length;return new s(l,a,c,p)}},this.getFoldWidget=function(e,t,n){var r=e.getLine(n),i=r.search(/\\S/),s=e.getLine(n+1),o=e.getLine(n-1),u=o.search(/\\S/),a=s.search(/\\S/);if(i==-1)return e.foldWidgets[n-1]=u!=-1&&u<a?\"start\":\"\",\"\";if(u==-1){if(i==a&&r[i]==\"#\"&&s[i]==\"#\")return e.foldWidgets[n-1]=\"\",e.foldWidgets[n+1]=\"\",\"start\"}else if(u==i&&r[i]==\"#\"&&o[i]==\"#\"&&e.getLine(n-2).search(/\\S/)==-1)return e.foldWidgets[n-1]=\"start\",e.foldWidgets[n+1]=\"\",\"\";return u!=-1&&u<i?e.foldWidgets[n-1]=\"start\":e.foldWidgets[n-1]=\"\",i<a?\"start\":\"\"}}.call(o.prototype)}),define(\"ace/mode/coffee\",[\"require\",\"exports\",\"module\",\"ace/mode/coffee_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/mode/folding/coffee\",\"ace/range\",\"ace/mode/text\",\"ace/worker/worker_client\",\"ace/lib/oop\"],function(e,t,n){\"use strict\";function l(){this.HighlightRules=r,this.$outdent=new i,this.foldingRules=new s}var r=e(\"./coffee_highlight_rules\").CoffeeHighlightRules,i=e(\"./matching_brace_outdent\").MatchingBraceOutdent,s=e(\"./folding/coffee\").FoldMode,o=e(\"../range\").Range,u=e(\"./text\").Mode,a=e(\"../worker/worker_client\").WorkerClient,f=e(\"../lib/oop\");f.inherits(l,u),function(){var e=/(?:[({[=:]|[-=]>|\\b(?:else|try|(?:swi|ca)tch(?:\\s+[$A-Za-z_\\x7f-\\uffff][$\\w\\x7f-\\uffff]*)?|finally))\\s*$|^\\s*(else\\b\\s*)?(?:if|for|while|loop)\\b(?!.*\\bthen\\b)/;this.lineCommentStart=\"#\",this.blockComment={start:\"###\",end:\"###\"},this.getNextLineIndent=function(t,n,r){var i=this.$getIndent(n),s=this.getTokenizer().getLineTokens(n,t).tokens;return(!s.length||s[s.length-1].type!==\"comment\")&&t===\"start\"&&e.test(n)&&(i+=r),i},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.createWorker=function(e){var t=new a([\"ace\"],\"ace/mode/coffee_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/coffee\"}.call(l.prototype),t.Mode=l})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-csharp.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/csharp_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=function(){var e=this.createKeywordMapper({\"variable.language\":\"this\",keyword:\"abstract|event|new|struct|as|explicit|null|switch|base|extern|object|this|bool|false|operator|throw|break|finally|out|true|byte|fixed|override|try|case|float|params|typeof|catch|for|private|uint|char|foreach|protected|ulong|checked|goto|public|unchecked|class|if|readonly|unsafe|const|implicit|ref|ushort|continue|in|return|using|decimal|int|sbyte|virtual|default|interface|sealed|volatile|delegate|internal|short|void|do|is|sizeof|while|double|lock|stackalloc|else|long|static|enum|namespace|string|var|dynamic\",\"constant.language\":\"null|true|false\"},\"identifier\");this.$rules={start:[{token:\"comment\",regex:\"\\\\/\\\\/.*$\"},i.getStartRule(\"doc-start\"),{token:\"comment\",regex:\"\\\\/\\\\*\",next:\"comment\"},{token:\"string\",regex:/'(?:.|\\\\(:?u[\\da-fA-F]+|x[\\da-fA-F]+|[tbrf'\"n]))'/},{token:\"string\",start:'\"',end:'\"|$',next:[{token:\"constant.language.escape\",regex:/\\\\(:?u[\\da-fA-F]+|x[\\da-fA-F]+|[tbrf'\"n])/},{token:\"invalid\",regex:/\\\\./}]},{token:\"string\",start:'@\"',end:'\"',next:[{token:\"constant.language.escape\",regex:'\"\"'}]},{token:\"string\",start:/\\$\"/,end:'\"|$',next:[{token:\"constant.language.escape\",regex:/\\\\(:?$)|{{/},{token:\"constant.language.escape\",regex:/\\\\(:?u[\\da-fA-F]+|x[\\da-fA-F]+|[tbrf'\"n])/},{token:\"invalid\",regex:/\\\\./}]},{token:\"constant.numeric\",regex:\"0[xX][0-9a-fA-F]+\\\\b\"},{token:\"constant.numeric\",regex:\"[+-]?\\\\d+(?:(?:\\\\.\\\\d*)?(?:[eE][+-]?\\\\d+)?)?\\\\b\"},{token:\"constant.language.boolean\",regex:\"(?:true|false)\\\\b\"},{token:e,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"keyword.operator\",regex:\"!|\\\\$|%|&|\\\\*|\\\\-\\\\-|\\\\-|\\\\+\\\\+|\\\\+|~|===|==|=|!=|!==|<=|>=|<<=|>>=|>>>=|<>|<|>|!|&&|\\\\|\\\\||\\\\?\\\\:|\\\\*=|%=|\\\\+=|\\\\-=|&=|\\\\^=|\\\\b(?:in|instanceof|new|delete|typeof|void)\"},{token:\"keyword\",regex:\"^\\\\s*#(if|else|elif|endif|define|undef|warning|error|line|region|endregion|pragma)\"},{token:\"punctuation.operator\",regex:\"\\\\?|\\\\:|\\\\,|\\\\;|\\\\.\"},{token:\"paren.lparen\",regex:\"[[({]\"},{token:\"paren.rparen\",regex:\"[\\\\])}]\"},{token:\"text\",regex:\"\\\\s+\"}],comment:[{token:\"comment\",regex:\".*?\\\\*\\\\/\",next:\"start\"},{token:\"comment\",regex:\".+\"}]},this.embedRules(i,\"doc-\",[i.getEndRule(\"start\")]),this.normalizeRules()};r.inherits(o,s),t.CSharpHighlightRules=o}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/folding/csharp\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./cstyle\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.usingRe=/^\\s*using \\S/,this.getFoldWidgetRangeBase=this.getFoldWidgetRange,this.getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=this.getFoldWidgetBase(e,t,n);if(!r){var i=e.getLine(n);if(/^\\s*#region\\b/.test(i))return\"start\";var s=this.usingRe;if(s.test(i)){var o=e.getLine(n-1),u=e.getLine(n+1);if(!s.test(o)&&s.test(u))return\"start\"}}return r},this.getFoldWidgetRange=function(e,t,n){var r=this.getFoldWidgetRangeBase(e,t,n);if(r)return r;var i=e.getLine(n);if(this.usingRe.test(i))return this.getUsingStatementBlock(e,i,n);if(/^\\s*#region\\b/.test(i))return this.getRegionBlock(e,i,n)},this.getUsingStatementBlock=function(e,t,n){var r=t.match(this.usingRe)[0].length-1,s=e.getLength(),o=n,u=n;while(++n<s){t=e.getLine(n);if(/^\\s*$/.test(t))continue;if(!this.usingRe.test(t))break;u=n}if(u>o){var a=e.getLine(u).length;return new i(o,r,u,a)}},this.getRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*#(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/csharp\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/csharp_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/csharp\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./csharp_highlight_rules\").CSharpHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"./behaviour/cstyle\").CstyleBehaviour,a=e(\"./folding/csharp\").FoldMode,f=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new u,this.foldingRules=new a};r.inherits(f,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"){var o=t.match(/^.*[\\{\\(\\[]\\s*$/);o&&(r+=n)}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.createWorker=function(e){return null},this.$id=\"ace/mode/csharp\"}.call(f.prototype),t.Mode=f})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-css.js",
    "content": "define(\"ace/mode/css_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text_highlight_rules\").TextHighlightRules,o=t.supportType=\"align-content|align-items|align-self|all|animation|animation-delay|animation-direction|animation-duration|animation-fill-mode|animation-iteration-count|animation-name|animation-play-state|animation-timing-function|backface-visibility|background|background-attachment|background-blend-mode|background-clip|background-color|background-image|background-origin|background-position|background-repeat|background-size|border|border-bottom|border-bottom-color|border-bottom-left-radius|border-bottom-right-radius|border-bottom-style|border-bottom-width|border-collapse|border-color|border-image|border-image-outset|border-image-repeat|border-image-slice|border-image-source|border-image-width|border-left|border-left-color|border-left-style|border-left-width|border-radius|border-right|border-right-color|border-right-style|border-right-width|border-spacing|border-style|border-top|border-top-color|border-top-left-radius|border-top-right-radius|border-top-style|border-top-width|border-width|bottom|box-shadow|box-sizing|caption-side|clear|clip|color|column-count|column-fill|column-gap|column-rule|column-rule-color|column-rule-style|column-rule-width|column-span|column-width|columns|content|counter-increment|counter-reset|cursor|direction|display|empty-cells|filter|flex|flex-basis|flex-direction|flex-flow|flex-grow|flex-shrink|flex-wrap|float|font|font-family|font-size|font-size-adjust|font-stretch|font-style|font-variant|font-weight|hanging-punctuation|height|justify-content|left|letter-spacing|line-height|list-style|list-style-image|list-style-position|list-style-type|margin|margin-bottom|margin-left|margin-right|margin-top|max-height|max-width|min-height|min-width|nav-down|nav-index|nav-left|nav-right|nav-up|opacity|order|outline|outline-color|outline-offset|outline-style|outline-width|overflow|overflow-x|overflow-y|padding|padding-bottom|padding-left|padding-right|padding-top|page-break-after|page-break-before|page-break-inside|perspective|perspective-origin|position|quotes|resize|right|tab-size|table-layout|text-align|text-align-last|text-decoration|text-decoration-color|text-decoration-line|text-decoration-style|text-indent|text-justify|text-overflow|text-shadow|text-transform|top|transform|transform-origin|transform-style|transition|transition-delay|transition-duration|transition-property|transition-timing-function|unicode-bidi|vertical-align|visibility|white-space|width|word-break|word-spacing|word-wrap|z-index\",u=t.supportFunction=\"rgb|rgba|url|attr|counter|counters\",a=t.supportConstant=\"absolute|after-edge|after|all-scroll|all|alphabetic|always|antialiased|armenian|auto|avoid-column|avoid-page|avoid|balance|baseline|before-edge|before|below|bidi-override|block-line-height|block|bold|bolder|border-box|both|bottom|box|break-all|break-word|capitalize|caps-height|caption|center|central|char|circle|cjk-ideographic|clone|close-quote|col-resize|collapse|column|consider-shifts|contain|content-box|cover|crosshair|cubic-bezier|dashed|decimal-leading-zero|decimal|default|disabled|disc|disregard-shifts|distribute-all-lines|distribute-letter|distribute-space|distribute|dotted|double|e-resize|ease-in|ease-in-out|ease-out|ease|ellipsis|end|exclude-ruby|fill|fixed|georgian|glyphs|grid-height|groove|hand|hanging|hebrew|help|hidden|hiragana-iroha|hiragana|horizontal|icon|ideograph-alpha|ideograph-numeric|ideograph-parenthesis|ideograph-space|ideographic|inactive|include-ruby|inherit|initial|inline-block|inline-box|inline-line-height|inline-table|inline|inset|inside|inter-ideograph|inter-word|invert|italic|justify|katakana-iroha|katakana|keep-all|last|left|lighter|line-edge|line-through|line|linear|list-item|local|loose|lower-alpha|lower-greek|lower-latin|lower-roman|lowercase|lr-tb|ltr|mathematical|max-height|max-size|medium|menu|message-box|middle|move|n-resize|ne-resize|newspaper|no-change|no-close-quote|no-drop|no-open-quote|no-repeat|none|normal|not-allowed|nowrap|nw-resize|oblique|open-quote|outset|outside|overline|padding-box|page|pointer|pre-line|pre-wrap|pre|preserve-3d|progress|relative|repeat-x|repeat-y|repeat|replaced|reset-size|ridge|right|round|row-resize|rtl|s-resize|scroll|se-resize|separate|slice|small-caps|small-caption|solid|space|square|start|static|status-bar|step-end|step-start|steps|stretch|strict|sub|super|sw-resize|table-caption|table-cell|table-column-group|table-column|table-footer-group|table-header-group|table-row-group|table-row|table|tb-rl|text-after-edge|text-before-edge|text-bottom|text-size|text-top|text|thick|thin|transparent|underline|upper-alpha|upper-latin|upper-roman|uppercase|use-script|vertical-ideographic|vertical-text|visible|w-resize|wait|whitespace|z-index|zero\",f=t.supportConstantColor=\"aqua|black|blue|fuchsia|gray|green|lime|maroon|navy|olive|orange|purple|red|silver|teal|white|yellow\",l=t.supportConstantFonts=\"arial|century|comic|courier|cursive|fantasy|garamond|georgia|helvetica|impact|lucida|symbol|system|tahoma|times|trebuchet|utopia|verdana|webdings|sans-serif|serif|monospace\",c=t.numRe=\"\\\\-?(?:(?:[0-9]+)|(?:[0-9]*\\\\.[0-9]+))\",h=t.pseudoElements=\"(\\\\:+)\\\\b(after|before|first-letter|first-line|moz-selection|selection)\\\\b\",p=t.pseudoClasses=\"(:)\\\\b(active|checked|disabled|empty|enabled|first-child|first-of-type|focus|hover|indeterminate|invalid|last-child|last-of-type|link|not|nth-child|nth-last-child|nth-last-of-type|nth-of-type|only-child|only-of-type|required|root|target|valid|visited)\\\\b\",d=function(){var e=this.createKeywordMapper({\"support.function\":u,\"support.constant\":a,\"support.type\":o,\"support.constant.color\":f,\"support.constant.fonts\":l},\"text\",!0);this.$rules={start:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"@.*?{\",push:\"media\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],media:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"\\\\}\",next:\"pop\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],comment:[{token:\"comment\",regex:\"\\\\*\\\\/\",next:\"pop\"},{defaultToken:\"comment\"}],ruleset:[{token:\"paren.rparen\",regex:\"\\\\}\",next:\"pop\"},{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},{token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},{token:[\"constant.numeric\",\"keyword\"],regex:\"(\"+c+\")(ch|cm|deg|em|ex|fr|gd|grad|Hz|in|kHz|mm|ms|pc|pt|px|rad|rem|s|turn|vh|vm|vw|%)\"},{token:\"constant.numeric\",regex:c},{token:\"constant.numeric\",regex:\"#[a-f0-9]{6}\"},{token:\"constant.numeric\",regex:\"#[a-f0-9]{3}\"},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-element.css\"],regex:h},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-class.css\"],regex:p},{token:[\"support.function\",\"string\",\"support.function\"],regex:\"(url\\\\()(.*)(\\\\))\"},{token:e,regex:\"\\\\-?[a-zA-Z_][a-zA-Z0-9_\\\\-]*\"},{caseInsensitive:!0}]},this.normalizeRules()};r.inherits(d,s),t.CssHighlightRules=d}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/css_completions\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={background:{\"#$0\":1},\"background-color\":{\"#$0\":1,transparent:1,fixed:1},\"background-image\":{\"url('/$0')\":1},\"background-repeat\":{repeat:1,\"repeat-x\":1,\"repeat-y\":1,\"no-repeat\":1,inherit:1},\"background-position\":{bottom:2,center:2,left:2,right:2,top:2,inherit:2},\"background-attachment\":{scroll:1,fixed:1},\"background-size\":{cover:1,contain:1},\"background-clip\":{\"border-box\":1,\"padding-box\":1,\"content-box\":1},\"background-origin\":{\"border-box\":1,\"padding-box\":1,\"content-box\":1},border:{\"solid $0\":1,\"dashed $0\":1,\"dotted $0\":1,\"#$0\":1},\"border-color\":{\"#$0\":1},\"border-style\":{solid:2,dashed:2,dotted:2,\"double\":2,groove:2,hidden:2,inherit:2,inset:2,none:2,outset:2,ridged:2},\"border-collapse\":{collapse:1,separate:1},bottom:{px:1,em:1,\"%\":1},clear:{left:1,right:1,both:1,none:1},color:{\"#$0\":1,\"rgb(#$00,0,0)\":1},cursor:{\"default\":1,pointer:1,move:1,text:1,wait:1,help:1,progress:1,\"n-resize\":1,\"ne-resize\":1,\"e-resize\":1,\"se-resize\":1,\"s-resize\":1,\"sw-resize\":1,\"w-resize\":1,\"nw-resize\":1},display:{none:1,block:1,inline:1,\"inline-block\":1,\"table-cell\":1},\"empty-cells\":{show:1,hide:1},\"float\":{left:1,right:1,none:1},\"font-family\":{Arial:2,\"Comic Sans MS\":2,Consolas:2,\"Courier New\":2,Courier:2,Georgia:2,Monospace:2,\"Sans-Serif\":2,\"Segoe UI\":2,Tahoma:2,\"Times New Roman\":2,\"Trebuchet MS\":2,Verdana:1},\"font-size\":{px:1,em:1,\"%\":1},\"font-weight\":{bold:1,normal:1},\"font-style\":{italic:1,normal:1},\"font-variant\":{normal:1,\"small-caps\":1},height:{px:1,em:1,\"%\":1},left:{px:1,em:1,\"%\":1},\"letter-spacing\":{normal:1},\"line-height\":{normal:1},\"list-style-type\":{none:1,disc:1,circle:1,square:1,decimal:1,\"decimal-leading-zero\":1,\"lower-roman\":1,\"upper-roman\":1,\"lower-greek\":1,\"lower-latin\":1,\"upper-latin\":1,georgian:1,\"lower-alpha\":1,\"upper-alpha\":1},margin:{px:1,em:1,\"%\":1},\"margin-right\":{px:1,em:1,\"%\":1},\"margin-left\":{px:1,em:1,\"%\":1},\"margin-top\":{px:1,em:1,\"%\":1},\"margin-bottom\":{px:1,em:1,\"%\":1},\"max-height\":{px:1,em:1,\"%\":1},\"max-width\":{px:1,em:1,\"%\":1},\"min-height\":{px:1,em:1,\"%\":1},\"min-width\":{px:1,em:1,\"%\":1},overflow:{hidden:1,visible:1,auto:1,scroll:1},\"overflow-x\":{hidden:1,visible:1,auto:1,scroll:1},\"overflow-y\":{hidden:1,visible:1,auto:1,scroll:1},padding:{px:1,em:1,\"%\":1},\"padding-top\":{px:1,em:1,\"%\":1},\"padding-right\":{px:1,em:1,\"%\":1},\"padding-bottom\":{px:1,em:1,\"%\":1},\"padding-left\":{px:1,em:1,\"%\":1},\"page-break-after\":{auto:1,always:1,avoid:1,left:1,right:1},\"page-break-before\":{auto:1,always:1,avoid:1,left:1,right:1},position:{absolute:1,relative:1,fixed:1,\"static\":1},right:{px:1,em:1,\"%\":1},\"table-layout\":{fixed:1,auto:1},\"text-decoration\":{none:1,underline:1,\"line-through\":1,blink:1},\"text-align\":{left:1,right:1,center:1,justify:1},\"text-transform\":{capitalize:1,uppercase:1,lowercase:1,none:1},top:{px:1,em:1,\"%\":1},\"vertical-align\":{top:1,bottom:1},visibility:{hidden:1,visible:1},\"white-space\":{nowrap:1,normal:1,pre:1,\"pre-line\":1,\"pre-wrap\":1},width:{px:1,em:1,\"%\":1},\"word-spacing\":{normal:1},filter:{\"alpha(opacity=$0100)\":1},\"text-shadow\":{\"$02px 2px 2px #777\":1},\"text-overflow\":{\"ellipsis-word\":1,clip:1,ellipsis:1},\"-moz-border-radius\":1,\"-moz-border-radius-topright\":1,\"-moz-border-radius-bottomright\":1,\"-moz-border-radius-topleft\":1,\"-moz-border-radius-bottomleft\":1,\"-webkit-border-radius\":1,\"-webkit-border-top-right-radius\":1,\"-webkit-border-top-left-radius\":1,\"-webkit-border-bottom-right-radius\":1,\"-webkit-border-bottom-left-radius\":1,\"-moz-box-shadow\":1,\"-webkit-box-shadow\":1,transform:{\"rotate($00deg)\":1,\"skew($00deg)\":1},\"-moz-transform\":{\"rotate($00deg)\":1,\"skew($00deg)\":1},\"-webkit-transform\":{\"rotate($00deg)\":1,\"skew($00deg)\":1}},i=function(){};(function(){this.completionsDefined=!1,this.defineCompletions=function(){if(document){var e=document.createElement(\"c\").style;for(var t in e){if(typeof e[t]!=\"string\")continue;var n=t.replace(/[A-Z]/g,function(e){return\"-\"+e.toLowerCase()});r.hasOwnProperty(n)||(r[n]=1)}}this.completionsDefined=!0},this.getCompletions=function(e,t,n,r){this.completionsDefined||this.defineCompletions();var i=t.getTokenAt(n.row,n.column);if(!i)return[];if(e===\"ruleset\"){var s=t.getLine(n.row).substr(0,n.column);return/:[^;]+$/.test(s)?(/([\\w\\-]+):[^:]*$/.test(s),this.getPropertyValueCompletions(e,t,n,r)):this.getPropertyCompletions(e,t,n,r)}return[]},this.getPropertyCompletions=function(e,t,n,i){var s=Object.keys(r);return s.map(function(e){return{caption:e,snippet:e+\": $0\",meta:\"property\",score:Number.MAX_VALUE}})},this.getPropertyValueCompletions=function(e,t,n,i){var s=t.getLine(n.row).substr(0,n.column),o=(/([\\w\\-]+):[^:]*$/.exec(s)||{})[1];if(!o)return[];var u=[];return o in r&&typeof r[o]==\"object\"&&(u=Object.keys(r[o])),u.map(function(e){return{caption:e,snippet:e,meta:\"property value\",score:Number.MAX_VALUE}})}}).call(i.prototype),t.CssCompletions=i}),define(\"ace/mode/behaviour/css\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/mode/behaviour/cstyle\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"./cstyle\").CstyleBehaviour,o=e(\"../../token_iterator\").TokenIterator,u=function(){this.inherit(s),this.add(\"colon\",\"insertion\",function(e,t,n,r,i){if(i===\":\"){var s=n.getCursorPosition(),u=new o(r,s.row,s.column),a=u.getCurrentToken();a&&a.value.match(/\\s+/)&&(a=u.stepBackward());if(a&&a.type===\"support.type\"){var f=r.doc.getLine(s.row),l=f.substring(s.column,s.column+1);if(l===\":\")return{text:\"\",selection:[1,1]};if(!f.substring(s.column).match(/^\\s*;/))return{text:\":;\",selection:[1,1]}}}}),this.add(\"colon\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&s===\":\"){var u=n.getCursorPosition(),a=new o(r,u.row,u.column),f=a.getCurrentToken();f&&f.value.match(/\\s+/)&&(f=a.stepBackward());if(f&&f.type===\"support.type\"){var l=r.doc.getLine(i.start.row),c=l.substring(i.end.column,i.end.column+1);if(c===\";\")return i.end.column++,i}}}),this.add(\"semicolon\",\"insertion\",function(e,t,n,r,i){if(i===\";\"){var s=n.getCursorPosition(),o=r.doc.getLine(s.row),u=o.substring(s.column,s.column+1);if(u===\";\")return{text:\"\",selection:[1,1]}}})};r.inherits(u,s),t.CssBehaviour=u}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/css\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/css_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/css_completions\",\"ace/mode/behaviour/css\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./css_highlight_rules\").CssHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./css_completions\").CssCompletions,f=e(\"./behaviour/css\").CssBehaviour,l=e(\"./folding/cstyle\").FoldMode,c=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new f,this.$completer=new a,this.foldingRules=new l};r.inherits(c,i),function(){this.foldingRules=\"cStyle\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e).tokens;if(i.length&&i[i.length-1].type==\"comment\")return r;var s=t.match(/^.*\\{\\s*$/);return s&&(r+=n),r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.getCompletions=function(e,t,n,r){return this.$completer.getCompletions(e,t,n,r)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/css_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/css\"}.call(c.prototype),t.Mode=c})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-golang.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/golang_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=function(){var e=\"else|break|case|return|goto|if|const|select|continue|struct|default|switch|for|range|func|import|package|chan|defer|fallthrough|go|interface|map|range|select|type|var\",t=\"string|uint8|uint16|uint32|uint64|int8|int16|int32|int64|float32|float64|complex64|complex128|byte|rune|uint|int|uintptr|bool|error\",n=\"new|close|cap|copy|panic|panicln|print|println|len|make|delete|real|recover|imag|append\",r=\"nil|true|false|iota\",s=this.createKeywordMapper({keyword:e,\"constant.language\":r,\"support.function\":n,\"support.type\":t},\"\"),o=\"\\\\\\\\(?:[0-7]{3}|x\\\\h{2}|u{4}|U\\\\h{6}|[abfnrtv'\\\"\\\\\\\\])\".replace(/\\\\h/g,\"[a-fA-F\\\\d]\");this.$rules={start:[{token:\"comment\",regex:\"\\\\/\\\\/.*$\"},i.getStartRule(\"doc-start\"),{token:\"comment.start\",regex:\"\\\\/\\\\*\",next:\"comment\"},{token:\"string\",regex:/\"(?:[^\"\\\\]|\\\\.)*?\"/},{token:\"string\",regex:\"`\",next:\"bqstring\"},{token:\"constant.numeric\",regex:\"'(?:[^\\\\'\\ud800-\\udbff]|[\\ud800-\\udbff][\\udc00-\\udfff]|\"+o.replace('\"',\"\")+\")'\"},{token:\"constant.numeric\",regex:\"0[xX][0-9a-fA-F]+\\\\b\"},{token:\"constant.numeric\",regex:\"[+-]?\\\\d+(?:(?:\\\\.\\\\d*)?(?:[eE][+-]?\\\\d+)?)?\\\\b\"},{token:[\"keyword\",\"text\",\"entity.name.function\"],regex:\"(func)(\\\\s+)([a-zA-Z_$][a-zA-Z0-9_$]*)\\\\b\"},{token:function(e){return e[e.length-1]==\"(\"?[{type:s(e.slice(0,-1))||\"support.function\",value:e.slice(0,-1)},{type:\"paren.lparen\",value:e.slice(-1)}]:s(e)||\"identifier\"},regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\\\\(?\"},{token:\"keyword.operator\",regex:\"!|\\\\$|%|&|\\\\*|\\\\-\\\\-|\\\\-|\\\\+\\\\+|\\\\+|~|==|=|!=|<=|>=|<<=|>>=|>>>=|<>|<|>|!|&&|\\\\|\\\\||\\\\?\\\\:|\\\\*=|%=|\\\\+=|\\\\-=|&=|\\\\^=\"},{token:\"punctuation.operator\",regex:\"\\\\?|\\\\:|\\\\,|\\\\;|\\\\.\"},{token:\"paren.lparen\",regex:\"[[({]\"},{token:\"paren.rparen\",regex:\"[\\\\])}]\"},{token:\"text\",regex:\"\\\\s+\"}],comment:[{token:\"comment.end\",regex:\"\\\\*\\\\/\",next:\"start\"},{defaultToken:\"comment\"}],bqstring:[{token:\"string\",regex:\"`\",next:\"start\"},{defaultToken:\"string\"}]},this.embedRules(i,\"doc-\",[i.getEndRule(\"start\")])};r.inherits(o,s),t.GolangHighlightRules=o}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/golang\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/golang_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/cstyle\"],function(e,t,n){var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./golang_highlight_rules\").GolangHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"./behaviour/cstyle\").CstyleBehaviour,a=e(\"./folding/cstyle\").FoldMode,f=function(){this.HighlightRules=s,this.$outdent=new o,this.foldingRules=new a,this.$behaviour=new u};r.inherits(f,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens,o=i.state;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"){var u=t.match(/^.*[\\{\\(\\[]\\s*$/);u&&(r+=n)}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.$id=\"ace/mode/golang\"}.call(f.prototype),t.Mode=f})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-haml.js",
    "content": "define(\"ace/mode/css_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text_highlight_rules\").TextHighlightRules,o=t.supportType=\"align-content|align-items|align-self|all|animation|animation-delay|animation-direction|animation-duration|animation-fill-mode|animation-iteration-count|animation-name|animation-play-state|animation-timing-function|backface-visibility|background|background-attachment|background-blend-mode|background-clip|background-color|background-image|background-origin|background-position|background-repeat|background-size|border|border-bottom|border-bottom-color|border-bottom-left-radius|border-bottom-right-radius|border-bottom-style|border-bottom-width|border-collapse|border-color|border-image|border-image-outset|border-image-repeat|border-image-slice|border-image-source|border-image-width|border-left|border-left-color|border-left-style|border-left-width|border-radius|border-right|border-right-color|border-right-style|border-right-width|border-spacing|border-style|border-top|border-top-color|border-top-left-radius|border-top-right-radius|border-top-style|border-top-width|border-width|bottom|box-shadow|box-sizing|caption-side|clear|clip|color|column-count|column-fill|column-gap|column-rule|column-rule-color|column-rule-style|column-rule-width|column-span|column-width|columns|content|counter-increment|counter-reset|cursor|direction|display|empty-cells|filter|flex|flex-basis|flex-direction|flex-flow|flex-grow|flex-shrink|flex-wrap|float|font|font-family|font-size|font-size-adjust|font-stretch|font-style|font-variant|font-weight|hanging-punctuation|height|justify-content|left|letter-spacing|line-height|list-style|list-style-image|list-style-position|list-style-type|margin|margin-bottom|margin-left|margin-right|margin-top|max-height|max-width|min-height|min-width|nav-down|nav-index|nav-left|nav-right|nav-up|opacity|order|outline|outline-color|outline-offset|outline-style|outline-width|overflow|overflow-x|overflow-y|padding|padding-bottom|padding-left|padding-right|padding-top|page-break-after|page-break-before|page-break-inside|perspective|perspective-origin|position|quotes|resize|right|tab-size|table-layout|text-align|text-align-last|text-decoration|text-decoration-color|text-decoration-line|text-decoration-style|text-indent|text-justify|text-overflow|text-shadow|text-transform|top|transform|transform-origin|transform-style|transition|transition-delay|transition-duration|transition-property|transition-timing-function|unicode-bidi|vertical-align|visibility|white-space|width|word-break|word-spacing|word-wrap|z-index\",u=t.supportFunction=\"rgb|rgba|url|attr|counter|counters\",a=t.supportConstant=\"absolute|after-edge|after|all-scroll|all|alphabetic|always|antialiased|armenian|auto|avoid-column|avoid-page|avoid|balance|baseline|before-edge|before|below|bidi-override|block-line-height|block|bold|bolder|border-box|both|bottom|box|break-all|break-word|capitalize|caps-height|caption|center|central|char|circle|cjk-ideographic|clone|close-quote|col-resize|collapse|column|consider-shifts|contain|content-box|cover|crosshair|cubic-bezier|dashed|decimal-leading-zero|decimal|default|disabled|disc|disregard-shifts|distribute-all-lines|distribute-letter|distribute-space|distribute|dotted|double|e-resize|ease-in|ease-in-out|ease-out|ease|ellipsis|end|exclude-ruby|fill|fixed|georgian|glyphs|grid-height|groove|hand|hanging|hebrew|help|hidden|hiragana-iroha|hiragana|horizontal|icon|ideograph-alpha|ideograph-numeric|ideograph-parenthesis|ideograph-space|ideographic|inactive|include-ruby|inherit|initial|inline-block|inline-box|inline-line-height|inline-table|inline|inset|inside|inter-ideograph|inter-word|invert|italic|justify|katakana-iroha|katakana|keep-all|last|left|lighter|line-edge|line-through|line|linear|list-item|local|loose|lower-alpha|lower-greek|lower-latin|lower-roman|lowercase|lr-tb|ltr|mathematical|max-height|max-size|medium|menu|message-box|middle|move|n-resize|ne-resize|newspaper|no-change|no-close-quote|no-drop|no-open-quote|no-repeat|none|normal|not-allowed|nowrap|nw-resize|oblique|open-quote|outset|outside|overline|padding-box|page|pointer|pre-line|pre-wrap|pre|preserve-3d|progress|relative|repeat-x|repeat-y|repeat|replaced|reset-size|ridge|right|round|row-resize|rtl|s-resize|scroll|se-resize|separate|slice|small-caps|small-caption|solid|space|square|start|static|status-bar|step-end|step-start|steps|stretch|strict|sub|super|sw-resize|table-caption|table-cell|table-column-group|table-column|table-footer-group|table-header-group|table-row-group|table-row|table|tb-rl|text-after-edge|text-before-edge|text-bottom|text-size|text-top|text|thick|thin|transparent|underline|upper-alpha|upper-latin|upper-roman|uppercase|use-script|vertical-ideographic|vertical-text|visible|w-resize|wait|whitespace|z-index|zero\",f=t.supportConstantColor=\"aqua|black|blue|fuchsia|gray|green|lime|maroon|navy|olive|orange|purple|red|silver|teal|white|yellow\",l=t.supportConstantFonts=\"arial|century|comic|courier|cursive|fantasy|garamond|georgia|helvetica|impact|lucida|symbol|system|tahoma|times|trebuchet|utopia|verdana|webdings|sans-serif|serif|monospace\",c=t.numRe=\"\\\\-?(?:(?:[0-9]+)|(?:[0-9]*\\\\.[0-9]+))\",h=t.pseudoElements=\"(\\\\:+)\\\\b(after|before|first-letter|first-line|moz-selection|selection)\\\\b\",p=t.pseudoClasses=\"(:)\\\\b(active|checked|disabled|empty|enabled|first-child|first-of-type|focus|hover|indeterminate|invalid|last-child|last-of-type|link|not|nth-child|nth-last-child|nth-last-of-type|nth-of-type|only-child|only-of-type|required|root|target|valid|visited)\\\\b\",d=function(){var e=this.createKeywordMapper({\"support.function\":u,\"support.constant\":a,\"support.type\":o,\"support.constant.color\":f,\"support.constant.fonts\":l},\"text\",!0);this.$rules={start:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"@.*?{\",push:\"media\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],media:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"\\\\}\",next:\"pop\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],comment:[{token:\"comment\",regex:\"\\\\*\\\\/\",next:\"pop\"},{defaultToken:\"comment\"}],ruleset:[{token:\"paren.rparen\",regex:\"\\\\}\",next:\"pop\"},{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},{token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},{token:[\"constant.numeric\",\"keyword\"],regex:\"(\"+c+\")(ch|cm|deg|em|ex|fr|gd|grad|Hz|in|kHz|mm|ms|pc|pt|px|rad|rem|s|turn|vh|vm|vw|%)\"},{token:\"constant.numeric\",regex:c},{token:\"constant.numeric\",regex:\"#[a-f0-9]{6}\"},{token:\"constant.numeric\",regex:\"#[a-f0-9]{3}\"},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-element.css\"],regex:h},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-class.css\"],regex:p},{token:[\"support.function\",\"string\",\"support.function\"],regex:\"(url\\\\()(.*)(\\\\))\"},{token:e,regex:\"\\\\-?[a-zA-Z_][a-zA-Z0-9_\\\\-]*\"},{caseInsensitive:!0}]},this.normalizeRules()};r.inherits(d,s),t.CssHighlightRules=d}),define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/javascript_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";function a(){var e=o.replace(\"\\\\d\",\"\\\\d\\\\-\"),t={onMatch:function(e,t,n){var r=e.charAt(1)==\"/\"?2:1;if(r==1)t!=this.nextState?n.unshift(this.next,this.nextState,0):n.unshift(this.next),n[2]++;else if(r==2&&t==this.nextState){n[1]--;if(!n[1]||n[1]<0)n.shift(),n.shift()}return[{type:\"meta.tag.punctuation.\"+(r==1?\"\":\"end-\")+\"tag-open.xml\",value:e.slice(0,r)},{type:\"meta.tag.tag-name.xml\",value:e.substr(r)}]},regex:\"</?\"+e+\"\",next:\"jsxAttributes\",nextState:\"jsx\"};this.$rules.start.unshift(t);var n={regex:\"{\",token:\"paren.quasi.start\",push:\"start\"};this.$rules.jsx=[n,t,{include:\"reference\"},{defaultToken:\"string\"}],this.$rules.jsxAttributes=[{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",onMatch:function(e,t,n){return t==n[0]&&n.shift(),e.length==2&&(n[0]==this.nextState&&n[1]--,(!n[1]||n[1]<0)&&n.splice(0,2)),this.next=n[0]||\"start\",[{type:this.token,value:e}]},nextState:\"jsx\"},n,f(\"jsxAttributes\"),{token:\"entity.other.attribute-name.xml\",regex:e},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"},{token:\"string.attribute-value.xml\",regex:\"'\",stateName:\"jsx_attr_q\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',stateName:\"jsx_attr_qq\",push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},t],this.$rules.reference=[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}]}function f(e){return[{token:\"comment\",regex:/\\/\\*/,next:[i.getTagRule(),{token:\"comment\",regex:\"\\\\*\\\\/\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]},{token:\"comment\",regex:\"\\\\/\\\\/\",next:[i.getTagRule(),{token:\"comment\",regex:\"$|^\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]}]}var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=\"[a-zA-Z\\\\$_\\u00a1-\\uffff][a-zA-Z\\\\d\\\\$_\\u00a1-\\uffff]*\",u=function(e){var t=this.createKeywordMapper({\"variable.language\":\"Array|Boolean|Date|Function|Iterator|Number|Object|RegExp|String|Proxy|Namespace|QName|XML|XMLList|ArrayBuffer|Float32Array|Float64Array|Int16Array|Int32Array|Int8Array|Uint16Array|Uint32Array|Uint8Array|Uint8ClampedArray|Error|EvalError|InternalError|RangeError|ReferenceError|StopIteration|SyntaxError|TypeError|URIError|decodeURI|decodeURIComponent|encodeURI|encodeURIComponent|eval|isFinite|isNaN|parseFloat|parseInt|JSON|Math|this|arguments|prototype|window|document\",keyword:\"const|yield|import|get|set|async|await|break|case|catch|continue|default|delete|do|else|finally|for|function|if|in|of|instanceof|new|return|switch|throw|try|typeof|let|var|while|with|debugger|__parent__|__count__|escape|unescape|with|__proto__|class|enum|extends|super|export|implements|private|public|interface|package|protected|static\",\"storage.type\":\"const|let|var|function\",\"constant.language\":\"null|Infinity|NaN|undefined\",\"support.function\":\"alert\",\"constant.language.boolean\":\"true|false\"},\"identifier\"),n=\"case|do|else|finally|in|instanceof|return|throw|try|typeof|yield|void\",r=\"\\\\\\\\(?:x[0-9a-fA-F]{2}|u[0-9a-fA-F]{4}|u{[0-9a-fA-F]{1,6}}|[0-2][0-7]{0,2}|3[0-7][0-7]?|[4-7][0-7]?|.)\";this.$rules={no_regex:[i.getStartRule(\"doc-start\"),f(\"no_regex\"),{token:\"string\",regex:\"'(?=.)\",next:\"qstring\"},{token:\"string\",regex:'\"(?=.)',next:\"qqstring\"},{token:\"constant.numeric\",regex:/0(?:[xX][0-9a-fA-F]+|[bB][01]+)\\b/},{token:\"constant.numeric\",regex:/[+-]?\\d[\\d_]*(?:(?:\\.\\d*)?(?:[eE][+-]?\\d+)?)?\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\"],regex:\"(\"+o+\")(\\\\.)(prototype)(\\\\.)(\"+o+\")(\\\\s*)(=)\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s+)(\\\\w+)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(function)(\\\\s+)(\"+o+\")(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"punctuation.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"text\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"keyword\",regex:\"(?:\"+n+\")\\\\b\",next:\"start\"},{token:[\"support.constant\"],regex:/that\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function.firebug\"],regex:/(console)(\\.)(warn|info|log|error|time|trace|timeEnd|assert)\\b/},{token:t,regex:o},{token:\"punctuation.operator\",regex:/[.](?![.])/,next:\"property\"},{token:\"keyword.operator\",regex:/--|\\+\\+|\\.{3}|===|==|=|!=|!==|<+=?|>+=?|!|&&|\\|\\||\\?:|[!$%&*+\\-~\\/^]=?/,next:\"start\"},{token:\"punctuation.operator\",regex:/[?:,;.]/,next:\"start\"},{token:\"paren.lparen\",regex:/[\\[({]/,next:\"start\"},{token:\"paren.rparen\",regex:/[\\])}]/},{token:\"comment\",regex:/^#!.*$/}],property:[{token:\"text\",regex:\"\\\\s+\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(?:(\\\\s+)(\\\\w+))?(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"punctuation.operator\",regex:/[.](?![.])/},{token:\"support.function\",regex:/(s(?:h(?:ift|ow(?:Mod(?:elessDialog|alDialog)|Help))|croll(?:X|By(?:Pages|Lines)?|Y|To)?|t(?:op|rike)|i(?:n|zeToContent|debar|gnText)|ort|u(?:p|b(?:str(?:ing)?)?)|pli(?:ce|t)|e(?:nd|t(?:Re(?:sizable|questHeader)|M(?:i(?:nutes|lliseconds)|onth)|Seconds|Ho(?:tKeys|urs)|Year|Cursor|Time(?:out)?|Interval|ZOptions|Date|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Date|FullYear)|FullYear|Active)|arch)|qrt|lice|avePreferences|mall)|h(?:ome|andleEvent)|navigate|c(?:har(?:CodeAt|At)|o(?:s|n(?:cat|textual|firm)|mpile)|eil|lear(?:Timeout|Interval)?|a(?:ptureEvents|ll)|reate(?:StyleSheet|Popup|EventObject))|t(?:o(?:GMTString|S(?:tring|ource)|U(?:TCString|pperCase)|Lo(?:caleString|werCase))|est|a(?:n|int(?:Enabled)?))|i(?:s(?:NaN|Finite)|ndexOf|talics)|d(?:isableExternalCapture|ump|etachEvent)|u(?:n(?:shift|taint|escape|watch)|pdateCommands)|j(?:oin|avaEnabled)|p(?:o(?:p|w)|ush|lugins.refresh|a(?:ddings|rse(?:Int|Float)?)|r(?:int|ompt|eference))|e(?:scape|nableExternalCapture|val|lementFromPoint|x(?:p|ec(?:Script|Command)?))|valueOf|UTC|queryCommand(?:State|Indeterm|Enabled|Value)|f(?:i(?:nd|le(?:ModifiedDate|Size|CreatedDate|UpdatedDate)|xed)|o(?:nt(?:size|color)|rward)|loor|romCharCode)|watch|l(?:ink|o(?:ad|g)|astIndexOf)|a(?:sin|nchor|cos|t(?:tachEvent|ob|an(?:2)?)|pply|lert|b(?:s|ort))|r(?:ou(?:nd|teEvents)|e(?:size(?:By|To)|calc|turnValue|place|verse|l(?:oad|ease(?:Capture|Events)))|andom)|g(?:o|et(?:ResponseHeader|M(?:i(?:nutes|lliseconds)|onth)|Se(?:conds|lection)|Hours|Year|Time(?:zoneOffset)?|Da(?:y|te)|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Da(?:y|te)|FullYear)|FullYear|A(?:ttention|llResponseHeaders)))|m(?:in|ove(?:B(?:y|elow)|To(?:Absolute)?|Above)|ergeAttributes|a(?:tch|rgins|x))|b(?:toa|ig|o(?:ld|rderWidths)|link|ack))\\b(?=\\()/},{token:\"support.function.dom\",regex:/(s(?:ub(?:stringData|mit)|plitText|e(?:t(?:NamedItem|Attribute(?:Node)?)|lect))|has(?:ChildNodes|Feature)|namedItem|c(?:l(?:ick|o(?:se|neNode))|reate(?:C(?:omment|DATASection|aption)|T(?:Head|extNode|Foot)|DocumentFragment|ProcessingInstruction|E(?:ntityReference|lement)|Attribute))|tabIndex|i(?:nsert(?:Row|Before|Cell|Data)|tem)|open|delete(?:Row|C(?:ell|aption)|T(?:Head|Foot)|Data)|focus|write(?:ln)?|a(?:dd|ppend(?:Child|Data))|re(?:set|place(?:Child|Data)|move(?:NamedItem|Child|Attribute(?:Node)?)?)|get(?:NamedItem|Element(?:sBy(?:Name|TagName|ClassName)|ById)|Attribute(?:Node)?)|blur)\\b(?=\\()/},{token:\"support.constant\",regex:/(s(?:ystemLanguage|cr(?:ipts|ollbars|een(?:X|Y|Top|Left))|t(?:yle(?:Sheets)?|atus(?:Text|bar)?)|ibling(?:Below|Above)|ource|uffixes|e(?:curity(?:Policy)?|l(?:ection|f)))|h(?:istory|ost(?:name)?|as(?:h|Focus))|y|X(?:MLDocument|SLDocument)|n(?:ext|ame(?:space(?:s|URI)|Prop))|M(?:IN_VALUE|AX_VALUE)|c(?:haracterSet|o(?:n(?:structor|trollers)|okieEnabled|lorDepth|mp(?:onents|lete))|urrent|puClass|l(?:i(?:p(?:boardData)?|entInformation)|osed|asses)|alle(?:e|r)|rypto)|t(?:o(?:olbar|p)|ext(?:Transform|Indent|Decoration|Align)|ags)|SQRT(?:1_2|2)|i(?:n(?:ner(?:Height|Width)|put)|ds|gnoreCase)|zIndex|o(?:scpu|n(?:readystatechange|Line)|uter(?:Height|Width)|p(?:sProfile|ener)|ffscreenBuffering)|NEGATIVE_INFINITY|d(?:i(?:splay|alog(?:Height|Top|Width|Left|Arguments)|rectories)|e(?:scription|fault(?:Status|Ch(?:ecked|arset)|View)))|u(?:ser(?:Profile|Language|Agent)|n(?:iqueID|defined)|pdateInterval)|_content|p(?:ixelDepth|ort|ersonalbar|kcs11|l(?:ugins|atform)|a(?:thname|dding(?:Right|Bottom|Top|Left)|rent(?:Window|Layer)?|ge(?:X(?:Offset)?|Y(?:Offset)?))|r(?:o(?:to(?:col|type)|duct(?:Sub)?|mpter)|e(?:vious|fix)))|e(?:n(?:coding|abledPlugin)|x(?:ternal|pando)|mbeds)|v(?:isibility|endor(?:Sub)?|Linkcolor)|URLUnencoded|P(?:I|OSITIVE_INFINITY)|f(?:ilename|o(?:nt(?:Size|Family|Weight)|rmName)|rame(?:s|Element)|gColor)|E|whiteSpace|l(?:i(?:stStyleType|n(?:eHeight|kColor))|o(?:ca(?:tion(?:bar)?|lName)|wsrc)|e(?:ngth|ft(?:Context)?)|a(?:st(?:M(?:odified|atch)|Index|Paren)|yer(?:s|X)|nguage))|a(?:pp(?:MinorVersion|Name|Co(?:deName|re)|Version)|vail(?:Height|Top|Width|Left)|ll|r(?:ity|guments)|Linkcolor|bove)|r(?:ight(?:Context)?|e(?:sponse(?:XML|Text)|adyState))|global|x|m(?:imeTypes|ultiline|enubar|argin(?:Right|Bottom|Top|Left))|L(?:N(?:10|2)|OG(?:10E|2E))|b(?:o(?:ttom|rder(?:Width|RightWidth|BottomWidth|Style|Color|TopWidth|LeftWidth))|ufferDepth|elow|ackground(?:Color|Image)))\\b/},{token:\"identifier\",regex:o},{regex:\"\",token:\"empty\",next:\"no_regex\"}],start:[i.getStartRule(\"doc-start\"),f(\"start\"),{token:\"string.regexp\",regex:\"\\\\/\",next:\"regex\"},{token:\"text\",regex:\"\\\\s+|^$\",next:\"start\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],regex:[{token:\"regexp.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"string.regexp\",regex:\"/[sxngimy]*\",next:\"no_regex\"},{token:\"invalid\",regex:/\\{\\d+\\b,?\\d*\\}[+*]|[+*$^?][+*]|[$^][?]|\\?{3,}/},{token:\"constant.language.escape\",regex:/\\(\\?[:=!]|\\)|\\{\\d+\\b,?\\d*\\}|[+*]\\?|[()$^+*?.]/},{token:\"constant.language.delimiter\",regex:/\\|/},{token:\"constant.language.escape\",regex:/\\[\\^?/,next:\"regex_character_class\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp\"}],regex_character_class:[{token:\"regexp.charclass.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"constant.language.escape\",regex:\"]\",next:\"regex\"},{token:\"constant.language.escape\",regex:\"-\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp.charachterclass\"}],function_arguments:[{token:\"variable.parameter\",regex:o},{token:\"punctuation.operator\",regex:\"[, ]+\"},{token:\"punctuation.operator\",regex:\"$\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],qqstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qqstring\"},{token:\"string\",regex:'\"|$',next:\"no_regex\"},{defaultToken:\"string\"}],qstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qstring\"},{token:\"string\",regex:\"'|$\",next:\"no_regex\"},{defaultToken:\"string\"}]};if(!e||!e.noES6)this.$rules.no_regex.unshift({regex:\"[{}]\",onMatch:function(e,t,n){this.next=e==\"{\"?this.nextState:\"\";if(e==\"{\"&&n.length)n.unshift(\"start\",t);else if(e==\"}\"&&n.length){n.shift(),this.next=n.shift();if(this.next.indexOf(\"string\")!=-1||this.next.indexOf(\"jsx\")!=-1)return\"paren.quasi.end\"}return e==\"{\"?\"paren.lparen\":\"paren.rparen\"},nextState:\"start\"},{token:\"string.quasi.start\",regex:/`/,push:[{token:\"constant.language.escape\",regex:r},{token:\"paren.quasi.start\",regex:/\\${/,push:\"start\"},{token:\"string.quasi.end\",regex:/`/,next:\"pop\"},{defaultToken:\"string.quasi\"}]}),(!e||e.jsx!=0)&&a.call(this);this.embedRules(i,\"doc-\",[i.getEndRule(\"no_regex\")]),this.normalizeRules()};r.inherits(u,s),t.JavaScriptHighlightRules=u}),define(\"ace/mode/xml_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(e){var t=\"[_:a-zA-Z\\u00c0-\\uffff][-_:.a-zA-Z0-9\\u00c0-\\uffff]*\";this.$rules={start:[{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\",next:\"cdata\"},{token:[\"punctuation.xml-decl.xml\",\"keyword.xml-decl.xml\"],regex:\"(<\\\\?)(xml)(?=[\\\\s])\",next:\"xml_decl\",caseInsensitive:!0},{token:[\"punctuation.instruction.xml\",\"keyword.instruction.xml\"],regex:\"(<\\\\?)(\"+t+\")\",next:\"processing_instruction\"},{token:\"comment.xml\",regex:\"<\\\\!--\",next:\"comment\"},{token:[\"xml-pe.doctype.xml\",\"xml-pe.doctype.xml\"],regex:\"(<\\\\!)(DOCTYPE)(?=[\\\\s])\",next:\"doctype\",caseInsensitive:!0},{include:\"tag\"},{token:\"text.end-tag-open.xml\",regex:\"</\"},{token:\"text.tag-open.xml\",regex:\"<\"},{include:\"reference\"},{defaultToken:\"text.xml\"}],xml_decl:[{token:\"entity.other.attribute-name.decl-attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.decl-attribute-equals.xml\",regex:\"=\"},{include:\"whitespace\"},{include:\"string\"},{token:\"punctuation.xml-decl.xml\",regex:\"\\\\?>\",next:\"start\"}],processing_instruction:[{token:\"punctuation.instruction.xml\",regex:\"\\\\?>\",next:\"start\"},{defaultToken:\"instruction.xml\"}],doctype:[{include:\"whitespace\"},{include:\"string\"},{token:\"xml-pe.doctype.xml\",regex:\">\",next:\"start\"},{token:\"xml-pe.xml\",regex:\"[-_a-zA-Z0-9:]+\"},{token:\"punctuation.int-subset\",regex:\"\\\\[\",push:\"int_subset\"}],int_subset:[{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"punctuation.int-subset.xml\",regex:\"]\",next:\"pop\"},{token:[\"punctuation.markup-decl.xml\",\"keyword.markup-decl.xml\"],regex:\"(<\\\\!)(\"+t+\")\",push:[{token:\"text\",regex:\"\\\\s+\"},{token:\"punctuation.markup-decl.xml\",regex:\">\",next:\"pop\"},{include:\"string\"}]}],cdata:[{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\",next:\"start\"},{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"text.xml\",regex:\"(?:[^\\\\]]|\\\\](?!\\\\]>))+\"}],comment:[{token:\"comment.xml\",regex:\"-->\",next:\"start\"},{defaultToken:\"comment.xml\"}],reference:[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],attr_reference:[{token:\"constant.language.escape.reference.attribute-value.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],tag:[{token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.tag-name.xml\"],regex:\"(?:(<)|(</))((?:\"+t+\":)?\"+t+\")\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}],tag_whitespace:[{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"}],whitespace:[{token:\"text.whitespace.xml\",regex:\"\\\\s+\"}],string:[{token:\"string.xml\",regex:\"'\",push:[{token:\"string.xml\",regex:\"'\",next:\"pop\"},{defaultToken:\"string.xml\"}]},{token:\"string.xml\",regex:'\"',push:[{token:\"string.xml\",regex:'\"',next:\"pop\"},{defaultToken:\"string.xml\"}]}],attributes:[{token:\"entity.other.attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{include:\"tag_whitespace\"},{include:\"attribute_value\"}],attribute_value:[{token:\"string.attribute-value.xml\",regex:\"'\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]}]},this.constructor===s&&this.normalizeRules()};(function(){this.embedTagRules=function(e,t,n){this.$rules.tag.unshift({token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(<)(\"+n+\"(?=\\\\s|>|$))\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:t+\"start\"}]}),this.$rules[n+\"-end\"]=[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\",onMatch:function(e,t,n){return n.splice(0),this.token}}],this.embedRules(e,t,[{token:[\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(</)(\"+n+\"(?=\\\\s|>|$))\",next:n+\"-end\"},{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\"},{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\"}])}}).call(i.prototype),r.inherits(s,i),t.XmlHighlightRules=s}),define(\"ace/mode/html_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/css_highlight_rules\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/xml_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./css_highlight_rules\").CssHighlightRules,o=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,u=e(\"./xml_highlight_rules\").XmlHighlightRules,a=i.createMap({a:\"anchor\",button:\"form\",form:\"form\",img:\"image\",input:\"form\",label:\"form\",option:\"form\",script:\"script\",select:\"form\",textarea:\"form\",style:\"style\",table:\"table\",tbody:\"table\",td:\"table\",tfoot:\"table\",th:\"table\",tr:\"table\"}),f=function(){u.call(this),this.addRules({attributes:[{include:\"tag_whitespace\"},{token:\"entity.other.attribute-name.xml\",regex:\"[-_a-zA-Z0-9:.]+\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\",push:[{include:\"tag_whitespace\"},{token:\"string.unquoted.attribute-value.html\",regex:\"[^<>='\\\"`\\\\s]+\",next:\"pop\"},{token:\"empty\",regex:\"\",next:\"pop\"}]},{include:\"attribute_value\"}],tag:[{token:function(e,t){var n=a[t];return[\"meta.tag.punctuation.\"+(e==\"<\"?\"\":\"end-\")+\"tag-open.xml\",\"meta.tag\"+(n?\".\"+n:\"\")+\".tag-name.xml\"]},regex:\"(</?)([-_a-zA-Z0-9:.]+)\",next:\"tag_stuff\"}],tag_stuff:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}),this.embedTagRules(s,\"css-\",\"style\"),this.embedTagRules((new o({jsx:!1})).getRules(),\"js-\",\"script\"),this.constructor===f&&this.normalizeRules()};r.inherits(f,u),t.HtmlHighlightRules=f}),define(\"ace/mode/ruby_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=t.constantOtherSymbol={token:\"constant.other.symbol.ruby\",regex:\"[:](?:[A-Za-z_]|[@$](?=[a-zA-Z0-9_]))[a-zA-Z0-9_]*[!=?]?\"},o=t.qString={token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},u=t.qqString={token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},a=t.tString={token:\"string\",regex:\"[`](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[`]\"},f=t.constantNumericHex={token:\"constant.numeric\",regex:\"0[xX][0-9a-fA-F](?:[0-9a-fA-F]|_(?=[0-9a-fA-F]))*\\\\b\"},l=t.constantNumericFloat={token:\"constant.numeric\",regex:\"[+-]?\\\\d(?:\\\\d|_(?=\\\\d))*(?:(?:\\\\.\\\\d(?:\\\\d|_(?=\\\\d))*)?(?:[eE][+-]?\\\\d+)?)?\\\\b\"},c=function(){var e=\"abort|Array|assert|assert_equal|assert_not_equal|assert_same|assert_not_same|assert_nil|assert_not_nil|assert_match|assert_no_match|assert_in_delta|assert_throws|assert_raise|assert_nothing_raised|assert_instance_of|assert_kind_of|assert_respond_to|assert_operator|assert_send|assert_difference|assert_no_difference|assert_recognizes|assert_generates|assert_response|assert_redirected_to|assert_template|assert_select|assert_select_email|assert_select_rjs|assert_select_encoded|css_select|at_exit|attr|attr_writer|attr_reader|attr_accessor|attr_accessible|autoload|binding|block_given?|callcc|caller|catch|chomp|chomp!|chop|chop!|defined?|delete_via_redirect|eval|exec|exit|exit!|fail|Float|flunk|follow_redirect!|fork|form_for|form_tag|format|gets|global_variables|gsub|gsub!|get_via_redirect|host!|https?|https!|include|Integer|lambda|link_to|link_to_unless_current|link_to_function|link_to_remote|load|local_variables|loop|open|open_session|p|print|printf|proc|putc|puts|post_via_redirect|put_via_redirect|raise|rand|raw|readline|readlines|redirect?|request_via_redirect|require|scan|select|set_trace_func|sleep|split|sprintf|srand|String|stylesheet_link_tag|syscall|system|sub|sub!|test|throw|trace_var|trap|untrace_var|atan2|cos|exp|frexp|ldexp|log|log10|sin|sqrt|tan|render|javascript_include_tag|csrf_meta_tag|label_tag|text_field_tag|submit_tag|check_box_tag|content_tag|radio_button_tag|text_area_tag|password_field_tag|hidden_field_tag|fields_for|select_tag|options_for_select|options_from_collection_for_select|collection_select|time_zone_select|select_date|select_time|select_datetime|date_select|time_select|datetime_select|select_year|select_month|select_day|select_hour|select_minute|select_second|file_field_tag|file_field|respond_to|skip_before_filter|around_filter|after_filter|verify|protect_from_forgery|rescue_from|helper_method|redirect_to|before_filter|send_data|send_file|validates_presence_of|validates_uniqueness_of|validates_length_of|validates_format_of|validates_acceptance_of|validates_associated|validates_exclusion_of|validates_inclusion_of|validates_numericality_of|validates_with|validates_each|authenticate_or_request_with_http_basic|authenticate_or_request_with_http_digest|filter_parameter_logging|match|get|post|resources|redirect|scope|assert_routing|translate|localize|extract_locale_from_tld|caches_page|expire_page|caches_action|expire_action|cache|expire_fragment|expire_cache_for|observe|cache_sweeper|has_many|has_one|belongs_to|has_and_belongs_to_many\",t=\"alias|and|BEGIN|begin|break|case|class|def|defined|do|else|elsif|END|end|ensure|__FILE__|finally|for|gem|if|in|__LINE__|module|next|not|or|private|protected|public|redo|rescue|retry|return|super|then|undef|unless|until|when|while|yield\",n=\"true|TRUE|false|FALSE|nil|NIL|ARGF|ARGV|DATA|ENV|RUBY_PLATFORM|RUBY_RELEASE_DATE|RUBY_VERSION|STDERR|STDIN|STDOUT|TOPLEVEL_BINDING\",r=\"$DEBUG|$defout|$FILENAME|$LOAD_PATH|$SAFE|$stdin|$stdout|$stderr|$VERBOSE|$!|root_url|flash|session|cookies|params|request|response|logger|self\",i=this.$keywords=this.createKeywordMapper({keyword:t,\"constant.language\":n,\"variable.language\":r,\"support.function\":e,\"invalid.deprecated\":\"debugger\"},\"identifier\");this.$rules={start:[{token:\"comment\",regex:\"#.*$\"},{token:\"comment\",regex:\"^=begin(?:$|\\\\s.*$)\",next:\"comment\"},{token:\"string.regexp\",regex:\"[/](?:(?:\\\\[(?:\\\\\\\\]|[^\\\\]])+\\\\])|(?:\\\\\\\\/|[^\\\\]/]))*[/]\\\\w*\\\\s*(?=[).,;]|$)\"},[{regex:\"[{}]\",onMatch:function(e,t,n){this.next=e==\"{\"?this.nextState:\"\";if(e==\"{\"&&n.length)return n.unshift(\"start\",t),\"paren.lparen\";if(e==\"}\"&&n.length){n.shift(),this.next=n.shift();if(this.next.indexOf(\"string\")!=-1)return\"paren.end\"}return e==\"{\"?\"paren.lparen\":\"paren.rparen\"},nextState:\"start\"},{token:\"string.start\",regex:/\"/,push:[{token:\"constant.language.escape\",regex:/\\\\(?:[nsrtvfbae'\"\\\\]|c.|C-.|M-.(?:\\\\C-.)?|[0-7]{3}|x[\\da-fA-F]{2}|u[\\da-fA-F]{4})/},{token:\"paren.start\",regex:/#{/,push:\"start\"},{token:\"string.end\",regex:/\"/,next:\"pop\"},{defaultToken:\"string\"}]},{token:\"string.start\",regex:/`/,push:[{token:\"constant.language.escape\",regex:/\\\\(?:[nsrtvfbae'\"\\\\]|c.|C-.|M-.(?:\\\\C-.)?|[0-7]{3}|x[\\da-fA-F]{2}|u[\\da-fA-F]{4})/},{token:\"paren.start\",regex:/#{/,push:\"start\"},{token:\"string.end\",regex:/`/,next:\"pop\"},{defaultToken:\"string\"}]},{token:\"string.start\",regex:/'/,push:[{token:\"constant.language.escape\",regex:/\\\\['\\\\]/},{token:\"string.end\",regex:/'/,next:\"pop\"},{defaultToken:\"string\"}]}],{token:\"text\",regex:\"::\"},{token:\"variable.instance\",regex:\"@{1,2}[a-zA-Z_\\\\d]+\"},{token:\"support.class\",regex:\"[A-Z][a-zA-Z_\\\\d]+\"},s,f,l,{token:\"constant.language.boolean\",regex:\"(?:true|false)\\\\b\"},{token:i,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"punctuation.separator.key-value\",regex:\"=>\"},{stateName:\"heredoc\",onMatch:function(e,t,n){var r=e[2]==\"-\"?\"indentedHeredoc\":\"heredoc\",i=e.split(this.splitRegex);return n.push(r,i[3]),[{type:\"constant\",value:i[1]},{type:\"string\",value:i[2]},{type:\"support.class\",value:i[3]},{type:\"string\",value:i[4]}]},regex:\"(<<-?)(['\\\"`]?)([\\\\w]+)(['\\\"`]?)\",rules:{heredoc:[{onMatch:function(e,t,n){return e===n[1]?(n.shift(),n.shift(),this.next=n[0]||\"start\",\"support.class\"):(this.next=\"\",\"string\")},regex:\".*$\",next:\"start\"}],indentedHeredoc:[{token:\"string\",regex:\"^ +\"},{onMatch:function(e,t,n){return e===n[1]?(n.shift(),n.shift(),this.next=n[0]||\"start\",\"support.class\"):(this.next=\"\",\"string\")},regex:\".*$\",next:\"start\"}]}},{regex:\"$\",token:\"empty\",next:function(e,t){return t[0]===\"heredoc\"||t[0]===\"indentedHeredoc\"?t[0]:e}},{token:\"string.character\",regex:\"\\\\B\\\\?.\"},{token:\"keyword.operator\",regex:\"!|\\\\$|%|&|\\\\*|\\\\-\\\\-|\\\\-|\\\\+\\\\+|\\\\+|~|===|==|=|!=|!==|<=|>=|<<=|>>=|>>>=|<>|<|>|!|&&|\\\\|\\\\||\\\\?\\\\:|\\\\*=|%=|\\\\+=|\\\\-=|&=|\\\\^=|\\\\b(?:in|instanceof|new|delete|typeof|void)\"},{token:\"paren.lparen\",regex:\"[[({]\"},{token:\"paren.rparen\",regex:\"[\\\\])}]\"},{token:\"text\",regex:\"\\\\s+\"}],comment:[{token:\"comment\",regex:\"^=end(?:$|\\\\s.*$)\",next:\"start\"},{token:\"comment\",regex:\".+\"}]},this.normalizeRules()};r.inherits(c,i),t.RubyHighlightRules=c}),define(\"ace/mode/haml_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/html_highlight_rules\",\"ace/mode/ruby_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./html_highlight_rules\").HtmlHighlightRules,s=e(\"./ruby_highlight_rules\"),o=s.RubyHighlightRules,u=function(){i.call(this),this.$rules.start.unshift({token:\"punctuation.section.comment\",regex:/^\\s*\\/.*/},{token:\"string.quoted.double\",regex:\"==.+?==\"},{token:\"keyword.other.doctype\",regex:\"^!!!\\\\s*(?:[a-zA-Z0-9-_]+)?\"},s.qString,s.qqString,s.tString,{token:\"character.escape.haml\",regex:\"^\\\\s*\\\\\\\\.\"},{token:\"text\",regex:/^\\s*/,next:\"tag_single\"},s.constantNumericHex,s.constantNumericFloat,s.constantOtherSymbol,{token:\"text\",regex:\"=|-|~\",next:\"embedded_ruby\"}),this.$rules.tag_single=[{token:\"meta.tag.haml\",regex:/(%[\\w:\\-]+)/},{token:\"keyword.attribute-name.class.haml\",regex:\"\\\\.[\\\\w-]+\"},{token:\"keyword.attribute-name.id.haml\",regex:\"#[\\\\w-]+\"},{token:\"punctuation.section\",regex:\"\\\\{\",next:\"section\"},s.constantOtherSymbol,{token:\"text\",regex:/\\s/,next:\"start\"},{token:\"empty\",regex:\"$|(?!\\\\.|#|\\\\{|\\\\[|=|-|~|\\\\/)\",next:\"start\"}],this.$rules.section=[s.constantOtherSymbol,s.qString,s.qqString,s.tString,s.constantNumericHex,s.constantNumericFloat,{token:\"punctuation.section\",regex:\"\\\\}\",next:\"start\"}],this.$rules.embedded_ruby=[s.constantNumericHex,s.constantNumericFloat,{token:\"support.class\",regex:\"[A-Z][a-zA-Z_\\\\d]+\"},{token:(new o).getKeywords(),regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:[\"keyword\",\"text\",\"text\"],regex:\"(?:do|\\\\{)(?: \\\\|[^|]+\\\\|)?$\",next:\"start\"},{token:[\"text\"],regex:\"^$\",next:\"start\"},{token:[\"text\"],regex:\"^(?!.*\\\\|\\\\s*$)\",next:\"start\"}],this.normalizeRules()};r.inherits(u,i),t.HamlHighlightRules=u}),define(\"ace/mode/folding/coffee\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=e(\"../../range\").Range,o=t.FoldMode=function(){};r.inherits(o,i),function(){this.getFoldWidgetRange=function(e,t,n){var r=this.indentationBlock(e,n);if(r)return r;var i=/\\S/,o=e.getLine(n),u=o.search(i);if(u==-1||o[u]!=\"#\")return;var a=o.length,f=e.getLength(),l=n,c=n;while(++n<f){o=e.getLine(n);var h=o.search(i);if(h==-1)continue;if(o[h]!=\"#\")break;c=n}if(c>l){var p=e.getLine(c).length;return new s(l,a,c,p)}},this.getFoldWidget=function(e,t,n){var r=e.getLine(n),i=r.search(/\\S/),s=e.getLine(n+1),o=e.getLine(n-1),u=o.search(/\\S/),a=s.search(/\\S/);if(i==-1)return e.foldWidgets[n-1]=u!=-1&&u<a?\"start\":\"\",\"\";if(u==-1){if(i==a&&r[i]==\"#\"&&s[i]==\"#\")return e.foldWidgets[n-1]=\"\",e.foldWidgets[n+1]=\"\",\"start\"}else if(u==i&&r[i]==\"#\"&&o[i]==\"#\"&&e.getLine(n-2).search(/\\S/)==-1)return e.foldWidgets[n-1]=\"start\",e.foldWidgets[n+1]=\"\",\"\";return u!=-1&&u<i?e.foldWidgets[n-1]=\"start\":e.foldWidgets[n-1]=\"\",i<a?\"start\":\"\"}}.call(o.prototype)}),define(\"ace/mode/haml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/haml_highlight_rules\",\"ace/mode/folding/coffee\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./haml_highlight_rules\").HamlHighlightRules,o=e(\"./folding/coffee\").FoldMode,u=function(){this.HighlightRules=s,this.foldingRules=new o,this.$behaviour=this.$defaultBehaviour};r.inherits(u,i),function(){this.lineCommentStart=\"//\",this.$id=\"ace/mode/haml\"}.call(u.prototype),t.Mode=u})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-html.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/javascript_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";function a(){var e=o.replace(\"\\\\d\",\"\\\\d\\\\-\"),t={onMatch:function(e,t,n){var r=e.charAt(1)==\"/\"?2:1;if(r==1)t!=this.nextState?n.unshift(this.next,this.nextState,0):n.unshift(this.next),n[2]++;else if(r==2&&t==this.nextState){n[1]--;if(!n[1]||n[1]<0)n.shift(),n.shift()}return[{type:\"meta.tag.punctuation.\"+(r==1?\"\":\"end-\")+\"tag-open.xml\",value:e.slice(0,r)},{type:\"meta.tag.tag-name.xml\",value:e.substr(r)}]},regex:\"</?\"+e+\"\",next:\"jsxAttributes\",nextState:\"jsx\"};this.$rules.start.unshift(t);var n={regex:\"{\",token:\"paren.quasi.start\",push:\"start\"};this.$rules.jsx=[n,t,{include:\"reference\"},{defaultToken:\"string\"}],this.$rules.jsxAttributes=[{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",onMatch:function(e,t,n){return t==n[0]&&n.shift(),e.length==2&&(n[0]==this.nextState&&n[1]--,(!n[1]||n[1]<0)&&n.splice(0,2)),this.next=n[0]||\"start\",[{type:this.token,value:e}]},nextState:\"jsx\"},n,f(\"jsxAttributes\"),{token:\"entity.other.attribute-name.xml\",regex:e},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"},{token:\"string.attribute-value.xml\",regex:\"'\",stateName:\"jsx_attr_q\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',stateName:\"jsx_attr_qq\",push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},t],this.$rules.reference=[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}]}function f(e){return[{token:\"comment\",regex:/\\/\\*/,next:[i.getTagRule(),{token:\"comment\",regex:\"\\\\*\\\\/\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]},{token:\"comment\",regex:\"\\\\/\\\\/\",next:[i.getTagRule(),{token:\"comment\",regex:\"$|^\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]}]}var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=\"[a-zA-Z\\\\$_\\u00a1-\\uffff][a-zA-Z\\\\d\\\\$_\\u00a1-\\uffff]*\",u=function(e){var t=this.createKeywordMapper({\"variable.language\":\"Array|Boolean|Date|Function|Iterator|Number|Object|RegExp|String|Proxy|Namespace|QName|XML|XMLList|ArrayBuffer|Float32Array|Float64Array|Int16Array|Int32Array|Int8Array|Uint16Array|Uint32Array|Uint8Array|Uint8ClampedArray|Error|EvalError|InternalError|RangeError|ReferenceError|StopIteration|SyntaxError|TypeError|URIError|decodeURI|decodeURIComponent|encodeURI|encodeURIComponent|eval|isFinite|isNaN|parseFloat|parseInt|JSON|Math|this|arguments|prototype|window|document\",keyword:\"const|yield|import|get|set|async|await|break|case|catch|continue|default|delete|do|else|finally|for|function|if|in|of|instanceof|new|return|switch|throw|try|typeof|let|var|while|with|debugger|__parent__|__count__|escape|unescape|with|__proto__|class|enum|extends|super|export|implements|private|public|interface|package|protected|static\",\"storage.type\":\"const|let|var|function\",\"constant.language\":\"null|Infinity|NaN|undefined\",\"support.function\":\"alert\",\"constant.language.boolean\":\"true|false\"},\"identifier\"),n=\"case|do|else|finally|in|instanceof|return|throw|try|typeof|yield|void\",r=\"\\\\\\\\(?:x[0-9a-fA-F]{2}|u[0-9a-fA-F]{4}|u{[0-9a-fA-F]{1,6}}|[0-2][0-7]{0,2}|3[0-7][0-7]?|[4-7][0-7]?|.)\";this.$rules={no_regex:[i.getStartRule(\"doc-start\"),f(\"no_regex\"),{token:\"string\",regex:\"'(?=.)\",next:\"qstring\"},{token:\"string\",regex:'\"(?=.)',next:\"qqstring\"},{token:\"constant.numeric\",regex:/0(?:[xX][0-9a-fA-F]+|[bB][01]+)\\b/},{token:\"constant.numeric\",regex:/[+-]?\\d[\\d_]*(?:(?:\\.\\d*)?(?:[eE][+-]?\\d+)?)?\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\"],regex:\"(\"+o+\")(\\\\.)(prototype)(\\\\.)(\"+o+\")(\\\\s*)(=)\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s+)(\\\\w+)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(function)(\\\\s+)(\"+o+\")(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"punctuation.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"text\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"keyword\",regex:\"(?:\"+n+\")\\\\b\",next:\"start\"},{token:[\"support.constant\"],regex:/that\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function.firebug\"],regex:/(console)(\\.)(warn|info|log|error|time|trace|timeEnd|assert)\\b/},{token:t,regex:o},{token:\"punctuation.operator\",regex:/[.](?![.])/,next:\"property\"},{token:\"keyword.operator\",regex:/--|\\+\\+|\\.{3}|===|==|=|!=|!==|<+=?|>+=?|!|&&|\\|\\||\\?:|[!$%&*+\\-~\\/^]=?/,next:\"start\"},{token:\"punctuation.operator\",regex:/[?:,;.]/,next:\"start\"},{token:\"paren.lparen\",regex:/[\\[({]/,next:\"start\"},{token:\"paren.rparen\",regex:/[\\])}]/},{token:\"comment\",regex:/^#!.*$/}],property:[{token:\"text\",regex:\"\\\\s+\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(?:(\\\\s+)(\\\\w+))?(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"punctuation.operator\",regex:/[.](?![.])/},{token:\"support.function\",regex:/(s(?:h(?:ift|ow(?:Mod(?:elessDialog|alDialog)|Help))|croll(?:X|By(?:Pages|Lines)?|Y|To)?|t(?:op|rike)|i(?:n|zeToContent|debar|gnText)|ort|u(?:p|b(?:str(?:ing)?)?)|pli(?:ce|t)|e(?:nd|t(?:Re(?:sizable|questHeader)|M(?:i(?:nutes|lliseconds)|onth)|Seconds|Ho(?:tKeys|urs)|Year|Cursor|Time(?:out)?|Interval|ZOptions|Date|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Date|FullYear)|FullYear|Active)|arch)|qrt|lice|avePreferences|mall)|h(?:ome|andleEvent)|navigate|c(?:har(?:CodeAt|At)|o(?:s|n(?:cat|textual|firm)|mpile)|eil|lear(?:Timeout|Interval)?|a(?:ptureEvents|ll)|reate(?:StyleSheet|Popup|EventObject))|t(?:o(?:GMTString|S(?:tring|ource)|U(?:TCString|pperCase)|Lo(?:caleString|werCase))|est|a(?:n|int(?:Enabled)?))|i(?:s(?:NaN|Finite)|ndexOf|talics)|d(?:isableExternalCapture|ump|etachEvent)|u(?:n(?:shift|taint|escape|watch)|pdateCommands)|j(?:oin|avaEnabled)|p(?:o(?:p|w)|ush|lugins.refresh|a(?:ddings|rse(?:Int|Float)?)|r(?:int|ompt|eference))|e(?:scape|nableExternalCapture|val|lementFromPoint|x(?:p|ec(?:Script|Command)?))|valueOf|UTC|queryCommand(?:State|Indeterm|Enabled|Value)|f(?:i(?:nd|le(?:ModifiedDate|Size|CreatedDate|UpdatedDate)|xed)|o(?:nt(?:size|color)|rward)|loor|romCharCode)|watch|l(?:ink|o(?:ad|g)|astIndexOf)|a(?:sin|nchor|cos|t(?:tachEvent|ob|an(?:2)?)|pply|lert|b(?:s|ort))|r(?:ou(?:nd|teEvents)|e(?:size(?:By|To)|calc|turnValue|place|verse|l(?:oad|ease(?:Capture|Events)))|andom)|g(?:o|et(?:ResponseHeader|M(?:i(?:nutes|lliseconds)|onth)|Se(?:conds|lection)|Hours|Year|Time(?:zoneOffset)?|Da(?:y|te)|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Da(?:y|te)|FullYear)|FullYear|A(?:ttention|llResponseHeaders)))|m(?:in|ove(?:B(?:y|elow)|To(?:Absolute)?|Above)|ergeAttributes|a(?:tch|rgins|x))|b(?:toa|ig|o(?:ld|rderWidths)|link|ack))\\b(?=\\()/},{token:\"support.function.dom\",regex:/(s(?:ub(?:stringData|mit)|plitText|e(?:t(?:NamedItem|Attribute(?:Node)?)|lect))|has(?:ChildNodes|Feature)|namedItem|c(?:l(?:ick|o(?:se|neNode))|reate(?:C(?:omment|DATASection|aption)|T(?:Head|extNode|Foot)|DocumentFragment|ProcessingInstruction|E(?:ntityReference|lement)|Attribute))|tabIndex|i(?:nsert(?:Row|Before|Cell|Data)|tem)|open|delete(?:Row|C(?:ell|aption)|T(?:Head|Foot)|Data)|focus|write(?:ln)?|a(?:dd|ppend(?:Child|Data))|re(?:set|place(?:Child|Data)|move(?:NamedItem|Child|Attribute(?:Node)?)?)|get(?:NamedItem|Element(?:sBy(?:Name|TagName|ClassName)|ById)|Attribute(?:Node)?)|blur)\\b(?=\\()/},{token:\"support.constant\",regex:/(s(?:ystemLanguage|cr(?:ipts|ollbars|een(?:X|Y|Top|Left))|t(?:yle(?:Sheets)?|atus(?:Text|bar)?)|ibling(?:Below|Above)|ource|uffixes|e(?:curity(?:Policy)?|l(?:ection|f)))|h(?:istory|ost(?:name)?|as(?:h|Focus))|y|X(?:MLDocument|SLDocument)|n(?:ext|ame(?:space(?:s|URI)|Prop))|M(?:IN_VALUE|AX_VALUE)|c(?:haracterSet|o(?:n(?:structor|trollers)|okieEnabled|lorDepth|mp(?:onents|lete))|urrent|puClass|l(?:i(?:p(?:boardData)?|entInformation)|osed|asses)|alle(?:e|r)|rypto)|t(?:o(?:olbar|p)|ext(?:Transform|Indent|Decoration|Align)|ags)|SQRT(?:1_2|2)|i(?:n(?:ner(?:Height|Width)|put)|ds|gnoreCase)|zIndex|o(?:scpu|n(?:readystatechange|Line)|uter(?:Height|Width)|p(?:sProfile|ener)|ffscreenBuffering)|NEGATIVE_INFINITY|d(?:i(?:splay|alog(?:Height|Top|Width|Left|Arguments)|rectories)|e(?:scription|fault(?:Status|Ch(?:ecked|arset)|View)))|u(?:ser(?:Profile|Language|Agent)|n(?:iqueID|defined)|pdateInterval)|_content|p(?:ixelDepth|ort|ersonalbar|kcs11|l(?:ugins|atform)|a(?:thname|dding(?:Right|Bottom|Top|Left)|rent(?:Window|Layer)?|ge(?:X(?:Offset)?|Y(?:Offset)?))|r(?:o(?:to(?:col|type)|duct(?:Sub)?|mpter)|e(?:vious|fix)))|e(?:n(?:coding|abledPlugin)|x(?:ternal|pando)|mbeds)|v(?:isibility|endor(?:Sub)?|Linkcolor)|URLUnencoded|P(?:I|OSITIVE_INFINITY)|f(?:ilename|o(?:nt(?:Size|Family|Weight)|rmName)|rame(?:s|Element)|gColor)|E|whiteSpace|l(?:i(?:stStyleType|n(?:eHeight|kColor))|o(?:ca(?:tion(?:bar)?|lName)|wsrc)|e(?:ngth|ft(?:Context)?)|a(?:st(?:M(?:odified|atch)|Index|Paren)|yer(?:s|X)|nguage))|a(?:pp(?:MinorVersion|Name|Co(?:deName|re)|Version)|vail(?:Height|Top|Width|Left)|ll|r(?:ity|guments)|Linkcolor|bove)|r(?:ight(?:Context)?|e(?:sponse(?:XML|Text)|adyState))|global|x|m(?:imeTypes|ultiline|enubar|argin(?:Right|Bottom|Top|Left))|L(?:N(?:10|2)|OG(?:10E|2E))|b(?:o(?:ttom|rder(?:Width|RightWidth|BottomWidth|Style|Color|TopWidth|LeftWidth))|ufferDepth|elow|ackground(?:Color|Image)))\\b/},{token:\"identifier\",regex:o},{regex:\"\",token:\"empty\",next:\"no_regex\"}],start:[i.getStartRule(\"doc-start\"),f(\"start\"),{token:\"string.regexp\",regex:\"\\\\/\",next:\"regex\"},{token:\"text\",regex:\"\\\\s+|^$\",next:\"start\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],regex:[{token:\"regexp.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"string.regexp\",regex:\"/[sxngimy]*\",next:\"no_regex\"},{token:\"invalid\",regex:/\\{\\d+\\b,?\\d*\\}[+*]|[+*$^?][+*]|[$^][?]|\\?{3,}/},{token:\"constant.language.escape\",regex:/\\(\\?[:=!]|\\)|\\{\\d+\\b,?\\d*\\}|[+*]\\?|[()$^+*?.]/},{token:\"constant.language.delimiter\",regex:/\\|/},{token:\"constant.language.escape\",regex:/\\[\\^?/,next:\"regex_character_class\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp\"}],regex_character_class:[{token:\"regexp.charclass.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"constant.language.escape\",regex:\"]\",next:\"regex\"},{token:\"constant.language.escape\",regex:\"-\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp.charachterclass\"}],function_arguments:[{token:\"variable.parameter\",regex:o},{token:\"punctuation.operator\",regex:\"[, ]+\"},{token:\"punctuation.operator\",regex:\"$\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],qqstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qqstring\"},{token:\"string\",regex:'\"|$',next:\"no_regex\"},{defaultToken:\"string\"}],qstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qstring\"},{token:\"string\",regex:\"'|$\",next:\"no_regex\"},{defaultToken:\"string\"}]};if(!e||!e.noES6)this.$rules.no_regex.unshift({regex:\"[{}]\",onMatch:function(e,t,n){this.next=e==\"{\"?this.nextState:\"\";if(e==\"{\"&&n.length)n.unshift(\"start\",t);else if(e==\"}\"&&n.length){n.shift(),this.next=n.shift();if(this.next.indexOf(\"string\")!=-1||this.next.indexOf(\"jsx\")!=-1)return\"paren.quasi.end\"}return e==\"{\"?\"paren.lparen\":\"paren.rparen\"},nextState:\"start\"},{token:\"string.quasi.start\",regex:/`/,push:[{token:\"constant.language.escape\",regex:r},{token:\"paren.quasi.start\",regex:/\\${/,push:\"start\"},{token:\"string.quasi.end\",regex:/`/,next:\"pop\"},{defaultToken:\"string.quasi\"}]}),(!e||e.jsx!=0)&&a.call(this);this.embedRules(i,\"doc-\",[i.getEndRule(\"no_regex\")]),this.normalizeRules()};r.inherits(u,s),t.JavaScriptHighlightRules=u}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/javascript\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./behaviour/cstyle\").CstyleBehaviour,f=e(\"./folding/cstyle\").FoldMode,l=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new a,this.foldingRules=new f};r.inherits(l,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens,o=i.state;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"||e==\"no_regex\"){var u=t.match(/^.*(?:\\bcase\\b.*:|[\\{\\(\\[])\\s*$/);u&&(r+=n)}else if(e==\"doc-start\"){if(o==\"start\"||o==\"no_regex\")return\"\";var u=t.match(/^\\s*(\\/?)\\*/);u&&(u[1]&&(r+=\" \"),r+=\"* \")}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/javascript_worker\",\"JavaScriptWorker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/javascript\"}.call(l.prototype),t.Mode=l}),define(\"ace/mode/css_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text_highlight_rules\").TextHighlightRules,o=t.supportType=\"align-content|align-items|align-self|all|animation|animation-delay|animation-direction|animation-duration|animation-fill-mode|animation-iteration-count|animation-name|animation-play-state|animation-timing-function|backface-visibility|background|background-attachment|background-blend-mode|background-clip|background-color|background-image|background-origin|background-position|background-repeat|background-size|border|border-bottom|border-bottom-color|border-bottom-left-radius|border-bottom-right-radius|border-bottom-style|border-bottom-width|border-collapse|border-color|border-image|border-image-outset|border-image-repeat|border-image-slice|border-image-source|border-image-width|border-left|border-left-color|border-left-style|border-left-width|border-radius|border-right|border-right-color|border-right-style|border-right-width|border-spacing|border-style|border-top|border-top-color|border-top-left-radius|border-top-right-radius|border-top-style|border-top-width|border-width|bottom|box-shadow|box-sizing|caption-side|clear|clip|color|column-count|column-fill|column-gap|column-rule|column-rule-color|column-rule-style|column-rule-width|column-span|column-width|columns|content|counter-increment|counter-reset|cursor|direction|display|empty-cells|filter|flex|flex-basis|flex-direction|flex-flow|flex-grow|flex-shrink|flex-wrap|float|font|font-family|font-size|font-size-adjust|font-stretch|font-style|font-variant|font-weight|hanging-punctuation|height|justify-content|left|letter-spacing|line-height|list-style|list-style-image|list-style-position|list-style-type|margin|margin-bottom|margin-left|margin-right|margin-top|max-height|max-width|min-height|min-width|nav-down|nav-index|nav-left|nav-right|nav-up|opacity|order|outline|outline-color|outline-offset|outline-style|outline-width|overflow|overflow-x|overflow-y|padding|padding-bottom|padding-left|padding-right|padding-top|page-break-after|page-break-before|page-break-inside|perspective|perspective-origin|position|quotes|resize|right|tab-size|table-layout|text-align|text-align-last|text-decoration|text-decoration-color|text-decoration-line|text-decoration-style|text-indent|text-justify|text-overflow|text-shadow|text-transform|top|transform|transform-origin|transform-style|transition|transition-delay|transition-duration|transition-property|transition-timing-function|unicode-bidi|vertical-align|visibility|white-space|width|word-break|word-spacing|word-wrap|z-index\",u=t.supportFunction=\"rgb|rgba|url|attr|counter|counters\",a=t.supportConstant=\"absolute|after-edge|after|all-scroll|all|alphabetic|always|antialiased|armenian|auto|avoid-column|avoid-page|avoid|balance|baseline|before-edge|before|below|bidi-override|block-line-height|block|bold|bolder|border-box|both|bottom|box|break-all|break-word|capitalize|caps-height|caption|center|central|char|circle|cjk-ideographic|clone|close-quote|col-resize|collapse|column|consider-shifts|contain|content-box|cover|crosshair|cubic-bezier|dashed|decimal-leading-zero|decimal|default|disabled|disc|disregard-shifts|distribute-all-lines|distribute-letter|distribute-space|distribute|dotted|double|e-resize|ease-in|ease-in-out|ease-out|ease|ellipsis|end|exclude-ruby|fill|fixed|georgian|glyphs|grid-height|groove|hand|hanging|hebrew|help|hidden|hiragana-iroha|hiragana|horizontal|icon|ideograph-alpha|ideograph-numeric|ideograph-parenthesis|ideograph-space|ideographic|inactive|include-ruby|inherit|initial|inline-block|inline-box|inline-line-height|inline-table|inline|inset|inside|inter-ideograph|inter-word|invert|italic|justify|katakana-iroha|katakana|keep-all|last|left|lighter|line-edge|line-through|line|linear|list-item|local|loose|lower-alpha|lower-greek|lower-latin|lower-roman|lowercase|lr-tb|ltr|mathematical|max-height|max-size|medium|menu|message-box|middle|move|n-resize|ne-resize|newspaper|no-change|no-close-quote|no-drop|no-open-quote|no-repeat|none|normal|not-allowed|nowrap|nw-resize|oblique|open-quote|outset|outside|overline|padding-box|page|pointer|pre-line|pre-wrap|pre|preserve-3d|progress|relative|repeat-x|repeat-y|repeat|replaced|reset-size|ridge|right|round|row-resize|rtl|s-resize|scroll|se-resize|separate|slice|small-caps|small-caption|solid|space|square|start|static|status-bar|step-end|step-start|steps|stretch|strict|sub|super|sw-resize|table-caption|table-cell|table-column-group|table-column|table-footer-group|table-header-group|table-row-group|table-row|table|tb-rl|text-after-edge|text-before-edge|text-bottom|text-size|text-top|text|thick|thin|transparent|underline|upper-alpha|upper-latin|upper-roman|uppercase|use-script|vertical-ideographic|vertical-text|visible|w-resize|wait|whitespace|z-index|zero\",f=t.supportConstantColor=\"aqua|black|blue|fuchsia|gray|green|lime|maroon|navy|olive|orange|purple|red|silver|teal|white|yellow\",l=t.supportConstantFonts=\"arial|century|comic|courier|cursive|fantasy|garamond|georgia|helvetica|impact|lucida|symbol|system|tahoma|times|trebuchet|utopia|verdana|webdings|sans-serif|serif|monospace\",c=t.numRe=\"\\\\-?(?:(?:[0-9]+)|(?:[0-9]*\\\\.[0-9]+))\",h=t.pseudoElements=\"(\\\\:+)\\\\b(after|before|first-letter|first-line|moz-selection|selection)\\\\b\",p=t.pseudoClasses=\"(:)\\\\b(active|checked|disabled|empty|enabled|first-child|first-of-type|focus|hover|indeterminate|invalid|last-child|last-of-type|link|not|nth-child|nth-last-child|nth-last-of-type|nth-of-type|only-child|only-of-type|required|root|target|valid|visited)\\\\b\",d=function(){var e=this.createKeywordMapper({\"support.function\":u,\"support.constant\":a,\"support.type\":o,\"support.constant.color\":f,\"support.constant.fonts\":l},\"text\",!0);this.$rules={start:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"@.*?{\",push:\"media\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],media:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"\\\\}\",next:\"pop\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],comment:[{token:\"comment\",regex:\"\\\\*\\\\/\",next:\"pop\"},{defaultToken:\"comment\"}],ruleset:[{token:\"paren.rparen\",regex:\"\\\\}\",next:\"pop\"},{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},{token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},{token:[\"constant.numeric\",\"keyword\"],regex:\"(\"+c+\")(ch|cm|deg|em|ex|fr|gd|grad|Hz|in|kHz|mm|ms|pc|pt|px|rad|rem|s|turn|vh|vm|vw|%)\"},{token:\"constant.numeric\",regex:c},{token:\"constant.numeric\",regex:\"#[a-f0-9]{6}\"},{token:\"constant.numeric\",regex:\"#[a-f0-9]{3}\"},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-element.css\"],regex:h},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-class.css\"],regex:p},{token:[\"support.function\",\"string\",\"support.function\"],regex:\"(url\\\\()(.*)(\\\\))\"},{token:e,regex:\"\\\\-?[a-zA-Z_][a-zA-Z0-9_\\\\-]*\"},{caseInsensitive:!0}]},this.normalizeRules()};r.inherits(d,s),t.CssHighlightRules=d}),define(\"ace/mode/css_completions\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={background:{\"#$0\":1},\"background-color\":{\"#$0\":1,transparent:1,fixed:1},\"background-image\":{\"url('/$0')\":1},\"background-repeat\":{repeat:1,\"repeat-x\":1,\"repeat-y\":1,\"no-repeat\":1,inherit:1},\"background-position\":{bottom:2,center:2,left:2,right:2,top:2,inherit:2},\"background-attachment\":{scroll:1,fixed:1},\"background-size\":{cover:1,contain:1},\"background-clip\":{\"border-box\":1,\"padding-box\":1,\"content-box\":1},\"background-origin\":{\"border-box\":1,\"padding-box\":1,\"content-box\":1},border:{\"solid $0\":1,\"dashed $0\":1,\"dotted $0\":1,\"#$0\":1},\"border-color\":{\"#$0\":1},\"border-style\":{solid:2,dashed:2,dotted:2,\"double\":2,groove:2,hidden:2,inherit:2,inset:2,none:2,outset:2,ridged:2},\"border-collapse\":{collapse:1,separate:1},bottom:{px:1,em:1,\"%\":1},clear:{left:1,right:1,both:1,none:1},color:{\"#$0\":1,\"rgb(#$00,0,0)\":1},cursor:{\"default\":1,pointer:1,move:1,text:1,wait:1,help:1,progress:1,\"n-resize\":1,\"ne-resize\":1,\"e-resize\":1,\"se-resize\":1,\"s-resize\":1,\"sw-resize\":1,\"w-resize\":1,\"nw-resize\":1},display:{none:1,block:1,inline:1,\"inline-block\":1,\"table-cell\":1},\"empty-cells\":{show:1,hide:1},\"float\":{left:1,right:1,none:1},\"font-family\":{Arial:2,\"Comic Sans MS\":2,Consolas:2,\"Courier New\":2,Courier:2,Georgia:2,Monospace:2,\"Sans-Serif\":2,\"Segoe UI\":2,Tahoma:2,\"Times New Roman\":2,\"Trebuchet MS\":2,Verdana:1},\"font-size\":{px:1,em:1,\"%\":1},\"font-weight\":{bold:1,normal:1},\"font-style\":{italic:1,normal:1},\"font-variant\":{normal:1,\"small-caps\":1},height:{px:1,em:1,\"%\":1},left:{px:1,em:1,\"%\":1},\"letter-spacing\":{normal:1},\"line-height\":{normal:1},\"list-style-type\":{none:1,disc:1,circle:1,square:1,decimal:1,\"decimal-leading-zero\":1,\"lower-roman\":1,\"upper-roman\":1,\"lower-greek\":1,\"lower-latin\":1,\"upper-latin\":1,georgian:1,\"lower-alpha\":1,\"upper-alpha\":1},margin:{px:1,em:1,\"%\":1},\"margin-right\":{px:1,em:1,\"%\":1},\"margin-left\":{px:1,em:1,\"%\":1},\"margin-top\":{px:1,em:1,\"%\":1},\"margin-bottom\":{px:1,em:1,\"%\":1},\"max-height\":{px:1,em:1,\"%\":1},\"max-width\":{px:1,em:1,\"%\":1},\"min-height\":{px:1,em:1,\"%\":1},\"min-width\":{px:1,em:1,\"%\":1},overflow:{hidden:1,visible:1,auto:1,scroll:1},\"overflow-x\":{hidden:1,visible:1,auto:1,scroll:1},\"overflow-y\":{hidden:1,visible:1,auto:1,scroll:1},padding:{px:1,em:1,\"%\":1},\"padding-top\":{px:1,em:1,\"%\":1},\"padding-right\":{px:1,em:1,\"%\":1},\"padding-bottom\":{px:1,em:1,\"%\":1},\"padding-left\":{px:1,em:1,\"%\":1},\"page-break-after\":{auto:1,always:1,avoid:1,left:1,right:1},\"page-break-before\":{auto:1,always:1,avoid:1,left:1,right:1},position:{absolute:1,relative:1,fixed:1,\"static\":1},right:{px:1,em:1,\"%\":1},\"table-layout\":{fixed:1,auto:1},\"text-decoration\":{none:1,underline:1,\"line-through\":1,blink:1},\"text-align\":{left:1,right:1,center:1,justify:1},\"text-transform\":{capitalize:1,uppercase:1,lowercase:1,none:1},top:{px:1,em:1,\"%\":1},\"vertical-align\":{top:1,bottom:1},visibility:{hidden:1,visible:1},\"white-space\":{nowrap:1,normal:1,pre:1,\"pre-line\":1,\"pre-wrap\":1},width:{px:1,em:1,\"%\":1},\"word-spacing\":{normal:1},filter:{\"alpha(opacity=$0100)\":1},\"text-shadow\":{\"$02px 2px 2px #777\":1},\"text-overflow\":{\"ellipsis-word\":1,clip:1,ellipsis:1},\"-moz-border-radius\":1,\"-moz-border-radius-topright\":1,\"-moz-border-radius-bottomright\":1,\"-moz-border-radius-topleft\":1,\"-moz-border-radius-bottomleft\":1,\"-webkit-border-radius\":1,\"-webkit-border-top-right-radius\":1,\"-webkit-border-top-left-radius\":1,\"-webkit-border-bottom-right-radius\":1,\"-webkit-border-bottom-left-radius\":1,\"-moz-box-shadow\":1,\"-webkit-box-shadow\":1,transform:{\"rotate($00deg)\":1,\"skew($00deg)\":1},\"-moz-transform\":{\"rotate($00deg)\":1,\"skew($00deg)\":1},\"-webkit-transform\":{\"rotate($00deg)\":1,\"skew($00deg)\":1}},i=function(){};(function(){this.completionsDefined=!1,this.defineCompletions=function(){if(document){var e=document.createElement(\"c\").style;for(var t in e){if(typeof e[t]!=\"string\")continue;var n=t.replace(/[A-Z]/g,function(e){return\"-\"+e.toLowerCase()});r.hasOwnProperty(n)||(r[n]=1)}}this.completionsDefined=!0},this.getCompletions=function(e,t,n,r){this.completionsDefined||this.defineCompletions();var i=t.getTokenAt(n.row,n.column);if(!i)return[];if(e===\"ruleset\"){var s=t.getLine(n.row).substr(0,n.column);return/:[^;]+$/.test(s)?(/([\\w\\-]+):[^:]*$/.test(s),this.getPropertyValueCompletions(e,t,n,r)):this.getPropertyCompletions(e,t,n,r)}return[]},this.getPropertyCompletions=function(e,t,n,i){var s=Object.keys(r);return s.map(function(e){return{caption:e,snippet:e+\": $0\",meta:\"property\",score:Number.MAX_VALUE}})},this.getPropertyValueCompletions=function(e,t,n,i){var s=t.getLine(n.row).substr(0,n.column),o=(/([\\w\\-]+):[^:]*$/.exec(s)||{})[1];if(!o)return[];var u=[];return o in r&&typeof r[o]==\"object\"&&(u=Object.keys(r[o])),u.map(function(e){return{caption:e,snippet:e,meta:\"property value\",score:Number.MAX_VALUE}})}}).call(i.prototype),t.CssCompletions=i}),define(\"ace/mode/behaviour/css\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/mode/behaviour/cstyle\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"./cstyle\").CstyleBehaviour,o=e(\"../../token_iterator\").TokenIterator,u=function(){this.inherit(s),this.add(\"colon\",\"insertion\",function(e,t,n,r,i){if(i===\":\"){var s=n.getCursorPosition(),u=new o(r,s.row,s.column),a=u.getCurrentToken();a&&a.value.match(/\\s+/)&&(a=u.stepBackward());if(a&&a.type===\"support.type\"){var f=r.doc.getLine(s.row),l=f.substring(s.column,s.column+1);if(l===\":\")return{text:\"\",selection:[1,1]};if(!f.substring(s.column).match(/^\\s*;/))return{text:\":;\",selection:[1,1]}}}}),this.add(\"colon\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&s===\":\"){var u=n.getCursorPosition(),a=new o(r,u.row,u.column),f=a.getCurrentToken();f&&f.value.match(/\\s+/)&&(f=a.stepBackward());if(f&&f.type===\"support.type\"){var l=r.doc.getLine(i.start.row),c=l.substring(i.end.column,i.end.column+1);if(c===\";\")return i.end.column++,i}}}),this.add(\"semicolon\",\"insertion\",function(e,t,n,r,i){if(i===\";\"){var s=n.getCursorPosition(),o=r.doc.getLine(s.row),u=o.substring(s.column,s.column+1);if(u===\";\")return{text:\"\",selection:[1,1]}}})};r.inherits(u,s),t.CssBehaviour=u}),define(\"ace/mode/css\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/css_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/css_completions\",\"ace/mode/behaviour/css\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./css_highlight_rules\").CssHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./css_completions\").CssCompletions,f=e(\"./behaviour/css\").CssBehaviour,l=e(\"./folding/cstyle\").FoldMode,c=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new f,this.$completer=new a,this.foldingRules=new l};r.inherits(c,i),function(){this.foldingRules=\"cStyle\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e).tokens;if(i.length&&i[i.length-1].type==\"comment\")return r;var s=t.match(/^.*\\{\\s*$/);return s&&(r+=n),r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.getCompletions=function(e,t,n,r){return this.$completer.getCompletions(e,t,n,r)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/css_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/css\"}.call(c.prototype),t.Mode=c}),define(\"ace/mode/xml_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(e){var t=\"[_:a-zA-Z\\u00c0-\\uffff][-_:.a-zA-Z0-9\\u00c0-\\uffff]*\";this.$rules={start:[{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\",next:\"cdata\"},{token:[\"punctuation.xml-decl.xml\",\"keyword.xml-decl.xml\"],regex:\"(<\\\\?)(xml)(?=[\\\\s])\",next:\"xml_decl\",caseInsensitive:!0},{token:[\"punctuation.instruction.xml\",\"keyword.instruction.xml\"],regex:\"(<\\\\?)(\"+t+\")\",next:\"processing_instruction\"},{token:\"comment.xml\",regex:\"<\\\\!--\",next:\"comment\"},{token:[\"xml-pe.doctype.xml\",\"xml-pe.doctype.xml\"],regex:\"(<\\\\!)(DOCTYPE)(?=[\\\\s])\",next:\"doctype\",caseInsensitive:!0},{include:\"tag\"},{token:\"text.end-tag-open.xml\",regex:\"</\"},{token:\"text.tag-open.xml\",regex:\"<\"},{include:\"reference\"},{defaultToken:\"text.xml\"}],xml_decl:[{token:\"entity.other.attribute-name.decl-attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.decl-attribute-equals.xml\",regex:\"=\"},{include:\"whitespace\"},{include:\"string\"},{token:\"punctuation.xml-decl.xml\",regex:\"\\\\?>\",next:\"start\"}],processing_instruction:[{token:\"punctuation.instruction.xml\",regex:\"\\\\?>\",next:\"start\"},{defaultToken:\"instruction.xml\"}],doctype:[{include:\"whitespace\"},{include:\"string\"},{token:\"xml-pe.doctype.xml\",regex:\">\",next:\"start\"},{token:\"xml-pe.xml\",regex:\"[-_a-zA-Z0-9:]+\"},{token:\"punctuation.int-subset\",regex:\"\\\\[\",push:\"int_subset\"}],int_subset:[{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"punctuation.int-subset.xml\",regex:\"]\",next:\"pop\"},{token:[\"punctuation.markup-decl.xml\",\"keyword.markup-decl.xml\"],regex:\"(<\\\\!)(\"+t+\")\",push:[{token:\"text\",regex:\"\\\\s+\"},{token:\"punctuation.markup-decl.xml\",regex:\">\",next:\"pop\"},{include:\"string\"}]}],cdata:[{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\",next:\"start\"},{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"text.xml\",regex:\"(?:[^\\\\]]|\\\\](?!\\\\]>))+\"}],comment:[{token:\"comment.xml\",regex:\"-->\",next:\"start\"},{defaultToken:\"comment.xml\"}],reference:[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],attr_reference:[{token:\"constant.language.escape.reference.attribute-value.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],tag:[{token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.tag-name.xml\"],regex:\"(?:(<)|(</))((?:\"+t+\":)?\"+t+\")\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}],tag_whitespace:[{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"}],whitespace:[{token:\"text.whitespace.xml\",regex:\"\\\\s+\"}],string:[{token:\"string.xml\",regex:\"'\",push:[{token:\"string.xml\",regex:\"'\",next:\"pop\"},{defaultToken:\"string.xml\"}]},{token:\"string.xml\",regex:'\"',push:[{token:\"string.xml\",regex:'\"',next:\"pop\"},{defaultToken:\"string.xml\"}]}],attributes:[{token:\"entity.other.attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{include:\"tag_whitespace\"},{include:\"attribute_value\"}],attribute_value:[{token:\"string.attribute-value.xml\",regex:\"'\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]}]},this.constructor===s&&this.normalizeRules()};(function(){this.embedTagRules=function(e,t,n){this.$rules.tag.unshift({token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(<)(\"+n+\"(?=\\\\s|>|$))\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:t+\"start\"}]}),this.$rules[n+\"-end\"]=[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\",onMatch:function(e,t,n){return n.splice(0),this.token}}],this.embedRules(e,t,[{token:[\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(</)(\"+n+\"(?=\\\\s|>|$))\",next:n+\"-end\"},{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\"},{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\"}])}}).call(i.prototype),r.inherits(s,i),t.XmlHighlightRules=s}),define(\"ace/mode/html_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/css_highlight_rules\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/xml_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./css_highlight_rules\").CssHighlightRules,o=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,u=e(\"./xml_highlight_rules\").XmlHighlightRules,a=i.createMap({a:\"anchor\",button:\"form\",form:\"form\",img:\"image\",input:\"form\",label:\"form\",option:\"form\",script:\"script\",select:\"form\",textarea:\"form\",style:\"style\",table:\"table\",tbody:\"table\",td:\"table\",tfoot:\"table\",th:\"table\",tr:\"table\"}),f=function(){u.call(this),this.addRules({attributes:[{include:\"tag_whitespace\"},{token:\"entity.other.attribute-name.xml\",regex:\"[-_a-zA-Z0-9:.]+\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\",push:[{include:\"tag_whitespace\"},{token:\"string.unquoted.attribute-value.html\",regex:\"[^<>='\\\"`\\\\s]+\",next:\"pop\"},{token:\"empty\",regex:\"\",next:\"pop\"}]},{include:\"attribute_value\"}],tag:[{token:function(e,t){var n=a[t];return[\"meta.tag.punctuation.\"+(e==\"<\"?\"\":\"end-\")+\"tag-open.xml\",\"meta.tag\"+(n?\".\"+n:\"\")+\".tag-name.xml\"]},regex:\"(</?)([-_a-zA-Z0-9:.]+)\",next:\"tag_stuff\"}],tag_stuff:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}),this.embedTagRules(s,\"css-\",\"style\"),this.embedTagRules((new o({jsx:!1})).getRules(),\"js-\",\"script\"),this.constructor===f&&this.normalizeRules()};r.inherits(f,u),t.HtmlHighlightRules=f}),define(\"ace/mode/behaviour/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/token_iterator\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";function u(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"../../token_iterator\").TokenIterator,o=e(\"../../lib/lang\"),a=function(){this.add(\"string_dquotes\",\"insertion\",function(e,t,n,r,i){if(i=='\"'||i==\"'\"){var o=i,a=r.doc.getTextRange(n.getSelectionRange());if(a!==\"\"&&a!==\"'\"&&a!='\"'&&n.getWrapBehavioursEnabled())return{text:o+a+o,selection:!1};var f=n.getCursorPosition(),l=r.doc.getLine(f.row),c=l.substring(f.column,f.column+1),h=new s(r,f.row,f.column),p=h.getCurrentToken();if(c==o&&(u(p,\"attribute-value\")||u(p,\"string\")))return{text:\"\",selection:[1,1]};p||(p=h.stepBackward());if(!p)return;while(u(p,\"tag-whitespace\")||u(p,\"whitespace\"))p=h.stepBackward();var d=!c||c.match(/\\s/);if(u(p,\"attribute-equals\")&&(d||c==\">\")||u(p,\"decl-attribute-equals\")&&(d||c==\"?\"))return{text:o+o,selection:[1,1]}}}),this.add(\"string_dquotes\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&(s=='\"'||s==\"'\")){var o=r.doc.getLine(i.start.row),u=o.substring(i.start.column+1,i.start.column+2);if(u==s)return i.end.column++,i}}),this.add(\"autoclosing\",\"insertion\",function(e,t,n,r,i){if(i==\">\"){var o=n.getSelectionRange().start,a=new s(r,o.row,o.column),f=a.getCurrentToken()||a.stepBackward();if(!f||!(u(f,\"tag-name\")||u(f,\"tag-whitespace\")||u(f,\"attribute-name\")||u(f,\"attribute-equals\")||u(f,\"attribute-value\")))return;if(u(f,\"reference.attribute-value\"))return;if(u(f,\"attribute-value\")){var l=f.value.charAt(0);if(l=='\"'||l==\"'\"){var c=f.value.charAt(f.value.length-1),h=a.getCurrentTokenColumn()+f.value.length;if(h>o.column||h==o.column&&l!=c)return}}while(!u(f,\"tag-name\")){f=a.stepBackward();if(f.value==\"<\"){f=a.stepForward();break}}var p=a.getCurrentTokenRow(),d=a.getCurrentTokenColumn();if(u(a.stepBackward(),\"end-tag-open\"))return;var v=f.value;p==o.row&&(v=v.substring(0,o.column-d));if(this.voidElements.hasOwnProperty(v.toLowerCase()))return;return{text:\"></\"+v+\">\",selection:[1,1]}}}),this.add(\"autoindent\",\"insertion\",function(e,t,n,r,i){if(i==\"\\n\"){var o=n.getCursorPosition(),u=r.getLine(o.row),a=new s(r,o.row,o.column),f=a.getCurrentToken();if(f&&f.type.indexOf(\"tag-close\")!==-1){if(f.value==\"/>\")return;while(f&&f.type.indexOf(\"tag-name\")===-1)f=a.stepBackward();if(!f)return;var l=f.value,c=a.getCurrentTokenRow();f=a.stepBackward();if(!f||f.type.indexOf(\"end-tag\")!==-1)return;if(this.voidElements&&!this.voidElements[l]){var h=r.getTokenAt(o.row,o.column+1),u=r.getLine(c),p=this.$getIndent(u),d=p+r.getTabString();return h&&h.value===\"</\"?{text:\"\\n\"+d+\"\\n\"+p,selection:[1,d.length,1,d.length]}:{text:\"\\n\"+d}}}}})};r.inherits(a,i),t.XmlBehaviour=a}),define(\"ace/mode/folding/mixed\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=t.FoldMode=function(e,t){this.defaultMode=e,this.subModes=t};r.inherits(s,i),function(){this.$getMode=function(e){typeof e!=\"string\"&&(e=e[0]);for(var t in this.subModes)if(e.indexOf(t)===0)return this.subModes[t];return null},this.$tryMode=function(e,t,n,r){var i=this.$getMode(e);return i?i.getFoldWidget(t,n,r):\"\"},this.getFoldWidget=function(e,t,n){return this.$tryMode(e.getState(n-1),e,t,n)||this.$tryMode(e.getState(n),e,t,n)||this.defaultMode.getFoldWidget(e,t,n)},this.getFoldWidgetRange=function(e,t,n){var r=this.$getMode(e.getState(n-1));if(!r||!r.getFoldWidget(e,t,n))r=this.$getMode(e.getState(n));if(!r||!r.getFoldWidget(e,t,n))r=this.defaultMode;return r.getFoldWidgetRange(e,t,n)}}.call(s.prototype)}),define(\"ace/mode/folding/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/range\",\"ace/mode/folding/fold_mode\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";function l(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}var r=e(\"../../lib/oop\"),i=e(\"../../lib/lang\"),s=e(\"../../range\").Range,o=e(\"./fold_mode\").FoldMode,u=e(\"../../token_iterator\").TokenIterator,a=t.FoldMode=function(e,t){o.call(this),this.voidElements=e||{},this.optionalEndTags=r.mixin({},this.voidElements),t&&r.mixin(this.optionalEndTags,t)};r.inherits(a,o);var f=function(){this.tagName=\"\",this.closing=!1,this.selfClosing=!1,this.start={row:0,column:0},this.end={row:0,column:0}};(function(){this.getFoldWidget=function(e,t,n){var r=this._getFirstTagInLine(e,n);return r?r.closing||!r.tagName&&r.selfClosing?t==\"markbeginend\"?\"end\":\"\":!r.tagName||r.selfClosing||this.voidElements.hasOwnProperty(r.tagName.toLowerCase())?\"\":this._findEndTagInLine(e,n,r.tagName,r.end.column)?\"\":\"start\":\"\"},this._getFirstTagInLine=function(e,t){var n=e.getTokens(t),r=new f;for(var i=0;i<n.length;i++){var s=n[i];if(l(s,\"tag-open\")){r.end.column=r.start.column+s.value.length,r.closing=l(s,\"end-tag-open\"),s=n[++i];if(!s)return null;r.tagName=s.value,r.end.column+=s.value.length;for(i++;i<n.length;i++){s=n[i],r.end.column+=s.value.length;if(l(s,\"tag-close\")){r.selfClosing=s.value==\"/>\";break}}return r}if(l(s,\"tag-close\"))return r.selfClosing=s.value==\"/>\",r;r.start.column+=s.value.length}return null},this._findEndTagInLine=function(e,t,n,r){var i=e.getTokens(t),s=0;for(var o=0;o<i.length;o++){var u=i[o];s+=u.value.length;if(s<r)continue;if(l(u,\"end-tag-open\")){u=i[o+1];if(u&&u.value==n)return!0}}return!1},this._readTagForward=function(e){var t=e.getCurrentToken();if(!t)return null;var n=new f;do if(l(t,\"tag-open\"))n.closing=l(t,\"end-tag-open\"),n.start.row=e.getCurrentTokenRow(),n.start.column=e.getCurrentTokenColumn();else if(l(t,\"tag-name\"))n.tagName=t.value;else if(l(t,\"tag-close\"))return n.selfClosing=t.value==\"/>\",n.end.row=e.getCurrentTokenRow(),n.end.column=e.getCurrentTokenColumn()+t.value.length,e.stepForward(),n;while(t=e.stepForward());return null},this._readTagBackward=function(e){var t=e.getCurrentToken();if(!t)return null;var n=new f;do{if(l(t,\"tag-open\"))return n.closing=l(t,\"end-tag-open\"),n.start.row=e.getCurrentTokenRow(),n.start.column=e.getCurrentTokenColumn(),e.stepBackward(),n;l(t,\"tag-name\")?n.tagName=t.value:l(t,\"tag-close\")&&(n.selfClosing=t.value==\"/>\",n.end.row=e.getCurrentTokenRow(),n.end.column=e.getCurrentTokenColumn()+t.value.length)}while(t=e.stepBackward());return null},this._pop=function(e,t){while(e.length){var n=e[e.length-1];if(!t||n.tagName==t.tagName)return e.pop();if(this.optionalEndTags.hasOwnProperty(n.tagName)){e.pop();continue}return null}},this.getFoldWidgetRange=function(e,t,n){var r=this._getFirstTagInLine(e,n);if(!r)return null;var i=r.closing||r.selfClosing,o=[],a;if(!i){var f=new u(e,n,r.start.column),l={row:n,column:r.start.column+r.tagName.length+2};r.start.row==r.end.row&&(l.column=r.end.column);while(a=this._readTagForward(f)){if(a.selfClosing){if(!o.length)return a.start.column+=a.tagName.length+2,a.end.column-=2,s.fromPoints(a.start,a.end);continue}if(a.closing){this._pop(o,a);if(o.length==0)return s.fromPoints(l,a.start)}else o.push(a)}}else{var f=new u(e,n,r.end.column),c={row:n,column:r.start.column};while(a=this._readTagBackward(f)){if(a.selfClosing){if(!o.length)return a.start.column+=a.tagName.length+2,a.end.column-=2,s.fromPoints(a.start,a.end);continue}if(!a.closing){this._pop(o,a);if(o.length==0)return a.start.column+=a.tagName.length+2,a.start.row==a.end.row&&a.start.column<a.end.column&&(a.start.column=a.end.column),s.fromPoints(a.start,c)}else o.push(a)}}}}).call(a.prototype)}),define(\"ace/mode/folding/html\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/mixed\",\"ace/mode/folding/xml\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./mixed\").FoldMode,s=e(\"./xml\").FoldMode,o=e(\"./cstyle\").FoldMode,u=t.FoldMode=function(e,t){i.call(this,new s(e,t),{\"js-\":new o,\"css-\":new o})};r.inherits(u,i)}),define(\"ace/mode/html_completions\",[\"require\",\"exports\",\"module\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";function f(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}function l(e,t){var n=new r(e,t.row,t.column),i=n.getCurrentToken();while(i&&!f(i,\"tag-name\"))i=n.stepBackward();if(i)return i.value}function c(e,t){var n=new r(e,t.row,t.column),i=n.getCurrentToken();while(i&&!f(i,\"attribute-name\"))i=n.stepBackward();if(i)return i.value}var r=e(\"../token_iterator\").TokenIterator,i=[\"accesskey\",\"class\",\"contenteditable\",\"contextmenu\",\"dir\",\"draggable\",\"dropzone\",\"hidden\",\"id\",\"inert\",\"itemid\",\"itemprop\",\"itemref\",\"itemscope\",\"itemtype\",\"lang\",\"spellcheck\",\"style\",\"tabindex\",\"title\",\"translate\"],s=[\"onabort\",\"onblur\",\"oncancel\",\"oncanplay\",\"oncanplaythrough\",\"onchange\",\"onclick\",\"onclose\",\"oncontextmenu\",\"oncuechange\",\"ondblclick\",\"ondrag\",\"ondragend\",\"ondragenter\",\"ondragleave\",\"ondragover\",\"ondragstart\",\"ondrop\",\"ondurationchange\",\"onemptied\",\"onended\",\"onerror\",\"onfocus\",\"oninput\",\"oninvalid\",\"onkeydown\",\"onkeypress\",\"onkeyup\",\"onload\",\"onloadeddata\",\"onloadedmetadata\",\"onloadstart\",\"onmousedown\",\"onmousemove\",\"onmouseout\",\"onmouseover\",\"onmouseup\",\"onmousewheel\",\"onpause\",\"onplay\",\"onplaying\",\"onprogress\",\"onratechange\",\"onreset\",\"onscroll\",\"onseeked\",\"onseeking\",\"onselect\",\"onshow\",\"onstalled\",\"onsubmit\",\"onsuspend\",\"ontimeupdate\",\"onvolumechange\",\"onwaiting\"],o=i.concat(s),u={html:{manifest:1},head:{},title:{},base:{href:1,target:1},link:{href:1,hreflang:1,rel:{stylesheet:1,icon:1},media:{all:1,screen:1,print:1},type:{\"text/css\":1,\"image/png\":1,\"image/jpeg\":1,\"image/gif\":1},sizes:1},meta:{\"http-equiv\":{\"content-type\":1},name:{description:1,keywords:1},content:{\"text/html; charset=UTF-8\":1},charset:1},style:{type:1,media:{all:1,screen:1,print:1},scoped:1},script:{charset:1,type:{\"text/javascript\":1},src:1,defer:1,async:1},noscript:{href:1},body:{onafterprint:1,onbeforeprint:1,onbeforeunload:1,onhashchange:1,onmessage:1,onoffline:1,onpopstate:1,onredo:1,onresize:1,onstorage:1,onundo:1,onunload:1},section:{},nav:{},article:{pubdate:1},aside:{},h1:{},h2:{},h3:{},h4:{},h5:{},h6:{},header:{},footer:{},address:{},main:{},p:{},hr:{},pre:{},blockquote:{cite:1},ol:{start:1,reversed:1},ul:{},li:{value:1},dl:{},dt:{},dd:{},figure:{},figcaption:{},div:{},a:{href:1,target:{_blank:1,top:1},ping:1,rel:{nofollow:1,alternate:1,author:1,bookmark:1,help:1,license:1,next:1,noreferrer:1,prefetch:1,prev:1,search:1,tag:1},media:1,hreflang:1,type:1},em:{},strong:{},small:{},s:{},cite:{},q:{cite:1},dfn:{},abbr:{},data:{},time:{datetime:1},code:{},\"var\":{},samp:{},kbd:{},sub:{},sup:{},i:{},b:{},u:{},mark:{},ruby:{},rt:{},rp:{},bdi:{},bdo:{},span:{},br:{},wbr:{},ins:{cite:1,datetime:1},del:{cite:1,datetime:1},img:{alt:1,src:1,height:1,width:1,usemap:1,ismap:1},iframe:{name:1,src:1,height:1,width:1,sandbox:{\"allow-same-origin\":1,\"allow-top-navigation\":1,\"allow-forms\":1,\"allow-scripts\":1},seamless:{seamless:1}},embed:{src:1,height:1,width:1,type:1},object:{param:1,data:1,type:1,height:1,width:1,usemap:1,name:1,form:1,classid:1},param:{name:1,value:1},video:{src:1,autobuffer:1,autoplay:{autoplay:1},loop:{loop:1},controls:{controls:1},width:1,height:1,poster:1,muted:{muted:1},preload:{auto:1,metadata:1,none:1}},audio:{src:1,autobuffer:1,autoplay:{autoplay:1},loop:{loop:1},controls:{controls:1},muted:{muted:1},preload:{auto:1,metadata:1,none:1}},source:{src:1,type:1,media:1},track:{kind:1,src:1,srclang:1,label:1,\"default\":1},canvas:{width:1,height:1},map:{name:1},area:{shape:1,coords:1,href:1,hreflang:1,alt:1,target:1,media:1,rel:1,ping:1,type:1},svg:{},math:{},table:{summary:1},caption:{},colgroup:{span:1},col:{span:1},tbody:{},thead:{},tfoot:{},tr:{},td:{headers:1,rowspan:1,colspan:1},th:{headers:1,rowspan:1,colspan:1,scope:1},form:{\"accept-charset\":1,action:1,autocomplete:1,enctype:{\"multipart/form-data\":1,\"application/x-www-form-urlencoded\":1},method:{get:1,post:1},name:1,novalidate:1,target:{_blank:1,top:1}},fieldset:{disabled:1,form:1,name:1},legend:{},label:{form:1,\"for\":1},input:{type:{text:1,password:1,hidden:1,checkbox:1,submit:1,radio:1,file:1,button:1,reset:1,image:31,color:1,date:1,datetime:1,\"datetime-local\":1,email:1,month:1,number:1,range:1,search:1,tel:1,time:1,url:1,week:1},accept:1,alt:1,autocomplete:{on:1,off:1},autofocus:{autofocus:1},checked:{checked:1},disabled:{disabled:1},form:1,formaction:1,formenctype:{\"application/x-www-form-urlencoded\":1,\"multipart/form-data\":1,\"text/plain\":1},formmethod:{get:1,post:1},formnovalidate:{formnovalidate:1},formtarget:{_blank:1,_self:1,_parent:1,_top:1},height:1,list:1,max:1,maxlength:1,min:1,multiple:{multiple:1},name:1,pattern:1,placeholder:1,readonly:{readonly:1},required:{required:1},size:1,src:1,step:1,width:1,files:1,value:1},button:{autofocus:1,disabled:{disabled:1},form:1,formaction:1,formenctype:1,formmethod:1,formnovalidate:1,formtarget:1,name:1,value:1,type:{button:1,submit:1}},select:{autofocus:1,disabled:1,form:1,multiple:{multiple:1},name:1,size:1,readonly:{readonly:1}},datalist:{},optgroup:{disabled:1,label:1},option:{disabled:1,selected:1,label:1,value:1},textarea:{autofocus:{autofocus:1},disabled:{disabled:1},form:1,maxlength:1,name:1,placeholder:1,readonly:{readonly:1},required:{required:1},rows:1,cols:1,wrap:{on:1,off:1,hard:1,soft:1}},keygen:{autofocus:1,challenge:{challenge:1},disabled:{disabled:1},form:1,keytype:{rsa:1,dsa:1,ec:1},name:1},output:{\"for\":1,form:1,name:1},progress:{value:1,max:1},meter:{value:1,min:1,max:1,low:1,high:1,optimum:1},details:{open:1},summary:{},command:{type:1,label:1,icon:1,disabled:1,checked:1,radiogroup:1,command:1},menu:{type:1,label:1},dialog:{open:1}},a=Object.keys(u),h=function(){};(function(){this.getCompletions=function(e,t,n,r){var i=t.getTokenAt(n.row,n.column);if(!i)return[];if(f(i,\"tag-name\")||f(i,\"tag-open\")||f(i,\"end-tag-open\"))return this.getTagCompletions(e,t,n,r);if(f(i,\"tag-whitespace\")||f(i,\"attribute-name\"))return this.getAttributeCompletions(e,t,n,r);if(f(i,\"attribute-value\"))return this.getAttributeValueCompletions(e,t,n,r);var s=t.getLine(n.row).substr(0,n.column);return/&[a-z]*$/i.test(s)?this.getHTMLEntityCompletions(e,t,n,r):[]},this.getTagCompletions=function(e,t,n,r){return a.map(function(e){return{value:e,meta:\"tag\",score:Number.MAX_VALUE}})},this.getAttributeCompletions=function(e,t,n,r){var i=l(t,n);if(!i)return[];var s=o;return i in u&&(s=s.concat(Object.keys(u[i]))),s.map(function(e){return{caption:e,snippet:e+'=\"$0\"',meta:\"attribute\",score:Number.MAX_VALUE}})},this.getAttributeValueCompletions=function(e,t,n,r){var i=l(t,n),s=c(t,n);if(!i)return[];var o=[];return i in u&&s in u[i]&&typeof u[i][s]==\"object\"&&(o=Object.keys(u[i][s])),o.map(function(e){return{caption:e,snippet:e,meta:\"attribute value\",score:Number.MAX_VALUE}})},this.getHTMLEntityCompletions=function(e,t,n,r){var i=[\"Aacute;\",\"aacute;\",\"Acirc;\",\"acirc;\",\"acute;\",\"AElig;\",\"aelig;\",\"Agrave;\",\"agrave;\",\"alefsym;\",\"Alpha;\",\"alpha;\",\"amp;\",\"and;\",\"ang;\",\"Aring;\",\"aring;\",\"asymp;\",\"Atilde;\",\"atilde;\",\"Auml;\",\"auml;\",\"bdquo;\",\"Beta;\",\"beta;\",\"brvbar;\",\"bull;\",\"cap;\",\"Ccedil;\",\"ccedil;\",\"cedil;\",\"cent;\",\"Chi;\",\"chi;\",\"circ;\",\"clubs;\",\"cong;\",\"copy;\",\"crarr;\",\"cup;\",\"curren;\",\"Dagger;\",\"dagger;\",\"dArr;\",\"darr;\",\"deg;\",\"Delta;\",\"delta;\",\"diams;\",\"divide;\",\"Eacute;\",\"eacute;\",\"Ecirc;\",\"ecirc;\",\"Egrave;\",\"egrave;\",\"empty;\",\"emsp;\",\"ensp;\",\"Epsilon;\",\"epsilon;\",\"equiv;\",\"Eta;\",\"eta;\",\"ETH;\",\"eth;\",\"Euml;\",\"euml;\",\"euro;\",\"exist;\",\"fnof;\",\"forall;\",\"frac12;\",\"frac14;\",\"frac34;\",\"frasl;\",\"Gamma;\",\"gamma;\",\"ge;\",\"gt;\",\"hArr;\",\"harr;\",\"hearts;\",\"hellip;\",\"Iacute;\",\"iacute;\",\"Icirc;\",\"icirc;\",\"iexcl;\",\"Igrave;\",\"igrave;\",\"image;\",\"infin;\",\"int;\",\"Iota;\",\"iota;\",\"iquest;\",\"isin;\",\"Iuml;\",\"iuml;\",\"Kappa;\",\"kappa;\",\"Lambda;\",\"lambda;\",\"lang;\",\"laquo;\",\"lArr;\",\"larr;\",\"lceil;\",\"ldquo;\",\"le;\",\"lfloor;\",\"lowast;\",\"loz;\",\"lrm;\",\"lsaquo;\",\"lsquo;\",\"lt;\",\"macr;\",\"mdash;\",\"micro;\",\"middot;\",\"minus;\",\"Mu;\",\"mu;\",\"nabla;\",\"nbsp;\",\"ndash;\",\"ne;\",\"ni;\",\"not;\",\"notin;\",\"nsub;\",\"Ntilde;\",\"ntilde;\",\"Nu;\",\"nu;\",\"Oacute;\",\"oacute;\",\"Ocirc;\",\"ocirc;\",\"OElig;\",\"oelig;\",\"Ograve;\",\"ograve;\",\"oline;\",\"Omega;\",\"omega;\",\"Omicron;\",\"omicron;\",\"oplus;\",\"or;\",\"ordf;\",\"ordm;\",\"Oslash;\",\"oslash;\",\"Otilde;\",\"otilde;\",\"otimes;\",\"Ouml;\",\"ouml;\",\"para;\",\"part;\",\"permil;\",\"perp;\",\"Phi;\",\"phi;\",\"Pi;\",\"pi;\",\"piv;\",\"plusmn;\",\"pound;\",\"Prime;\",\"prime;\",\"prod;\",\"prop;\",\"Psi;\",\"psi;\",\"quot;\",\"radic;\",\"rang;\",\"raquo;\",\"rArr;\",\"rarr;\",\"rceil;\",\"rdquo;\",\"real;\",\"reg;\",\"rfloor;\",\"Rho;\",\"rho;\",\"rlm;\",\"rsaquo;\",\"rsquo;\",\"sbquo;\",\"Scaron;\",\"scaron;\",\"sdot;\",\"sect;\",\"shy;\",\"Sigma;\",\"sigma;\",\"sigmaf;\",\"sim;\",\"spades;\",\"sub;\",\"sube;\",\"sum;\",\"sup;\",\"sup1;\",\"sup2;\",\"sup3;\",\"supe;\",\"szlig;\",\"Tau;\",\"tau;\",\"there4;\",\"Theta;\",\"theta;\",\"thetasym;\",\"thinsp;\",\"THORN;\",\"thorn;\",\"tilde;\",\"times;\",\"trade;\",\"Uacute;\",\"uacute;\",\"uArr;\",\"uarr;\",\"Ucirc;\",\"ucirc;\",\"Ugrave;\",\"ugrave;\",\"uml;\",\"upsih;\",\"Upsilon;\",\"upsilon;\",\"Uuml;\",\"uuml;\",\"weierp;\",\"Xi;\",\"xi;\",\"Yacute;\",\"yacute;\",\"yen;\",\"Yuml;\",\"yuml;\",\"Zeta;\",\"zeta;\",\"zwj;\",\"zwnj;\"];return i.map(function(e){return{caption:e,snippet:e,meta:\"html entity\",score:Number.MAX_VALUE}})}}).call(h.prototype),t.HtmlCompletions=h}),define(\"ace/mode/html\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text\",\"ace/mode/javascript\",\"ace/mode/css\",\"ace/mode/html_highlight_rules\",\"ace/mode/behaviour/xml\",\"ace/mode/folding/html\",\"ace/mode/html_completions\",\"ace/worker/worker_client\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text\").Mode,o=e(\"./javascript\").Mode,u=e(\"./css\").Mode,a=e(\"./html_highlight_rules\").HtmlHighlightRules,f=e(\"./behaviour/xml\").XmlBehaviour,l=e(\"./folding/html\").FoldMode,c=e(\"./html_completions\").HtmlCompletions,h=e(\"../worker/worker_client\").WorkerClient,p=[\"area\",\"base\",\"br\",\"col\",\"embed\",\"hr\",\"img\",\"input\",\"keygen\",\"link\",\"meta\",\"menuitem\",\"param\",\"source\",\"track\",\"wbr\"],d=[\"li\",\"dt\",\"dd\",\"p\",\"rt\",\"rp\",\"optgroup\",\"option\",\"colgroup\",\"td\",\"th\"],v=function(e){this.fragmentContext=e&&e.fragmentContext,this.HighlightRules=a,this.$behaviour=new f,this.$completer=new c,this.createModeDelegates({\"js-\":o,\"css-\":u}),this.foldingRules=new l(this.voidElements,i.arrayToMap(d))};r.inherits(v,s),function(){this.blockComment={start:\"<!--\",end:\"-->\"},this.voidElements=i.arrayToMap(p),this.getNextLineIndent=function(e,t,n){return this.$getIndent(t)},this.checkOutdent=function(e,t,n){return!1},this.getCompletions=function(e,t,n,r){return this.$completer.getCompletions(e,t,n,r)},this.createWorker=function(e){if(this.constructor!=v)return;var t=new h([\"ace\"],\"ace/mode/html_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),this.fragmentContext&&t.call(\"setOptions\",[{context:this.fragmentContext}]),t.on(\"error\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/html\"}.call(v.prototype),t.Mode=v})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-ini.js",
    "content": "define(\"ace/mode/ini_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=\"\\\\\\\\(?:[\\\\\\\\0abtrn;#=:]|x[a-fA-F\\\\d]{4})\",o=function(){this.$rules={start:[{token:\"punctuation.definition.comment.ini\",regex:\"#.*\",push_:[{token:\"comment.line.number-sign.ini\",regex:\"$|^\",next:\"pop\"},{defaultToken:\"comment.line.number-sign.ini\"}]},{token:\"punctuation.definition.comment.ini\",regex:\";.*\",push_:[{token:\"comment.line.semicolon.ini\",regex:\"$|^\",next:\"pop\"},{defaultToken:\"comment.line.semicolon.ini\"}]},{token:[\"keyword.other.definition.ini\",\"text\",\"punctuation.separator.key-value.ini\"],regex:\"\\\\b([a-zA-Z0-9_.-]+)\\\\b(\\\\s*)(=)\"},{token:[\"punctuation.definition.entity.ini\",\"constant.section.group-title.ini\",\"punctuation.definition.entity.ini\"],regex:\"^(\\\\[)(.*?)(\\\\])\"},{token:\"punctuation.definition.string.begin.ini\",regex:\"'\",push:[{token:\"punctuation.definition.string.end.ini\",regex:\"'\",next:\"pop\"},{token:\"constant.language.escape\",regex:s},{defaultToken:\"string.quoted.single.ini\"}]},{token:\"punctuation.definition.string.begin.ini\",regex:'\"',push:[{token:\"constant.language.escape\",regex:s},{token:\"punctuation.definition.string.end.ini\",regex:'\"',next:\"pop\"},{defaultToken:\"string.quoted.double.ini\"}]}]},this.normalizeRules()};o.metaData={fileTypes:[\"ini\",\"conf\"],keyEquivalent:\"^~I\",name:\"Ini\",scopeName:\"source.ini\"},r.inherits(o,i),t.IniHighlightRules=o}),define(\"ace/mode/folding/ini\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(){};r.inherits(o,s),function(){this.foldingStartMarker=/^\\s*\\[([^\\])]*)]\\s*(?:$|[;#])/,this.getFoldWidgetRange=function(e,t,n){var r=this.foldingStartMarker,s=e.getLine(n),o=s.match(r);if(!o)return;var u=o[1]+\".\",a=s.length,f=e.getLength(),l=n,c=n;while(++n<f){s=e.getLine(n);if(/^\\s*$/.test(s))continue;o=s.match(r);if(o&&o[1].lastIndexOf(u,0)!==0)break;c=n}if(c>l){var h=e.getLine(c).length;return new i(l,a,c,h)}}}.call(o.prototype)}),define(\"ace/mode/ini\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/ini_highlight_rules\",\"ace/mode/folding/ini\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./ini_highlight_rules\").IniHighlightRules,o=e(\"./folding/ini\").FoldMode,u=function(){this.HighlightRules=s,this.foldingRules=new o,this.$behaviour=this.$defaultBehaviour};r.inherits(u,i),function(){this.lineCommentStart=\";\",this.blockComment=null,this.$id=\"ace/mode/ini\"}.call(u.prototype),t.Mode=u})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-java.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/javascript_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";function a(){var e=o.replace(\"\\\\d\",\"\\\\d\\\\-\"),t={onMatch:function(e,t,n){var r=e.charAt(1)==\"/\"?2:1;if(r==1)t!=this.nextState?n.unshift(this.next,this.nextState,0):n.unshift(this.next),n[2]++;else if(r==2&&t==this.nextState){n[1]--;if(!n[1]||n[1]<0)n.shift(),n.shift()}return[{type:\"meta.tag.punctuation.\"+(r==1?\"\":\"end-\")+\"tag-open.xml\",value:e.slice(0,r)},{type:\"meta.tag.tag-name.xml\",value:e.substr(r)}]},regex:\"</?\"+e+\"\",next:\"jsxAttributes\",nextState:\"jsx\"};this.$rules.start.unshift(t);var n={regex:\"{\",token:\"paren.quasi.start\",push:\"start\"};this.$rules.jsx=[n,t,{include:\"reference\"},{defaultToken:\"string\"}],this.$rules.jsxAttributes=[{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",onMatch:function(e,t,n){return t==n[0]&&n.shift(),e.length==2&&(n[0]==this.nextState&&n[1]--,(!n[1]||n[1]<0)&&n.splice(0,2)),this.next=n[0]||\"start\",[{type:this.token,value:e}]},nextState:\"jsx\"},n,f(\"jsxAttributes\"),{token:\"entity.other.attribute-name.xml\",regex:e},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"},{token:\"string.attribute-value.xml\",regex:\"'\",stateName:\"jsx_attr_q\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',stateName:\"jsx_attr_qq\",push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},t],this.$rules.reference=[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}]}function f(e){return[{token:\"comment\",regex:/\\/\\*/,next:[i.getTagRule(),{token:\"comment\",regex:\"\\\\*\\\\/\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]},{token:\"comment\",regex:\"\\\\/\\\\/\",next:[i.getTagRule(),{token:\"comment\",regex:\"$|^\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]}]}var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=\"[a-zA-Z\\\\$_\\u00a1-\\uffff][a-zA-Z\\\\d\\\\$_\\u00a1-\\uffff]*\",u=function(e){var t=this.createKeywordMapper({\"variable.language\":\"Array|Boolean|Date|Function|Iterator|Number|Object|RegExp|String|Proxy|Namespace|QName|XML|XMLList|ArrayBuffer|Float32Array|Float64Array|Int16Array|Int32Array|Int8Array|Uint16Array|Uint32Array|Uint8Array|Uint8ClampedArray|Error|EvalError|InternalError|RangeError|ReferenceError|StopIteration|SyntaxError|TypeError|URIError|decodeURI|decodeURIComponent|encodeURI|encodeURIComponent|eval|isFinite|isNaN|parseFloat|parseInt|JSON|Math|this|arguments|prototype|window|document\",keyword:\"const|yield|import|get|set|async|await|break|case|catch|continue|default|delete|do|else|finally|for|function|if|in|of|instanceof|new|return|switch|throw|try|typeof|let|var|while|with|debugger|__parent__|__count__|escape|unescape|with|__proto__|class|enum|extends|super|export|implements|private|public|interface|package|protected|static\",\"storage.type\":\"const|let|var|function\",\"constant.language\":\"null|Infinity|NaN|undefined\",\"support.function\":\"alert\",\"constant.language.boolean\":\"true|false\"},\"identifier\"),n=\"case|do|else|finally|in|instanceof|return|throw|try|typeof|yield|void\",r=\"\\\\\\\\(?:x[0-9a-fA-F]{2}|u[0-9a-fA-F]{4}|u{[0-9a-fA-F]{1,6}}|[0-2][0-7]{0,2}|3[0-7][0-7]?|[4-7][0-7]?|.)\";this.$rules={no_regex:[i.getStartRule(\"doc-start\"),f(\"no_regex\"),{token:\"string\",regex:\"'(?=.)\",next:\"qstring\"},{token:\"string\",regex:'\"(?=.)',next:\"qqstring\"},{token:\"constant.numeric\",regex:/0(?:[xX][0-9a-fA-F]+|[bB][01]+)\\b/},{token:\"constant.numeric\",regex:/[+-]?\\d[\\d_]*(?:(?:\\.\\d*)?(?:[eE][+-]?\\d+)?)?\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\"],regex:\"(\"+o+\")(\\\\.)(prototype)(\\\\.)(\"+o+\")(\\\\s*)(=)\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s+)(\\\\w+)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(function)(\\\\s+)(\"+o+\")(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"punctuation.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"text\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"keyword\",regex:\"(?:\"+n+\")\\\\b\",next:\"start\"},{token:[\"support.constant\"],regex:/that\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function.firebug\"],regex:/(console)(\\.)(warn|info|log|error|time|trace|timeEnd|assert)\\b/},{token:t,regex:o},{token:\"punctuation.operator\",regex:/[.](?![.])/,next:\"property\"},{token:\"keyword.operator\",regex:/--|\\+\\+|\\.{3}|===|==|=|!=|!==|<+=?|>+=?|!|&&|\\|\\||\\?:|[!$%&*+\\-~\\/^]=?/,next:\"start\"},{token:\"punctuation.operator\",regex:/[?:,;.]/,next:\"start\"},{token:\"paren.lparen\",regex:/[\\[({]/,next:\"start\"},{token:\"paren.rparen\",regex:/[\\])}]/},{token:\"comment\",regex:/^#!.*$/}],property:[{token:\"text\",regex:\"\\\\s+\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(?:(\\\\s+)(\\\\w+))?(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"punctuation.operator\",regex:/[.](?![.])/},{token:\"support.function\",regex:/(s(?:h(?:ift|ow(?:Mod(?:elessDialog|alDialog)|Help))|croll(?:X|By(?:Pages|Lines)?|Y|To)?|t(?:op|rike)|i(?:n|zeToContent|debar|gnText)|ort|u(?:p|b(?:str(?:ing)?)?)|pli(?:ce|t)|e(?:nd|t(?:Re(?:sizable|questHeader)|M(?:i(?:nutes|lliseconds)|onth)|Seconds|Ho(?:tKeys|urs)|Year|Cursor|Time(?:out)?|Interval|ZOptions|Date|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Date|FullYear)|FullYear|Active)|arch)|qrt|lice|avePreferences|mall)|h(?:ome|andleEvent)|navigate|c(?:har(?:CodeAt|At)|o(?:s|n(?:cat|textual|firm)|mpile)|eil|lear(?:Timeout|Interval)?|a(?:ptureEvents|ll)|reate(?:StyleSheet|Popup|EventObject))|t(?:o(?:GMTString|S(?:tring|ource)|U(?:TCString|pperCase)|Lo(?:caleString|werCase))|est|a(?:n|int(?:Enabled)?))|i(?:s(?:NaN|Finite)|ndexOf|talics)|d(?:isableExternalCapture|ump|etachEvent)|u(?:n(?:shift|taint|escape|watch)|pdateCommands)|j(?:oin|avaEnabled)|p(?:o(?:p|w)|ush|lugins.refresh|a(?:ddings|rse(?:Int|Float)?)|r(?:int|ompt|eference))|e(?:scape|nableExternalCapture|val|lementFromPoint|x(?:p|ec(?:Script|Command)?))|valueOf|UTC|queryCommand(?:State|Indeterm|Enabled|Value)|f(?:i(?:nd|le(?:ModifiedDate|Size|CreatedDate|UpdatedDate)|xed)|o(?:nt(?:size|color)|rward)|loor|romCharCode)|watch|l(?:ink|o(?:ad|g)|astIndexOf)|a(?:sin|nchor|cos|t(?:tachEvent|ob|an(?:2)?)|pply|lert|b(?:s|ort))|r(?:ou(?:nd|teEvents)|e(?:size(?:By|To)|calc|turnValue|place|verse|l(?:oad|ease(?:Capture|Events)))|andom)|g(?:o|et(?:ResponseHeader|M(?:i(?:nutes|lliseconds)|onth)|Se(?:conds|lection)|Hours|Year|Time(?:zoneOffset)?|Da(?:y|te)|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Da(?:y|te)|FullYear)|FullYear|A(?:ttention|llResponseHeaders)))|m(?:in|ove(?:B(?:y|elow)|To(?:Absolute)?|Above)|ergeAttributes|a(?:tch|rgins|x))|b(?:toa|ig|o(?:ld|rderWidths)|link|ack))\\b(?=\\()/},{token:\"support.function.dom\",regex:/(s(?:ub(?:stringData|mit)|plitText|e(?:t(?:NamedItem|Attribute(?:Node)?)|lect))|has(?:ChildNodes|Feature)|namedItem|c(?:l(?:ick|o(?:se|neNode))|reate(?:C(?:omment|DATASection|aption)|T(?:Head|extNode|Foot)|DocumentFragment|ProcessingInstruction|E(?:ntityReference|lement)|Attribute))|tabIndex|i(?:nsert(?:Row|Before|Cell|Data)|tem)|open|delete(?:Row|C(?:ell|aption)|T(?:Head|Foot)|Data)|focus|write(?:ln)?|a(?:dd|ppend(?:Child|Data))|re(?:set|place(?:Child|Data)|move(?:NamedItem|Child|Attribute(?:Node)?)?)|get(?:NamedItem|Element(?:sBy(?:Name|TagName|ClassName)|ById)|Attribute(?:Node)?)|blur)\\b(?=\\()/},{token:\"support.constant\",regex:/(s(?:ystemLanguage|cr(?:ipts|ollbars|een(?:X|Y|Top|Left))|t(?:yle(?:Sheets)?|atus(?:Text|bar)?)|ibling(?:Below|Above)|ource|uffixes|e(?:curity(?:Policy)?|l(?:ection|f)))|h(?:istory|ost(?:name)?|as(?:h|Focus))|y|X(?:MLDocument|SLDocument)|n(?:ext|ame(?:space(?:s|URI)|Prop))|M(?:IN_VALUE|AX_VALUE)|c(?:haracterSet|o(?:n(?:structor|trollers)|okieEnabled|lorDepth|mp(?:onents|lete))|urrent|puClass|l(?:i(?:p(?:boardData)?|entInformation)|osed|asses)|alle(?:e|r)|rypto)|t(?:o(?:olbar|p)|ext(?:Transform|Indent|Decoration|Align)|ags)|SQRT(?:1_2|2)|i(?:n(?:ner(?:Height|Width)|put)|ds|gnoreCase)|zIndex|o(?:scpu|n(?:readystatechange|Line)|uter(?:Height|Width)|p(?:sProfile|ener)|ffscreenBuffering)|NEGATIVE_INFINITY|d(?:i(?:splay|alog(?:Height|Top|Width|Left|Arguments)|rectories)|e(?:scription|fault(?:Status|Ch(?:ecked|arset)|View)))|u(?:ser(?:Profile|Language|Agent)|n(?:iqueID|defined)|pdateInterval)|_content|p(?:ixelDepth|ort|ersonalbar|kcs11|l(?:ugins|atform)|a(?:thname|dding(?:Right|Bottom|Top|Left)|rent(?:Window|Layer)?|ge(?:X(?:Offset)?|Y(?:Offset)?))|r(?:o(?:to(?:col|type)|duct(?:Sub)?|mpter)|e(?:vious|fix)))|e(?:n(?:coding|abledPlugin)|x(?:ternal|pando)|mbeds)|v(?:isibility|endor(?:Sub)?|Linkcolor)|URLUnencoded|P(?:I|OSITIVE_INFINITY)|f(?:ilename|o(?:nt(?:Size|Family|Weight)|rmName)|rame(?:s|Element)|gColor)|E|whiteSpace|l(?:i(?:stStyleType|n(?:eHeight|kColor))|o(?:ca(?:tion(?:bar)?|lName)|wsrc)|e(?:ngth|ft(?:Context)?)|a(?:st(?:M(?:odified|atch)|Index|Paren)|yer(?:s|X)|nguage))|a(?:pp(?:MinorVersion|Name|Co(?:deName|re)|Version)|vail(?:Height|Top|Width|Left)|ll|r(?:ity|guments)|Linkcolor|bove)|r(?:ight(?:Context)?|e(?:sponse(?:XML|Text)|adyState))|global|x|m(?:imeTypes|ultiline|enubar|argin(?:Right|Bottom|Top|Left))|L(?:N(?:10|2)|OG(?:10E|2E))|b(?:o(?:ttom|rder(?:Width|RightWidth|BottomWidth|Style|Color|TopWidth|LeftWidth))|ufferDepth|elow|ackground(?:Color|Image)))\\b/},{token:\"identifier\",regex:o},{regex:\"\",token:\"empty\",next:\"no_regex\"}],start:[i.getStartRule(\"doc-start\"),f(\"start\"),{token:\"string.regexp\",regex:\"\\\\/\",next:\"regex\"},{token:\"text\",regex:\"\\\\s+|^$\",next:\"start\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],regex:[{token:\"regexp.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"string.regexp\",regex:\"/[sxngimy]*\",next:\"no_regex\"},{token:\"invalid\",regex:/\\{\\d+\\b,?\\d*\\}[+*]|[+*$^?][+*]|[$^][?]|\\?{3,}/},{token:\"constant.language.escape\",regex:/\\(\\?[:=!]|\\)|\\{\\d+\\b,?\\d*\\}|[+*]\\?|[()$^+*?.]/},{token:\"constant.language.delimiter\",regex:/\\|/},{token:\"constant.language.escape\",regex:/\\[\\^?/,next:\"regex_character_class\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp\"}],regex_character_class:[{token:\"regexp.charclass.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"constant.language.escape\",regex:\"]\",next:\"regex\"},{token:\"constant.language.escape\",regex:\"-\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp.charachterclass\"}],function_arguments:[{token:\"variable.parameter\",regex:o},{token:\"punctuation.operator\",regex:\"[, ]+\"},{token:\"punctuation.operator\",regex:\"$\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],qqstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qqstring\"},{token:\"string\",regex:'\"|$',next:\"no_regex\"},{defaultToken:\"string\"}],qstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qstring\"},{token:\"string\",regex:\"'|$\",next:\"no_regex\"},{defaultToken:\"string\"}]};if(!e||!e.noES6)this.$rules.no_regex.unshift({regex:\"[{}]\",onMatch:function(e,t,n){this.next=e==\"{\"?this.nextState:\"\";if(e==\"{\"&&n.length)n.unshift(\"start\",t);else if(e==\"}\"&&n.length){n.shift(),this.next=n.shift();if(this.next.indexOf(\"string\")!=-1||this.next.indexOf(\"jsx\")!=-1)return\"paren.quasi.end\"}return e==\"{\"?\"paren.lparen\":\"paren.rparen\"},nextState:\"start\"},{token:\"string.quasi.start\",regex:/`/,push:[{token:\"constant.language.escape\",regex:r},{token:\"paren.quasi.start\",regex:/\\${/,push:\"start\"},{token:\"string.quasi.end\",regex:/`/,next:\"pop\"},{defaultToken:\"string.quasi\"}]}),(!e||e.jsx!=0)&&a.call(this);this.embedRules(i,\"doc-\",[i.getEndRule(\"no_regex\")]),this.normalizeRules()};r.inherits(u,s),t.JavaScriptHighlightRules=u}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/javascript\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./behaviour/cstyle\").CstyleBehaviour,f=e(\"./folding/cstyle\").FoldMode,l=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new a,this.foldingRules=new f};r.inherits(l,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens,o=i.state;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"||e==\"no_regex\"){var u=t.match(/^.*(?:\\bcase\\b.*:|[\\{\\(\\[])\\s*$/);u&&(r+=n)}else if(e==\"doc-start\"){if(o==\"start\"||o==\"no_regex\")return\"\";var u=t.match(/^\\s*(\\/?)\\*/);u&&(u[1]&&(r+=\" \"),r+=\"* \")}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/javascript_worker\",\"JavaScriptWorker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/javascript\"}.call(l.prototype),t.Mode=l}),define(\"ace/mode/java_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=function(){var e=\"abstract|continue|for|new|switch|assert|default|goto|package|synchronized|boolean|do|if|private|this|break|double|implements|protected|throw|byte|else|import|public|throws|case|enum|instanceof|return|transient|catch|extends|int|short|try|char|final|interface|static|void|class|finally|long|strictfp|volatile|const|float|native|super|while\",t=\"null|Infinity|NaN|undefined\",n=\"AbstractMethodError|AssertionError|ClassCircularityError|ClassFormatError|Deprecated|EnumConstantNotPresentException|ExceptionInInitializerError|IllegalAccessError|IllegalThreadStateException|InstantiationError|InternalError|NegativeArraySizeException|NoSuchFieldError|Override|Process|ProcessBuilder|SecurityManager|StringIndexOutOfBoundsException|SuppressWarnings|TypeNotPresentException|UnknownError|UnsatisfiedLinkError|UnsupportedClassVersionError|VerifyError|InstantiationException|IndexOutOfBoundsException|ArrayIndexOutOfBoundsException|CloneNotSupportedException|NoSuchFieldException|IllegalArgumentException|NumberFormatException|SecurityException|Void|InheritableThreadLocal|IllegalStateException|InterruptedException|NoSuchMethodException|IllegalAccessException|UnsupportedOperationException|Enum|StrictMath|Package|Compiler|Readable|Runtime|StringBuilder|Math|IncompatibleClassChangeError|NoSuchMethodError|ThreadLocal|RuntimePermission|ArithmeticException|NullPointerException|Long|Integer|Short|Byte|Double|Number|Float|Character|Boolean|StackTraceElement|Appendable|StringBuffer|Iterable|ThreadGroup|Runnable|Thread|IllegalMonitorStateException|StackOverflowError|OutOfMemoryError|VirtualMachineError|ArrayStoreException|ClassCastException|LinkageError|NoClassDefFoundError|ClassNotFoundException|RuntimeException|Exception|ThreadDeath|Error|Throwable|System|ClassLoader|Cloneable|Class|CharSequence|Comparable|String|Object\",r=this.createKeywordMapper({\"variable.language\":\"this\",keyword:e,\"constant.language\":t,\"support.function\":n},\"identifier\");this.$rules={start:[{token:\"comment\",regex:\"\\\\/\\\\/.*$\"},i.getStartRule(\"doc-start\"),{token:\"comment\",regex:\"\\\\/\\\\*\",next:\"comment\"},{token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},{token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},{token:\"constant.numeric\",regex:/0(?:[xX][0-9a-fA-F][0-9a-fA-F_]*|[bB][01][01_]*)[LlSsDdFfYy]?\\b/},{token:\"constant.numeric\",regex:/[+-]?\\d[\\d_]*(?:(?:\\.[\\d_]*)?(?:[eE][+-]?[\\d_]+)?)?[LlSsDdFfYy]?\\b/},{token:\"constant.language.boolean\",regex:\"(?:true|false)\\\\b\"},{token:r,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"keyword.operator\",regex:\"!|\\\\$|%|&|\\\\*|\\\\-\\\\-|\\\\-|\\\\+\\\\+|\\\\+|~|===|==|=|!=|!==|<=|>=|<<=|>>=|>>>=|<>|<|>|!|&&|\\\\|\\\\||\\\\?\\\\:|\\\\*=|%=|\\\\+=|\\\\-=|&=|\\\\^=|\\\\b(?:in|instanceof|new|delete|typeof|void)\"},{token:\"lparen\",regex:\"[[({]\"},{token:\"rparen\",regex:\"[\\\\])}]\"},{token:\"text\",regex:\"\\\\s+\"}],comment:[{token:\"comment\",regex:\".*?\\\\*\\\\/\",next:\"start\"},{token:\"comment\",regex:\".+\"}]},this.embedRules(i,\"doc-\",[i.getEndRule(\"start\")])};r.inherits(o,s),t.JavaHighlightRules=o}),define(\"ace/mode/java\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/javascript\",\"ace/mode/java_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./javascript\").Mode,s=e(\"./java_highlight_rules\").JavaHighlightRules,o=function(){i.call(this),this.HighlightRules=s};r.inherits(o,i),function(){this.createWorker=function(e){return null},this.$id=\"ace/mode/java\"}.call(o.prototype),t.Mode=o})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-javascript.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/javascript_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";function a(){var e=o.replace(\"\\\\d\",\"\\\\d\\\\-\"),t={onMatch:function(e,t,n){var r=e.charAt(1)==\"/\"?2:1;if(r==1)t!=this.nextState?n.unshift(this.next,this.nextState,0):n.unshift(this.next),n[2]++;else if(r==2&&t==this.nextState){n[1]--;if(!n[1]||n[1]<0)n.shift(),n.shift()}return[{type:\"meta.tag.punctuation.\"+(r==1?\"\":\"end-\")+\"tag-open.xml\",value:e.slice(0,r)},{type:\"meta.tag.tag-name.xml\",value:e.substr(r)}]},regex:\"</?\"+e+\"\",next:\"jsxAttributes\",nextState:\"jsx\"};this.$rules.start.unshift(t);var n={regex:\"{\",token:\"paren.quasi.start\",push:\"start\"};this.$rules.jsx=[n,t,{include:\"reference\"},{defaultToken:\"string\"}],this.$rules.jsxAttributes=[{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",onMatch:function(e,t,n){return t==n[0]&&n.shift(),e.length==2&&(n[0]==this.nextState&&n[1]--,(!n[1]||n[1]<0)&&n.splice(0,2)),this.next=n[0]||\"start\",[{type:this.token,value:e}]},nextState:\"jsx\"},n,f(\"jsxAttributes\"),{token:\"entity.other.attribute-name.xml\",regex:e},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"},{token:\"string.attribute-value.xml\",regex:\"'\",stateName:\"jsx_attr_q\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',stateName:\"jsx_attr_qq\",push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},t],this.$rules.reference=[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}]}function f(e){return[{token:\"comment\",regex:/\\/\\*/,next:[i.getTagRule(),{token:\"comment\",regex:\"\\\\*\\\\/\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]},{token:\"comment\",regex:\"\\\\/\\\\/\",next:[i.getTagRule(),{token:\"comment\",regex:\"$|^\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]}]}var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=\"[a-zA-Z\\\\$_\\u00a1-\\uffff][a-zA-Z\\\\d\\\\$_\\u00a1-\\uffff]*\",u=function(e){var t=this.createKeywordMapper({\"variable.language\":\"Array|Boolean|Date|Function|Iterator|Number|Object|RegExp|String|Proxy|Namespace|QName|XML|XMLList|ArrayBuffer|Float32Array|Float64Array|Int16Array|Int32Array|Int8Array|Uint16Array|Uint32Array|Uint8Array|Uint8ClampedArray|Error|EvalError|InternalError|RangeError|ReferenceError|StopIteration|SyntaxError|TypeError|URIError|decodeURI|decodeURIComponent|encodeURI|encodeURIComponent|eval|isFinite|isNaN|parseFloat|parseInt|JSON|Math|this|arguments|prototype|window|document\",keyword:\"const|yield|import|get|set|async|await|break|case|catch|continue|default|delete|do|else|finally|for|function|if|in|of|instanceof|new|return|switch|throw|try|typeof|let|var|while|with|debugger|__parent__|__count__|escape|unescape|with|__proto__|class|enum|extends|super|export|implements|private|public|interface|package|protected|static\",\"storage.type\":\"const|let|var|function\",\"constant.language\":\"null|Infinity|NaN|undefined\",\"support.function\":\"alert\",\"constant.language.boolean\":\"true|false\"},\"identifier\"),n=\"case|do|else|finally|in|instanceof|return|throw|try|typeof|yield|void\",r=\"\\\\\\\\(?:x[0-9a-fA-F]{2}|u[0-9a-fA-F]{4}|u{[0-9a-fA-F]{1,6}}|[0-2][0-7]{0,2}|3[0-7][0-7]?|[4-7][0-7]?|.)\";this.$rules={no_regex:[i.getStartRule(\"doc-start\"),f(\"no_regex\"),{token:\"string\",regex:\"'(?=.)\",next:\"qstring\"},{token:\"string\",regex:'\"(?=.)',next:\"qqstring\"},{token:\"constant.numeric\",regex:/0(?:[xX][0-9a-fA-F]+|[bB][01]+)\\b/},{token:\"constant.numeric\",regex:/[+-]?\\d[\\d_]*(?:(?:\\.\\d*)?(?:[eE][+-]?\\d+)?)?\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\"],regex:\"(\"+o+\")(\\\\.)(prototype)(\\\\.)(\"+o+\")(\\\\s*)(=)\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s+)(\\\\w+)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(function)(\\\\s+)(\"+o+\")(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"punctuation.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"text\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"keyword\",regex:\"(?:\"+n+\")\\\\b\",next:\"start\"},{token:[\"support.constant\"],regex:/that\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function.firebug\"],regex:/(console)(\\.)(warn|info|log|error|time|trace|timeEnd|assert)\\b/},{token:t,regex:o},{token:\"punctuation.operator\",regex:/[.](?![.])/,next:\"property\"},{token:\"keyword.operator\",regex:/--|\\+\\+|\\.{3}|===|==|=|!=|!==|<+=?|>+=?|!|&&|\\|\\||\\?:|[!$%&*+\\-~\\/^]=?/,next:\"start\"},{token:\"punctuation.operator\",regex:/[?:,;.]/,next:\"start\"},{token:\"paren.lparen\",regex:/[\\[({]/,next:\"start\"},{token:\"paren.rparen\",regex:/[\\])}]/},{token:\"comment\",regex:/^#!.*$/}],property:[{token:\"text\",regex:\"\\\\s+\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(?:(\\\\s+)(\\\\w+))?(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"punctuation.operator\",regex:/[.](?![.])/},{token:\"support.function\",regex:/(s(?:h(?:ift|ow(?:Mod(?:elessDialog|alDialog)|Help))|croll(?:X|By(?:Pages|Lines)?|Y|To)?|t(?:op|rike)|i(?:n|zeToContent|debar|gnText)|ort|u(?:p|b(?:str(?:ing)?)?)|pli(?:ce|t)|e(?:nd|t(?:Re(?:sizable|questHeader)|M(?:i(?:nutes|lliseconds)|onth)|Seconds|Ho(?:tKeys|urs)|Year|Cursor|Time(?:out)?|Interval|ZOptions|Date|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Date|FullYear)|FullYear|Active)|arch)|qrt|lice|avePreferences|mall)|h(?:ome|andleEvent)|navigate|c(?:har(?:CodeAt|At)|o(?:s|n(?:cat|textual|firm)|mpile)|eil|lear(?:Timeout|Interval)?|a(?:ptureEvents|ll)|reate(?:StyleSheet|Popup|EventObject))|t(?:o(?:GMTString|S(?:tring|ource)|U(?:TCString|pperCase)|Lo(?:caleString|werCase))|est|a(?:n|int(?:Enabled)?))|i(?:s(?:NaN|Finite)|ndexOf|talics)|d(?:isableExternalCapture|ump|etachEvent)|u(?:n(?:shift|taint|escape|watch)|pdateCommands)|j(?:oin|avaEnabled)|p(?:o(?:p|w)|ush|lugins.refresh|a(?:ddings|rse(?:Int|Float)?)|r(?:int|ompt|eference))|e(?:scape|nableExternalCapture|val|lementFromPoint|x(?:p|ec(?:Script|Command)?))|valueOf|UTC|queryCommand(?:State|Indeterm|Enabled|Value)|f(?:i(?:nd|le(?:ModifiedDate|Size|CreatedDate|UpdatedDate)|xed)|o(?:nt(?:size|color)|rward)|loor|romCharCode)|watch|l(?:ink|o(?:ad|g)|astIndexOf)|a(?:sin|nchor|cos|t(?:tachEvent|ob|an(?:2)?)|pply|lert|b(?:s|ort))|r(?:ou(?:nd|teEvents)|e(?:size(?:By|To)|calc|turnValue|place|verse|l(?:oad|ease(?:Capture|Events)))|andom)|g(?:o|et(?:ResponseHeader|M(?:i(?:nutes|lliseconds)|onth)|Se(?:conds|lection)|Hours|Year|Time(?:zoneOffset)?|Da(?:y|te)|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Da(?:y|te)|FullYear)|FullYear|A(?:ttention|llResponseHeaders)))|m(?:in|ove(?:B(?:y|elow)|To(?:Absolute)?|Above)|ergeAttributes|a(?:tch|rgins|x))|b(?:toa|ig|o(?:ld|rderWidths)|link|ack))\\b(?=\\()/},{token:\"support.function.dom\",regex:/(s(?:ub(?:stringData|mit)|plitText|e(?:t(?:NamedItem|Attribute(?:Node)?)|lect))|has(?:ChildNodes|Feature)|namedItem|c(?:l(?:ick|o(?:se|neNode))|reate(?:C(?:omment|DATASection|aption)|T(?:Head|extNode|Foot)|DocumentFragment|ProcessingInstruction|E(?:ntityReference|lement)|Attribute))|tabIndex|i(?:nsert(?:Row|Before|Cell|Data)|tem)|open|delete(?:Row|C(?:ell|aption)|T(?:Head|Foot)|Data)|focus|write(?:ln)?|a(?:dd|ppend(?:Child|Data))|re(?:set|place(?:Child|Data)|move(?:NamedItem|Child|Attribute(?:Node)?)?)|get(?:NamedItem|Element(?:sBy(?:Name|TagName|ClassName)|ById)|Attribute(?:Node)?)|blur)\\b(?=\\()/},{token:\"support.constant\",regex:/(s(?:ystemLanguage|cr(?:ipts|ollbars|een(?:X|Y|Top|Left))|t(?:yle(?:Sheets)?|atus(?:Text|bar)?)|ibling(?:Below|Above)|ource|uffixes|e(?:curity(?:Policy)?|l(?:ection|f)))|h(?:istory|ost(?:name)?|as(?:h|Focus))|y|X(?:MLDocument|SLDocument)|n(?:ext|ame(?:space(?:s|URI)|Prop))|M(?:IN_VALUE|AX_VALUE)|c(?:haracterSet|o(?:n(?:structor|trollers)|okieEnabled|lorDepth|mp(?:onents|lete))|urrent|puClass|l(?:i(?:p(?:boardData)?|entInformation)|osed|asses)|alle(?:e|r)|rypto)|t(?:o(?:olbar|p)|ext(?:Transform|Indent|Decoration|Align)|ags)|SQRT(?:1_2|2)|i(?:n(?:ner(?:Height|Width)|put)|ds|gnoreCase)|zIndex|o(?:scpu|n(?:readystatechange|Line)|uter(?:Height|Width)|p(?:sProfile|ener)|ffscreenBuffering)|NEGATIVE_INFINITY|d(?:i(?:splay|alog(?:Height|Top|Width|Left|Arguments)|rectories)|e(?:scription|fault(?:Status|Ch(?:ecked|arset)|View)))|u(?:ser(?:Profile|Language|Agent)|n(?:iqueID|defined)|pdateInterval)|_content|p(?:ixelDepth|ort|ersonalbar|kcs11|l(?:ugins|atform)|a(?:thname|dding(?:Right|Bottom|Top|Left)|rent(?:Window|Layer)?|ge(?:X(?:Offset)?|Y(?:Offset)?))|r(?:o(?:to(?:col|type)|duct(?:Sub)?|mpter)|e(?:vious|fix)))|e(?:n(?:coding|abledPlugin)|x(?:ternal|pando)|mbeds)|v(?:isibility|endor(?:Sub)?|Linkcolor)|URLUnencoded|P(?:I|OSITIVE_INFINITY)|f(?:ilename|o(?:nt(?:Size|Family|Weight)|rmName)|rame(?:s|Element)|gColor)|E|whiteSpace|l(?:i(?:stStyleType|n(?:eHeight|kColor))|o(?:ca(?:tion(?:bar)?|lName)|wsrc)|e(?:ngth|ft(?:Context)?)|a(?:st(?:M(?:odified|atch)|Index|Paren)|yer(?:s|X)|nguage))|a(?:pp(?:MinorVersion|Name|Co(?:deName|re)|Version)|vail(?:Height|Top|Width|Left)|ll|r(?:ity|guments)|Linkcolor|bove)|r(?:ight(?:Context)?|e(?:sponse(?:XML|Text)|adyState))|global|x|m(?:imeTypes|ultiline|enubar|argin(?:Right|Bottom|Top|Left))|L(?:N(?:10|2)|OG(?:10E|2E))|b(?:o(?:ttom|rder(?:Width|RightWidth|BottomWidth|Style|Color|TopWidth|LeftWidth))|ufferDepth|elow|ackground(?:Color|Image)))\\b/},{token:\"identifier\",regex:o},{regex:\"\",token:\"empty\",next:\"no_regex\"}],start:[i.getStartRule(\"doc-start\"),f(\"start\"),{token:\"string.regexp\",regex:\"\\\\/\",next:\"regex\"},{token:\"text\",regex:\"\\\\s+|^$\",next:\"start\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],regex:[{token:\"regexp.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"string.regexp\",regex:\"/[sxngimy]*\",next:\"no_regex\"},{token:\"invalid\",regex:/\\{\\d+\\b,?\\d*\\}[+*]|[+*$^?][+*]|[$^][?]|\\?{3,}/},{token:\"constant.language.escape\",regex:/\\(\\?[:=!]|\\)|\\{\\d+\\b,?\\d*\\}|[+*]\\?|[()$^+*?.]/},{token:\"constant.language.delimiter\",regex:/\\|/},{token:\"constant.language.escape\",regex:/\\[\\^?/,next:\"regex_character_class\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp\"}],regex_character_class:[{token:\"regexp.charclass.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"constant.language.escape\",regex:\"]\",next:\"regex\"},{token:\"constant.language.escape\",regex:\"-\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp.charachterclass\"}],function_arguments:[{token:\"variable.parameter\",regex:o},{token:\"punctuation.operator\",regex:\"[, ]+\"},{token:\"punctuation.operator\",regex:\"$\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],qqstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qqstring\"},{token:\"string\",regex:'\"|$',next:\"no_regex\"},{defaultToken:\"string\"}],qstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qstring\"},{token:\"string\",regex:\"'|$\",next:\"no_regex\"},{defaultToken:\"string\"}]};if(!e||!e.noES6)this.$rules.no_regex.unshift({regex:\"[{}]\",onMatch:function(e,t,n){this.next=e==\"{\"?this.nextState:\"\";if(e==\"{\"&&n.length)n.unshift(\"start\",t);else if(e==\"}\"&&n.length){n.shift(),this.next=n.shift();if(this.next.indexOf(\"string\")!=-1||this.next.indexOf(\"jsx\")!=-1)return\"paren.quasi.end\"}return e==\"{\"?\"paren.lparen\":\"paren.rparen\"},nextState:\"start\"},{token:\"string.quasi.start\",regex:/`/,push:[{token:\"constant.language.escape\",regex:r},{token:\"paren.quasi.start\",regex:/\\${/,push:\"start\"},{token:\"string.quasi.end\",regex:/`/,next:\"pop\"},{defaultToken:\"string.quasi\"}]}),(!e||e.jsx!=0)&&a.call(this);this.embedRules(i,\"doc-\",[i.getEndRule(\"no_regex\")]),this.normalizeRules()};r.inherits(u,s),t.JavaScriptHighlightRules=u}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/javascript\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./behaviour/cstyle\").CstyleBehaviour,f=e(\"./folding/cstyle\").FoldMode,l=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new a,this.foldingRules=new f};r.inherits(l,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens,o=i.state;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"||e==\"no_regex\"){var u=t.match(/^.*(?:\\bcase\\b.*:|[\\{\\(\\[])\\s*$/);u&&(r+=n)}else if(e==\"doc-start\"){if(o==\"start\"||o==\"no_regex\")return\"\";var u=t.match(/^\\s*(\\/?)\\*/);u&&(u[1]&&(r+=\" \"),r+=\"* \")}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/javascript_worker\",\"JavaScriptWorker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/javascript\"}.call(l.prototype),t.Mode=l})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-json.js",
    "content": "define(\"ace/mode/json_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"variable\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]\\\\s*(?=:)'},{token:\"string\",regex:'\"',next:\"string\"},{token:\"constant.numeric\",regex:\"0[xX][0-9a-fA-F]+\\\\b\"},{token:\"constant.numeric\",regex:\"[+-]?\\\\d+(?:(?:\\\\.\\\\d*)?(?:[eE][+-]?\\\\d+)?)?\\\\b\"},{token:\"constant.language.boolean\",regex:\"(?:true|false)\\\\b\"},{token:\"invalid.illegal\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},{token:\"invalid.illegal\",regex:\"\\\\/\\\\/.*$\"},{token:\"paren.lparen\",regex:\"[[({]\"},{token:\"paren.rparen\",regex:\"[\\\\])}]\"},{token:\"text\",regex:\"\\\\s+\"}],string:[{token:\"constant.language.escape\",regex:/\\\\(?:x[0-9a-fA-F]{2}|u[0-9a-fA-F]{4}|[\"\\\\\\/bfnrt])/},{token:\"string\",regex:'[^\"\\\\\\\\]+'},{token:\"string\",regex:'\"',next:\"start\"},{token:\"string\",regex:\"\",next:\"start\"}]}};r.inherits(s,i),t.JsonHighlightRules=s}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/json\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/json_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/cstyle\",\"ace/worker/worker_client\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./json_highlight_rules\").JsonHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"./behaviour/cstyle\").CstyleBehaviour,a=e(\"./folding/cstyle\").FoldMode,f=e(\"../worker/worker_client\").WorkerClient,l=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new u,this.foldingRules=new a};r.inherits(l,i),function(){this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t);if(e==\"start\"){var i=t.match(/^.*[\\{\\(\\[]\\s*$/);i&&(r+=n)}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.createWorker=function(e){var t=new f([\"ace\"],\"ace/mode/json_worker\",\"JsonWorker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/json\"}.call(l.prototype),t.Mode=l})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-kotlin.js",
    "content": "define(\"ace/mode/kotlin_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{include:\"#comments\"},{token:[\"text\",\"keyword.other.kotlin\",\"text\",\"entity.name.package.kotlin\",\"text\"],regex:/^(\\s*)(package)\\b(?:(\\s*)([^ ;$]+)(\\s*))?/},{include:\"#imports\"},{include:\"#statements\"}],\"#classes\":[{token:\"text\",regex:/(?=\\s*(?:companion|class|object|interface))/,push:[{token:\"text\",regex:/}|(?=$)/,next:\"pop\"},{token:[\"keyword.other.kotlin\",\"text\"],regex:/\\b((?:companion\\s*)?)(class|object|interface)\\b/,push:[{token:\"text\",regex:/(?=<|{|\\(|:)/,next:\"pop\"},{token:\"keyword.other.kotlin\",regex:/\\bobject\\b/},{token:\"entity.name.type.class.kotlin\",regex:/\\w+/}]},{token:\"text\",regex:/</,push:[{token:\"text\",regex:/>/,next:\"pop\"},{include:\"#generics\"}]},{token:\"text\",regex:/\\(/,push:[{token:\"text\",regex:/\\)/,next:\"pop\"},{include:\"#parameters\"}]},{token:\"keyword.operator.declaration.kotlin\",regex:/:/,push:[{token:\"text\",regex:/(?={|$)/,next:\"pop\"},{token:\"entity.other.inherited-class.kotlin\",regex:/\\w+/},{token:\"text\",regex:/\\(/,push:[{token:\"text\",regex:/\\)/,next:\"pop\"},{include:\"#expressions\"}]}]},{token:\"text\",regex:/\\{/,push:[{token:\"text\",regex:/\\}/,next:\"pop\"},{include:\"#statements\"}]}]}],\"#comments\":[{token:\"punctuation.definition.comment.kotlin\",regex:/\\/\\*/,push:[{token:\"punctuation.definition.comment.kotlin\",regex:/\\*\\//,next:\"pop\"},{defaultToken:\"comment.block.kotlin\"}]},{token:[\"text\",\"punctuation.definition.comment.kotlin\",\"comment.line.double-slash.kotlin\"],regex:/(\\s*)(\\/\\/)(.*$)/}],\"#constants\":[{token:\"constant.language.kotlin\",regex:/\\b(?:true|false|null|this|super)\\b/},{token:\"constant.numeric.kotlin\",regex:/\\b(?:0(?:x|X)[0-9a-fA-F]*|(?:[0-9]+\\.?[0-9]*|\\.[0-9]+)(?:(?:e|E)(?:\\+|-)?[0-9]+)?)(?:[LlFfUuDd]|UL|ul)?\\b/},{token:\"constant.other.kotlin\",regex:/\\b[A-Z][A-Z0-9_]+\\b/}],\"#expressions\":[{token:\"text\",regex:/\\(/,push:[{token:\"text\",regex:/\\)/,next:\"pop\"},{include:\"#expressions\"}]},{include:\"#types\"},{include:\"#strings\"},{include:\"#constants\"},{include:\"#comments\"},{include:\"#keywords\"}],\"#functions\":[{token:\"text\",regex:/(?=\\s*fun)/,push:[{token:\"text\",regex:/}|(?=$)/,next:\"pop\"},{token:\"keyword.other.kotlin\",regex:/\\bfun\\b/,push:[{token:\"text\",regex:/(?=\\()/,next:\"pop\"},{token:\"text\",regex:/</,push:[{token:\"text\",regex:/>/,next:\"pop\"},{include:\"#generics\"}]},{token:[\"text\",\"entity.name.function.kotlin\"],regex:/((?:[\\.<\\?>\\w]+\\.)?)(\\w+)/}]},{token:\"text\",regex:/\\(/,push:[{token:\"text\",regex:/\\)/,next:\"pop\"},{include:\"#parameters\"}]},{token:\"keyword.operator.declaration.kotlin\",regex:/:/,push:[{token:\"text\",regex:/(?={|=|$)/,next:\"pop\"},{include:\"#types\"}]},{token:\"text\",regex:/\\{/,push:[{token:\"text\",regex:/(?=\\})/,next:\"pop\"},{include:\"#statements\"}]},{token:\"keyword.operator.assignment.kotlin\",regex:/=/,push:[{token:\"text\",regex:/(?=$)/,next:\"pop\"},{include:\"#expressions\"}]}]}],\"#generics\":[{token:\"keyword.operator.declaration.kotlin\",regex:/:/,push:[{token:\"text\",regex:/(?=,|>)/,next:\"pop\"},{include:\"#types\"}]},{include:\"#keywords\"},{token:\"storage.type.generic.kotlin\",regex:/\\w+/}],\"#getters-and-setters\":[{token:[\"entity.name.function.kotlin\",\"text\"],regex:/\\b(get)\\b(\\s*\\(\\s*\\))/,push:[{token:\"text\",regex:/\\}|(?=\\bset\\b)|$/,next:\"pop\"},{token:\"keyword.operator.assignment.kotlin\",regex:/=/,push:[{token:\"text\",regex:/(?=$|\\bset\\b)/,next:\"pop\"},{include:\"#expressions\"}]},{token:\"text\",regex:/\\{/,push:[{token:\"text\",regex:/\\}/,next:\"pop\"},{include:\"#expressions\"}]}]},{token:[\"entity.name.function.kotlin\",\"text\"],regex:/\\b(set)\\b(\\s*)(?=\\()/,push:[{token:\"text\",regex:/\\}|(?=\\bget\\b)|$/,next:\"pop\"},{token:\"text\",regex:/\\(/,push:[{token:\"text\",regex:/\\)/,next:\"pop\"},{include:\"#parameters\"}]},{token:\"keyword.operator.assignment.kotlin\",regex:/=/,push:[{token:\"text\",regex:/(?=$|\\bset\\b)/,next:\"pop\"},{include:\"#expressions\"}]},{token:\"text\",regex:/\\{/,push:[{token:\"text\",regex:/\\}/,next:\"pop\"},{include:\"#expressions\"}]}]}],\"#imports\":[{token:[\"text\",\"keyword.other.kotlin\",\"text\",\"keyword.other.kotlin\"],regex:/^(\\s*)(import)(\\s+[^ $]+\\s+)((?:as)?)/}],\"#keywords\":[{token:\"storage.modifier.kotlin\",regex:/\\b(?:var|val|public|private|protected|abstract|final|enum|open|attribute|annotation|override|inline|var|val|vararg|lazy|in|out|internal|data|tailrec|operator|infix|const|yield|typealias|typeof)\\b/},{token:\"keyword.control.catch-exception.kotlin\",regex:/\\b(?:try|catch|finally|throw)\\b/},{token:\"keyword.control.kotlin\",regex:/\\b(?:if|else|while|for|do|return|when|where|break|continue)\\b/},{token:\"keyword.operator.kotlin\",regex:/\\b(?:in|is|as|assert)\\b/},{token:\"keyword.operator.comparison.kotlin\",regex:/==|!=|===|!==|<=|>=|<|>/},{token:\"keyword.operator.assignment.kotlin\",regex:/=/},{token:\"keyword.operator.declaration.kotlin\",regex:/:/},{token:\"keyword.operator.dot.kotlin\",regex:/\\./},{token:\"keyword.operator.increment-decrement.kotlin\",regex:/\\-\\-|\\+\\+/},{token:\"keyword.operator.arithmetic.kotlin\",regex:/\\-|\\+|\\*|\\/|%/},{token:\"keyword.operator.arithmetic.assign.kotlin\",regex:/\\+=|\\-=|\\*=|\\/=/},{token:\"keyword.operator.logical.kotlin\",regex:/!|&&|\\|\\|/},{token:\"keyword.operator.range.kotlin\",regex:/\\.\\./},{token:\"punctuation.terminator.kotlin\",regex:/;/}],\"#namespaces\":[{token:\"keyword.other.kotlin\",regex:/\\bnamespace\\b/},{token:\"text\",regex:/\\{/,push:[{token:\"text\",regex:/\\}/,next:\"pop\"},{include:\"#statements\"}]}],\"#parameters\":[{token:\"keyword.operator.declaration.kotlin\",regex:/:/,push:[{token:\"text\",regex:/(?=,|\\)|=)/,next:\"pop\"},{include:\"#types\"}]},{token:\"keyword.operator.declaration.kotlin\",regex:/=/,push:[{token:\"text\",regex:/(?=,|\\))/,next:\"pop\"},{include:\"#expressions\"}]},{include:\"#keywords\"},{token:\"variable.parameter.function.kotlin\",regex:/\\w+/}],\"#statements\":[{include:\"#namespaces\"},{include:\"#typedefs\"},{include:\"#classes\"},{include:\"#functions\"},{include:\"#variables\"},{include:\"#getters-and-setters\"},{include:\"#expressions\"}],\"#strings\":[{token:\"punctuation.definition.string.begin.kotlin\",regex:/\"\"\"/,push:[{token:\"punctuation.definition.string.end.kotlin\",regex:/\"\"\"/,next:\"pop\"},{token:\"variable.parameter.template.kotlin\",regex:/\\$\\w+|\\$\\{[^\\}]+\\}/},{token:\"constant.character.escape.kotlin\",regex:/\\\\./},{defaultToken:\"string.quoted.third.kotlin\"}]},{token:\"punctuation.definition.string.begin.kotlin\",regex:/\"/,push:[{token:\"punctuation.definition.string.end.kotlin\",regex:/\"/,next:\"pop\"},{token:\"variable.parameter.template.kotlin\",regex:/\\$\\w+|\\$\\{[^\\}]+\\}/},{token:\"constant.character.escape.kotlin\",regex:/\\\\./},{defaultToken:\"string.quoted.double.kotlin\"}]},{token:\"punctuation.definition.string.begin.kotlin\",regex:/'/,push:[{token:\"punctuation.definition.string.end.kotlin\",regex:/'/,next:\"pop\"},{token:\"constant.character.escape.kotlin\",regex:/\\\\./},{defaultToken:\"string.quoted.single.kotlin\"}]},{token:\"punctuation.definition.string.begin.kotlin\",regex:/`/,push:[{token:\"punctuation.definition.string.end.kotlin\",regex:/`/,next:\"pop\"},{defaultToken:\"string.quoted.single.kotlin\"}]}],\"#typedefs\":[{token:\"text\",regex:/(?=\\s*type)/,push:[{token:\"text\",regex:/(?=$)/,next:\"pop\"},{token:\"keyword.other.kotlin\",regex:/\\btype\\b/},{token:\"text\",regex:/</,push:[{token:\"text\",regex:/>/,next:\"pop\"},{include:\"#generics\"}]},{include:\"#expressions\"}]}],\"#types\":[{token:\"storage.type.buildin.kotlin\",regex:/\\b(?:Any|Unit|String|Int|Boolean|Char|Long|Double|Float|Short|Byte|dynamic)\\b/},{token:\"storage.type.buildin.array.kotlin\",regex:/\\b(?:IntArray|BooleanArray|CharArray|LongArray|DoubleArray|FloatArray|ShortArray|ByteArray)\\b/},{token:[\"storage.type.buildin.collection.kotlin\",\"text\"],regex:/\\b(Array|List|Map)(<\\b)/,push:[{token:\"text\",regex:/>/,next:\"pop\"},{include:\"#types\"},{include:\"#keywords\"}]},{token:\"text\",regex:/\\w+</,push:[{token:\"text\",regex:/>/,next:\"pop\"},{include:\"#types\"},{include:\"#keywords\"}]},{token:[\"keyword.operator.tuple.kotlin\",\"text\"],regex:/(#)(\\()/,push:[{token:\"text\",regex:/\\)/,next:\"pop\"},{include:\"#expressions\"}]},{token:\"text\",regex:/\\{/,push:[{token:\"text\",regex:/\\}/,next:\"pop\"},{include:\"#statements\"}]},{token:\"text\",regex:/\\(/,push:[{token:\"text\",regex:/\\)/,next:\"pop\"},{include:\"#types\"}]},{token:\"keyword.operator.declaration.kotlin\",regex:/->/}],\"#variables\":[{token:\"text\",regex:/(?=\\s*(?:var|val))/,push:[{token:\"text\",regex:/(?=:|=|$)/,next:\"pop\"},{token:\"keyword.other.kotlin\",regex:/\\b(?:var|val)\\b/,push:[{token:\"text\",regex:/(?=:|=|$)/,next:\"pop\"},{token:\"text\",regex:/</,push:[{token:\"text\",regex:/>/,next:\"pop\"},{include:\"#generics\"}]},{token:[\"text\",\"entity.name.variable.kotlin\"],regex:/((?:[\\.<\\?>\\w]+\\.)?)(\\w+)/}]},{token:\"keyword.operator.declaration.kotlin\",regex:/:/,push:[{token:\"text\",regex:/(?==|$)/,next:\"pop\"},{include:\"#types\"},{include:\"#getters-and-setters\"}]},{token:\"keyword.operator.assignment.kotlin\",regex:/=/,push:[{token:\"text\",regex:/(?=$)/,next:\"pop\"},{include:\"#expressions\"},{include:\"#getters-and-setters\"}]}]}]},this.normalizeRules()};s.metaData={fileTypes:[\"kt\",\"kts\"],name:\"Kotlin\",scopeName:\"source.Kotlin\"},r.inherits(s,i),t.KotlinHighlightRules=s}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/kotlin\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/kotlin_highlight_rules\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./kotlin_highlight_rules\").KotlinHighlightRules,o=e(\"./folding/cstyle\").FoldMode,u=function(){this.HighlightRules=s,this.foldingRules=new o};r.inherits(u,i),function(){this.$id=\"ace/mode/kotlin\"}.call(u.prototype),t.Mode=u})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-lua.js",
    "content": "define(\"ace/mode/lua_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){var e=\"break|do|else|elseif|end|for|function|if|in|local|repeat|return|then|until|while|or|and|not\",t=\"true|false|nil|_G|_VERSION\",n=\"string|xpcall|package|tostring|print|os|unpack|require|getfenv|setmetatable|next|assert|tonumber|io|rawequal|collectgarbage|getmetatable|module|rawset|math|debug|pcall|table|newproxy|type|coroutine|_G|select|gcinfo|pairs|rawget|loadstring|ipairs|_VERSION|dofile|setfenv|load|error|loadfile|sub|upper|len|gfind|rep|find|match|char|dump|gmatch|reverse|byte|format|gsub|lower|preload|loadlib|loaded|loaders|cpath|config|path|seeall|exit|setlocale|date|getenv|difftime|remove|time|clock|tmpname|rename|execute|lines|write|close|flush|open|output|type|read|stderr|stdin|input|stdout|popen|tmpfile|log|max|acos|huge|ldexp|pi|cos|tanh|pow|deg|tan|cosh|sinh|random|randomseed|frexp|ceil|floor|rad|abs|sqrt|modf|asin|min|mod|fmod|log10|atan2|exp|sin|atan|getupvalue|debug|sethook|getmetatable|gethook|setmetatable|setlocal|traceback|setfenv|getinfo|setupvalue|getlocal|getregistry|getfenv|setn|insert|getn|foreachi|maxn|foreach|concat|sort|remove|resume|yield|status|wrap|create|running|__add|__sub|__mod|__unm|__concat|__lt|__index|__call|__gc|__metatable|__mul|__div|__pow|__len|__eq|__le|__newindex|__tostring|__mode|__tonumber\",r=\"string|package|os|io|math|debug|table|coroutine\",i=\"setn|foreach|foreachi|gcinfo|log10|maxn\",s=this.createKeywordMapper({keyword:e,\"support.function\":n,\"keyword.deprecated\":i,\"constant.library\":r,\"constant.language\":t,\"variable.language\":\"self\"},\"identifier\"),o=\"(?:(?:[1-9]\\\\d*)|(?:0))\",u=\"(?:0[xX][\\\\dA-Fa-f]+)\",a=\"(?:\"+o+\"|\"+u+\")\",f=\"(?:\\\\.\\\\d+)\",l=\"(?:\\\\d+)\",c=\"(?:(?:\"+l+\"?\"+f+\")|(?:\"+l+\"\\\\.))\",h=\"(?:\"+c+\")\";this.$rules={start:[{stateName:\"bracketedComment\",onMatch:function(e,t,n){return n.unshift(this.next,e.length-2,t),\"comment\"},regex:/\\-\\-\\[=*\\[/,next:[{onMatch:function(e,t,n){return e.length==n[1]?(n.shift(),n.shift(),this.next=n.shift()):this.next=\"\",\"comment\"},regex:/\\]=*\\]/,next:\"start\"},{defaultToken:\"comment\"}]},{token:\"comment\",regex:\"\\\\-\\\\-.*$\"},{stateName:\"bracketedString\",onMatch:function(e,t,n){return n.unshift(this.next,e.length,t),\"comment\"},regex:/\\[=*\\[/,next:[{onMatch:function(e,t,n){return e.length==n[1]?(n.shift(),n.shift(),this.next=n.shift()):this.next=\"\",\"comment\"},regex:/\\]=*\\]/,next:\"start\"},{defaultToken:\"comment\"}]},{token:\"string\",regex:'\"(?:[^\\\\\\\\]|\\\\\\\\.)*?\"'},{token:\"string\",regex:\"'(?:[^\\\\\\\\]|\\\\\\\\.)*?'\"},{token:\"constant.numeric\",regex:h},{token:\"constant.numeric\",regex:a+\"\\\\b\"},{token:s,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"keyword.operator\",regex:\"\\\\+|\\\\-|\\\\*|\\\\/|%|\\\\#|\\\\^|~|<|>|<=|=>|==|~=|=|\\\\:|\\\\.\\\\.\\\\.|\\\\.\\\\.\"},{token:\"paren.lparen\",regex:\"[\\\\[\\\\(\\\\{]\"},{token:\"paren.rparen\",regex:\"[\\\\]\\\\)\\\\}]\"},{token:\"text\",regex:\"\\\\s+|\\\\w+\"}]},this.normalizeRules()};r.inherits(s,i),t.LuaHighlightRules=s}),define(\"ace/mode/folding/lua\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\",\"ace/range\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=e(\"../../range\").Range,o=e(\"../../token_iterator\").TokenIterator,u=t.FoldMode=function(){};r.inherits(u,i),function(){this.foldingStartMarker=/\\b(function|then|do|repeat)\\b|{\\s*$|(\\[=*\\[)/,this.foldingStopMarker=/\\bend\\b|^\\s*}|\\]=*\\]/,this.getFoldWidget=function(e,t,n){var r=e.getLine(n),i=this.foldingStartMarker.test(r),s=this.foldingStopMarker.test(r);if(i&&!s){var o=r.match(this.foldingStartMarker);if(o[1]==\"then\"&&/\\belseif\\b/.test(r))return;if(o[1]){if(e.getTokenAt(n,o.index+1).type===\"keyword\")return\"start\"}else{if(!o[2])return\"start\";var u=e.bgTokenizer.getState(n)||\"\";if(u[0]==\"bracketedComment\"||u[0]==\"bracketedString\")return\"start\"}}if(t!=\"markbeginend\"||!s||i&&s)return\"\";var o=r.match(this.foldingStopMarker);if(o[0]===\"end\"){if(e.getTokenAt(n,o.index+1).type===\"keyword\")return\"end\"}else{if(o[0][0]!==\"]\")return\"end\";var u=e.bgTokenizer.getState(n-1)||\"\";if(u[0]==\"bracketedComment\"||u[0]==\"bracketedString\")return\"end\"}},this.getFoldWidgetRange=function(e,t,n){var r=e.doc.getLine(n),i=this.foldingStartMarker.exec(r);if(i)return i[1]?this.luaBlock(e,n,i.index+1):i[2]?e.getCommentFoldRange(n,i.index+1):this.openingBracketBlock(e,\"{\",n,i.index);var i=this.foldingStopMarker.exec(r);if(i)return i[0]===\"end\"&&e.getTokenAt(n,i.index+1).type===\"keyword\"?this.luaBlock(e,n,i.index+1):i[0][0]===\"]\"?e.getCommentFoldRange(n,i.index+1):this.closingBracketBlock(e,\"}\",n,i.index+i[0].length)},this.luaBlock=function(e,t,n){var r=new o(e,t,n),i={\"function\":1,\"do\":1,then:1,elseif:-1,end:-1,repeat:1,until:-1},u=r.getCurrentToken();if(!u||u.type!=\"keyword\")return;var a=u.value,f=[a],l=i[a];if(!l)return;var c=l===-1?r.getCurrentTokenColumn():e.getLine(t).length,h=t;r.step=l===-1?r.stepBackward:r.stepForward;while(u=r.step()){if(u.type!==\"keyword\")continue;var p=l*i[u.value];if(p>0)f.unshift(u.value);else if(p<=0){f.shift();if(!f.length&&u.value!=\"elseif\")break;p===0&&f.unshift(u.value)}}var t=r.getCurrentTokenRow();return l===-1?new s(t,e.getLine(t).length,h,c):new s(h,c,t,r.getCurrentTokenColumn())}}.call(u.prototype)}),define(\"ace/mode/lua\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/lua_highlight_rules\",\"ace/mode/folding/lua\",\"ace/range\",\"ace/worker/worker_client\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./lua_highlight_rules\").LuaHighlightRules,o=e(\"./folding/lua\").FoldMode,u=e(\"../range\").Range,a=e(\"../worker/worker_client\").WorkerClient,f=function(){this.HighlightRules=s,this.foldingRules=new o,this.$behaviour=this.$defaultBehaviour};r.inherits(f,i),function(){function n(t){var n=0;for(var r=0;r<t.length;r++){var i=t[r];i.type==\"keyword\"?i.value in e&&(n+=e[i.value]):i.type==\"paren.lparen\"?n+=i.value.length:i.type==\"paren.rparen\"&&(n-=i.value.length)}return n<0?-1:n>0?1:0}this.lineCommentStart=\"--\",this.blockComment={start:\"--[\",end:\"]--\"};var e={\"function\":1,then:1,\"do\":1,\"else\":1,elseif:1,repeat:1,end:-1,until:-1},t=[\"else\",\"elseif\",\"end\",\"until\"];this.getNextLineIndent=function(e,t,r){var i=this.$getIndent(t),s=0,o=this.getTokenizer().getLineTokens(t,e),u=o.tokens;return e==\"start\"&&(s=n(u)),s>0?i+r:s<0&&i.substr(i.length-r.length)==r&&!this.checkOutdent(e,t,\"\\n\")?i.substr(0,i.length-r.length):i},this.checkOutdent=function(e,n,r){if(r!=\"\\n\"&&r!=\"\\r\"&&r!=\"\\r\\n\")return!1;if(n.match(/^\\s*[\\)\\}\\]]$/))return!0;var i=this.getTokenizer().getLineTokens(n.trim(),e).tokens;return!i||!i.length?!1:i[0].type==\"keyword\"&&t.indexOf(i[0].value)!=-1},this.autoOutdent=function(e,t,r){var i=t.getLine(r-1),s=this.$getIndent(i).length,o=this.getTokenizer().getLineTokens(i,\"start\").tokens,a=t.getTabString().length,f=s+a*n(o),l=this.$getIndent(t.getLine(r)).length;if(l<f)return;t.outdentRows(new u(r,0,r+2,0))},this.createWorker=function(e){var t=new a([\"ace\"],\"ace/mode/lua_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/lua\"}.call(f.prototype),t.Mode=f})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-markdown.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/javascript_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";function a(){var e=o.replace(\"\\\\d\",\"\\\\d\\\\-\"),t={onMatch:function(e,t,n){var r=e.charAt(1)==\"/\"?2:1;if(r==1)t!=this.nextState?n.unshift(this.next,this.nextState,0):n.unshift(this.next),n[2]++;else if(r==2&&t==this.nextState){n[1]--;if(!n[1]||n[1]<0)n.shift(),n.shift()}return[{type:\"meta.tag.punctuation.\"+(r==1?\"\":\"end-\")+\"tag-open.xml\",value:e.slice(0,r)},{type:\"meta.tag.tag-name.xml\",value:e.substr(r)}]},regex:\"</?\"+e+\"\",next:\"jsxAttributes\",nextState:\"jsx\"};this.$rules.start.unshift(t);var n={regex:\"{\",token:\"paren.quasi.start\",push:\"start\"};this.$rules.jsx=[n,t,{include:\"reference\"},{defaultToken:\"string\"}],this.$rules.jsxAttributes=[{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",onMatch:function(e,t,n){return t==n[0]&&n.shift(),e.length==2&&(n[0]==this.nextState&&n[1]--,(!n[1]||n[1]<0)&&n.splice(0,2)),this.next=n[0]||\"start\",[{type:this.token,value:e}]},nextState:\"jsx\"},n,f(\"jsxAttributes\"),{token:\"entity.other.attribute-name.xml\",regex:e},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"},{token:\"string.attribute-value.xml\",regex:\"'\",stateName:\"jsx_attr_q\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',stateName:\"jsx_attr_qq\",push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},t],this.$rules.reference=[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}]}function f(e){return[{token:\"comment\",regex:/\\/\\*/,next:[i.getTagRule(),{token:\"comment\",regex:\"\\\\*\\\\/\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]},{token:\"comment\",regex:\"\\\\/\\\\/\",next:[i.getTagRule(),{token:\"comment\",regex:\"$|^\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]}]}var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=\"[a-zA-Z\\\\$_\\u00a1-\\uffff][a-zA-Z\\\\d\\\\$_\\u00a1-\\uffff]*\",u=function(e){var t=this.createKeywordMapper({\"variable.language\":\"Array|Boolean|Date|Function|Iterator|Number|Object|RegExp|String|Proxy|Namespace|QName|XML|XMLList|ArrayBuffer|Float32Array|Float64Array|Int16Array|Int32Array|Int8Array|Uint16Array|Uint32Array|Uint8Array|Uint8ClampedArray|Error|EvalError|InternalError|RangeError|ReferenceError|StopIteration|SyntaxError|TypeError|URIError|decodeURI|decodeURIComponent|encodeURI|encodeURIComponent|eval|isFinite|isNaN|parseFloat|parseInt|JSON|Math|this|arguments|prototype|window|document\",keyword:\"const|yield|import|get|set|async|await|break|case|catch|continue|default|delete|do|else|finally|for|function|if|in|of|instanceof|new|return|switch|throw|try|typeof|let|var|while|with|debugger|__parent__|__count__|escape|unescape|with|__proto__|class|enum|extends|super|export|implements|private|public|interface|package|protected|static\",\"storage.type\":\"const|let|var|function\",\"constant.language\":\"null|Infinity|NaN|undefined\",\"support.function\":\"alert\",\"constant.language.boolean\":\"true|false\"},\"identifier\"),n=\"case|do|else|finally|in|instanceof|return|throw|try|typeof|yield|void\",r=\"\\\\\\\\(?:x[0-9a-fA-F]{2}|u[0-9a-fA-F]{4}|u{[0-9a-fA-F]{1,6}}|[0-2][0-7]{0,2}|3[0-7][0-7]?|[4-7][0-7]?|.)\";this.$rules={no_regex:[i.getStartRule(\"doc-start\"),f(\"no_regex\"),{token:\"string\",regex:\"'(?=.)\",next:\"qstring\"},{token:\"string\",regex:'\"(?=.)',next:\"qqstring\"},{token:\"constant.numeric\",regex:/0(?:[xX][0-9a-fA-F]+|[bB][01]+)\\b/},{token:\"constant.numeric\",regex:/[+-]?\\d[\\d_]*(?:(?:\\.\\d*)?(?:[eE][+-]?\\d+)?)?\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\"],regex:\"(\"+o+\")(\\\\.)(prototype)(\\\\.)(\"+o+\")(\\\\s*)(=)\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s+)(\\\\w+)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(function)(\\\\s+)(\"+o+\")(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"punctuation.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"text\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"keyword\",regex:\"(?:\"+n+\")\\\\b\",next:\"start\"},{token:[\"support.constant\"],regex:/that\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function.firebug\"],regex:/(console)(\\.)(warn|info|log|error|time|trace|timeEnd|assert)\\b/},{token:t,regex:o},{token:\"punctuation.operator\",regex:/[.](?![.])/,next:\"property\"},{token:\"keyword.operator\",regex:/--|\\+\\+|\\.{3}|===|==|=|!=|!==|<+=?|>+=?|!|&&|\\|\\||\\?:|[!$%&*+\\-~\\/^]=?/,next:\"start\"},{token:\"punctuation.operator\",regex:/[?:,;.]/,next:\"start\"},{token:\"paren.lparen\",regex:/[\\[({]/,next:\"start\"},{token:\"paren.rparen\",regex:/[\\])}]/},{token:\"comment\",regex:/^#!.*$/}],property:[{token:\"text\",regex:\"\\\\s+\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(?:(\\\\s+)(\\\\w+))?(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"punctuation.operator\",regex:/[.](?![.])/},{token:\"support.function\",regex:/(s(?:h(?:ift|ow(?:Mod(?:elessDialog|alDialog)|Help))|croll(?:X|By(?:Pages|Lines)?|Y|To)?|t(?:op|rike)|i(?:n|zeToContent|debar|gnText)|ort|u(?:p|b(?:str(?:ing)?)?)|pli(?:ce|t)|e(?:nd|t(?:Re(?:sizable|questHeader)|M(?:i(?:nutes|lliseconds)|onth)|Seconds|Ho(?:tKeys|urs)|Year|Cursor|Time(?:out)?|Interval|ZOptions|Date|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Date|FullYear)|FullYear|Active)|arch)|qrt|lice|avePreferences|mall)|h(?:ome|andleEvent)|navigate|c(?:har(?:CodeAt|At)|o(?:s|n(?:cat|textual|firm)|mpile)|eil|lear(?:Timeout|Interval)?|a(?:ptureEvents|ll)|reate(?:StyleSheet|Popup|EventObject))|t(?:o(?:GMTString|S(?:tring|ource)|U(?:TCString|pperCase)|Lo(?:caleString|werCase))|est|a(?:n|int(?:Enabled)?))|i(?:s(?:NaN|Finite)|ndexOf|talics)|d(?:isableExternalCapture|ump|etachEvent)|u(?:n(?:shift|taint|escape|watch)|pdateCommands)|j(?:oin|avaEnabled)|p(?:o(?:p|w)|ush|lugins.refresh|a(?:ddings|rse(?:Int|Float)?)|r(?:int|ompt|eference))|e(?:scape|nableExternalCapture|val|lementFromPoint|x(?:p|ec(?:Script|Command)?))|valueOf|UTC|queryCommand(?:State|Indeterm|Enabled|Value)|f(?:i(?:nd|le(?:ModifiedDate|Size|CreatedDate|UpdatedDate)|xed)|o(?:nt(?:size|color)|rward)|loor|romCharCode)|watch|l(?:ink|o(?:ad|g)|astIndexOf)|a(?:sin|nchor|cos|t(?:tachEvent|ob|an(?:2)?)|pply|lert|b(?:s|ort))|r(?:ou(?:nd|teEvents)|e(?:size(?:By|To)|calc|turnValue|place|verse|l(?:oad|ease(?:Capture|Events)))|andom)|g(?:o|et(?:ResponseHeader|M(?:i(?:nutes|lliseconds)|onth)|Se(?:conds|lection)|Hours|Year|Time(?:zoneOffset)?|Da(?:y|te)|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Da(?:y|te)|FullYear)|FullYear|A(?:ttention|llResponseHeaders)))|m(?:in|ove(?:B(?:y|elow)|To(?:Absolute)?|Above)|ergeAttributes|a(?:tch|rgins|x))|b(?:toa|ig|o(?:ld|rderWidths)|link|ack))\\b(?=\\()/},{token:\"support.function.dom\",regex:/(s(?:ub(?:stringData|mit)|plitText|e(?:t(?:NamedItem|Attribute(?:Node)?)|lect))|has(?:ChildNodes|Feature)|namedItem|c(?:l(?:ick|o(?:se|neNode))|reate(?:C(?:omment|DATASection|aption)|T(?:Head|extNode|Foot)|DocumentFragment|ProcessingInstruction|E(?:ntityReference|lement)|Attribute))|tabIndex|i(?:nsert(?:Row|Before|Cell|Data)|tem)|open|delete(?:Row|C(?:ell|aption)|T(?:Head|Foot)|Data)|focus|write(?:ln)?|a(?:dd|ppend(?:Child|Data))|re(?:set|place(?:Child|Data)|move(?:NamedItem|Child|Attribute(?:Node)?)?)|get(?:NamedItem|Element(?:sBy(?:Name|TagName|ClassName)|ById)|Attribute(?:Node)?)|blur)\\b(?=\\()/},{token:\"support.constant\",regex:/(s(?:ystemLanguage|cr(?:ipts|ollbars|een(?:X|Y|Top|Left))|t(?:yle(?:Sheets)?|atus(?:Text|bar)?)|ibling(?:Below|Above)|ource|uffixes|e(?:curity(?:Policy)?|l(?:ection|f)))|h(?:istory|ost(?:name)?|as(?:h|Focus))|y|X(?:MLDocument|SLDocument)|n(?:ext|ame(?:space(?:s|URI)|Prop))|M(?:IN_VALUE|AX_VALUE)|c(?:haracterSet|o(?:n(?:structor|trollers)|okieEnabled|lorDepth|mp(?:onents|lete))|urrent|puClass|l(?:i(?:p(?:boardData)?|entInformation)|osed|asses)|alle(?:e|r)|rypto)|t(?:o(?:olbar|p)|ext(?:Transform|Indent|Decoration|Align)|ags)|SQRT(?:1_2|2)|i(?:n(?:ner(?:Height|Width)|put)|ds|gnoreCase)|zIndex|o(?:scpu|n(?:readystatechange|Line)|uter(?:Height|Width)|p(?:sProfile|ener)|ffscreenBuffering)|NEGATIVE_INFINITY|d(?:i(?:splay|alog(?:Height|Top|Width|Left|Arguments)|rectories)|e(?:scription|fault(?:Status|Ch(?:ecked|arset)|View)))|u(?:ser(?:Profile|Language|Agent)|n(?:iqueID|defined)|pdateInterval)|_content|p(?:ixelDepth|ort|ersonalbar|kcs11|l(?:ugins|atform)|a(?:thname|dding(?:Right|Bottom|Top|Left)|rent(?:Window|Layer)?|ge(?:X(?:Offset)?|Y(?:Offset)?))|r(?:o(?:to(?:col|type)|duct(?:Sub)?|mpter)|e(?:vious|fix)))|e(?:n(?:coding|abledPlugin)|x(?:ternal|pando)|mbeds)|v(?:isibility|endor(?:Sub)?|Linkcolor)|URLUnencoded|P(?:I|OSITIVE_INFINITY)|f(?:ilename|o(?:nt(?:Size|Family|Weight)|rmName)|rame(?:s|Element)|gColor)|E|whiteSpace|l(?:i(?:stStyleType|n(?:eHeight|kColor))|o(?:ca(?:tion(?:bar)?|lName)|wsrc)|e(?:ngth|ft(?:Context)?)|a(?:st(?:M(?:odified|atch)|Index|Paren)|yer(?:s|X)|nguage))|a(?:pp(?:MinorVersion|Name|Co(?:deName|re)|Version)|vail(?:Height|Top|Width|Left)|ll|r(?:ity|guments)|Linkcolor|bove)|r(?:ight(?:Context)?|e(?:sponse(?:XML|Text)|adyState))|global|x|m(?:imeTypes|ultiline|enubar|argin(?:Right|Bottom|Top|Left))|L(?:N(?:10|2)|OG(?:10E|2E))|b(?:o(?:ttom|rder(?:Width|RightWidth|BottomWidth|Style|Color|TopWidth|LeftWidth))|ufferDepth|elow|ackground(?:Color|Image)))\\b/},{token:\"identifier\",regex:o},{regex:\"\",token:\"empty\",next:\"no_regex\"}],start:[i.getStartRule(\"doc-start\"),f(\"start\"),{token:\"string.regexp\",regex:\"\\\\/\",next:\"regex\"},{token:\"text\",regex:\"\\\\s+|^$\",next:\"start\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],regex:[{token:\"regexp.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"string.regexp\",regex:\"/[sxngimy]*\",next:\"no_regex\"},{token:\"invalid\",regex:/\\{\\d+\\b,?\\d*\\}[+*]|[+*$^?][+*]|[$^][?]|\\?{3,}/},{token:\"constant.language.escape\",regex:/\\(\\?[:=!]|\\)|\\{\\d+\\b,?\\d*\\}|[+*]\\?|[()$^+*?.]/},{token:\"constant.language.delimiter\",regex:/\\|/},{token:\"constant.language.escape\",regex:/\\[\\^?/,next:\"regex_character_class\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp\"}],regex_character_class:[{token:\"regexp.charclass.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"constant.language.escape\",regex:\"]\",next:\"regex\"},{token:\"constant.language.escape\",regex:\"-\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp.charachterclass\"}],function_arguments:[{token:\"variable.parameter\",regex:o},{token:\"punctuation.operator\",regex:\"[, ]+\"},{token:\"punctuation.operator\",regex:\"$\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],qqstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qqstring\"},{token:\"string\",regex:'\"|$',next:\"no_regex\"},{defaultToken:\"string\"}],qstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qstring\"},{token:\"string\",regex:\"'|$\",next:\"no_regex\"},{defaultToken:\"string\"}]};if(!e||!e.noES6)this.$rules.no_regex.unshift({regex:\"[{}]\",onMatch:function(e,t,n){this.next=e==\"{\"?this.nextState:\"\";if(e==\"{\"&&n.length)n.unshift(\"start\",t);else if(e==\"}\"&&n.length){n.shift(),this.next=n.shift();if(this.next.indexOf(\"string\")!=-1||this.next.indexOf(\"jsx\")!=-1)return\"paren.quasi.end\"}return e==\"{\"?\"paren.lparen\":\"paren.rparen\"},nextState:\"start\"},{token:\"string.quasi.start\",regex:/`/,push:[{token:\"constant.language.escape\",regex:r},{token:\"paren.quasi.start\",regex:/\\${/,push:\"start\"},{token:\"string.quasi.end\",regex:/`/,next:\"pop\"},{defaultToken:\"string.quasi\"}]}),(!e||e.jsx!=0)&&a.call(this);this.embedRules(i,\"doc-\",[i.getEndRule(\"no_regex\")]),this.normalizeRules()};r.inherits(u,s),t.JavaScriptHighlightRules=u}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/javascript\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./behaviour/cstyle\").CstyleBehaviour,f=e(\"./folding/cstyle\").FoldMode,l=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new a,this.foldingRules=new f};r.inherits(l,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens,o=i.state;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"||e==\"no_regex\"){var u=t.match(/^.*(?:\\bcase\\b.*:|[\\{\\(\\[])\\s*$/);u&&(r+=n)}else if(e==\"doc-start\"){if(o==\"start\"||o==\"no_regex\")return\"\";var u=t.match(/^\\s*(\\/?)\\*/);u&&(u[1]&&(r+=\" \"),r+=\"* \")}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/javascript_worker\",\"JavaScriptWorker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/javascript\"}.call(l.prototype),t.Mode=l}),define(\"ace/mode/xml_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(e){var t=\"[_:a-zA-Z\\u00c0-\\uffff][-_:.a-zA-Z0-9\\u00c0-\\uffff]*\";this.$rules={start:[{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\",next:\"cdata\"},{token:[\"punctuation.xml-decl.xml\",\"keyword.xml-decl.xml\"],regex:\"(<\\\\?)(xml)(?=[\\\\s])\",next:\"xml_decl\",caseInsensitive:!0},{token:[\"punctuation.instruction.xml\",\"keyword.instruction.xml\"],regex:\"(<\\\\?)(\"+t+\")\",next:\"processing_instruction\"},{token:\"comment.xml\",regex:\"<\\\\!--\",next:\"comment\"},{token:[\"xml-pe.doctype.xml\",\"xml-pe.doctype.xml\"],regex:\"(<\\\\!)(DOCTYPE)(?=[\\\\s])\",next:\"doctype\",caseInsensitive:!0},{include:\"tag\"},{token:\"text.end-tag-open.xml\",regex:\"</\"},{token:\"text.tag-open.xml\",regex:\"<\"},{include:\"reference\"},{defaultToken:\"text.xml\"}],xml_decl:[{token:\"entity.other.attribute-name.decl-attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.decl-attribute-equals.xml\",regex:\"=\"},{include:\"whitespace\"},{include:\"string\"},{token:\"punctuation.xml-decl.xml\",regex:\"\\\\?>\",next:\"start\"}],processing_instruction:[{token:\"punctuation.instruction.xml\",regex:\"\\\\?>\",next:\"start\"},{defaultToken:\"instruction.xml\"}],doctype:[{include:\"whitespace\"},{include:\"string\"},{token:\"xml-pe.doctype.xml\",regex:\">\",next:\"start\"},{token:\"xml-pe.xml\",regex:\"[-_a-zA-Z0-9:]+\"},{token:\"punctuation.int-subset\",regex:\"\\\\[\",push:\"int_subset\"}],int_subset:[{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"punctuation.int-subset.xml\",regex:\"]\",next:\"pop\"},{token:[\"punctuation.markup-decl.xml\",\"keyword.markup-decl.xml\"],regex:\"(<\\\\!)(\"+t+\")\",push:[{token:\"text\",regex:\"\\\\s+\"},{token:\"punctuation.markup-decl.xml\",regex:\">\",next:\"pop\"},{include:\"string\"}]}],cdata:[{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\",next:\"start\"},{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"text.xml\",regex:\"(?:[^\\\\]]|\\\\](?!\\\\]>))+\"}],comment:[{token:\"comment.xml\",regex:\"-->\",next:\"start\"},{defaultToken:\"comment.xml\"}],reference:[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],attr_reference:[{token:\"constant.language.escape.reference.attribute-value.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],tag:[{token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.tag-name.xml\"],regex:\"(?:(<)|(</))((?:\"+t+\":)?\"+t+\")\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}],tag_whitespace:[{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"}],whitespace:[{token:\"text.whitespace.xml\",regex:\"\\\\s+\"}],string:[{token:\"string.xml\",regex:\"'\",push:[{token:\"string.xml\",regex:\"'\",next:\"pop\"},{defaultToken:\"string.xml\"}]},{token:\"string.xml\",regex:'\"',push:[{token:\"string.xml\",regex:'\"',next:\"pop\"},{defaultToken:\"string.xml\"}]}],attributes:[{token:\"entity.other.attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{include:\"tag_whitespace\"},{include:\"attribute_value\"}],attribute_value:[{token:\"string.attribute-value.xml\",regex:\"'\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]}]},this.constructor===s&&this.normalizeRules()};(function(){this.embedTagRules=function(e,t,n){this.$rules.tag.unshift({token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(<)(\"+n+\"(?=\\\\s|>|$))\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:t+\"start\"}]}),this.$rules[n+\"-end\"]=[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\",onMatch:function(e,t,n){return n.splice(0),this.token}}],this.embedRules(e,t,[{token:[\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(</)(\"+n+\"(?=\\\\s|>|$))\",next:n+\"-end\"},{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\"},{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\"}])}}).call(i.prototype),r.inherits(s,i),t.XmlHighlightRules=s}),define(\"ace/mode/behaviour/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/token_iterator\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";function u(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"../../token_iterator\").TokenIterator,o=e(\"../../lib/lang\"),a=function(){this.add(\"string_dquotes\",\"insertion\",function(e,t,n,r,i){if(i=='\"'||i==\"'\"){var o=i,a=r.doc.getTextRange(n.getSelectionRange());if(a!==\"\"&&a!==\"'\"&&a!='\"'&&n.getWrapBehavioursEnabled())return{text:o+a+o,selection:!1};var f=n.getCursorPosition(),l=r.doc.getLine(f.row),c=l.substring(f.column,f.column+1),h=new s(r,f.row,f.column),p=h.getCurrentToken();if(c==o&&(u(p,\"attribute-value\")||u(p,\"string\")))return{text:\"\",selection:[1,1]};p||(p=h.stepBackward());if(!p)return;while(u(p,\"tag-whitespace\")||u(p,\"whitespace\"))p=h.stepBackward();var d=!c||c.match(/\\s/);if(u(p,\"attribute-equals\")&&(d||c==\">\")||u(p,\"decl-attribute-equals\")&&(d||c==\"?\"))return{text:o+o,selection:[1,1]}}}),this.add(\"string_dquotes\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&(s=='\"'||s==\"'\")){var o=r.doc.getLine(i.start.row),u=o.substring(i.start.column+1,i.start.column+2);if(u==s)return i.end.column++,i}}),this.add(\"autoclosing\",\"insertion\",function(e,t,n,r,i){if(i==\">\"){var o=n.getSelectionRange().start,a=new s(r,o.row,o.column),f=a.getCurrentToken()||a.stepBackward();if(!f||!(u(f,\"tag-name\")||u(f,\"tag-whitespace\")||u(f,\"attribute-name\")||u(f,\"attribute-equals\")||u(f,\"attribute-value\")))return;if(u(f,\"reference.attribute-value\"))return;if(u(f,\"attribute-value\")){var l=f.value.charAt(0);if(l=='\"'||l==\"'\"){var c=f.value.charAt(f.value.length-1),h=a.getCurrentTokenColumn()+f.value.length;if(h>o.column||h==o.column&&l!=c)return}}while(!u(f,\"tag-name\")){f=a.stepBackward();if(f.value==\"<\"){f=a.stepForward();break}}var p=a.getCurrentTokenRow(),d=a.getCurrentTokenColumn();if(u(a.stepBackward(),\"end-tag-open\"))return;var v=f.value;p==o.row&&(v=v.substring(0,o.column-d));if(this.voidElements.hasOwnProperty(v.toLowerCase()))return;return{text:\"></\"+v+\">\",selection:[1,1]}}}),this.add(\"autoindent\",\"insertion\",function(e,t,n,r,i){if(i==\"\\n\"){var o=n.getCursorPosition(),u=r.getLine(o.row),a=new s(r,o.row,o.column),f=a.getCurrentToken();if(f&&f.type.indexOf(\"tag-close\")!==-1){if(f.value==\"/>\")return;while(f&&f.type.indexOf(\"tag-name\")===-1)f=a.stepBackward();if(!f)return;var l=f.value,c=a.getCurrentTokenRow();f=a.stepBackward();if(!f||f.type.indexOf(\"end-tag\")!==-1)return;if(this.voidElements&&!this.voidElements[l]){var h=r.getTokenAt(o.row,o.column+1),u=r.getLine(c),p=this.$getIndent(u),d=p+r.getTabString();return h&&h.value===\"</\"?{text:\"\\n\"+d+\"\\n\"+p,selection:[1,d.length,1,d.length]}:{text:\"\\n\"+d}}}}})};r.inherits(a,i),t.XmlBehaviour=a}),define(\"ace/mode/folding/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/range\",\"ace/mode/folding/fold_mode\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";function l(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}var r=e(\"../../lib/oop\"),i=e(\"../../lib/lang\"),s=e(\"../../range\").Range,o=e(\"./fold_mode\").FoldMode,u=e(\"../../token_iterator\").TokenIterator,a=t.FoldMode=function(e,t){o.call(this),this.voidElements=e||{},this.optionalEndTags=r.mixin({},this.voidElements),t&&r.mixin(this.optionalEndTags,t)};r.inherits(a,o);var f=function(){this.tagName=\"\",this.closing=!1,this.selfClosing=!1,this.start={row:0,column:0},this.end={row:0,column:0}};(function(){this.getFoldWidget=function(e,t,n){var r=this._getFirstTagInLine(e,n);return r?r.closing||!r.tagName&&r.selfClosing?t==\"markbeginend\"?\"end\":\"\":!r.tagName||r.selfClosing||this.voidElements.hasOwnProperty(r.tagName.toLowerCase())?\"\":this._findEndTagInLine(e,n,r.tagName,r.end.column)?\"\":\"start\":\"\"},this._getFirstTagInLine=function(e,t){var n=e.getTokens(t),r=new f;for(var i=0;i<n.length;i++){var s=n[i];if(l(s,\"tag-open\")){r.end.column=r.start.column+s.value.length,r.closing=l(s,\"end-tag-open\"),s=n[++i];if(!s)return null;r.tagName=s.value,r.end.column+=s.value.length;for(i++;i<n.length;i++){s=n[i],r.end.column+=s.value.length;if(l(s,\"tag-close\")){r.selfClosing=s.value==\"/>\";break}}return r}if(l(s,\"tag-close\"))return r.selfClosing=s.value==\"/>\",r;r.start.column+=s.value.length}return null},this._findEndTagInLine=function(e,t,n,r){var i=e.getTokens(t),s=0;for(var o=0;o<i.length;o++){var u=i[o];s+=u.value.length;if(s<r)continue;if(l(u,\"end-tag-open\")){u=i[o+1];if(u&&u.value==n)return!0}}return!1},this._readTagForward=function(e){var t=e.getCurrentToken();if(!t)return null;var n=new f;do if(l(t,\"tag-open\"))n.closing=l(t,\"end-tag-open\"),n.start.row=e.getCurrentTokenRow(),n.start.column=e.getCurrentTokenColumn();else if(l(t,\"tag-name\"))n.tagName=t.value;else if(l(t,\"tag-close\"))return n.selfClosing=t.value==\"/>\",n.end.row=e.getCurrentTokenRow(),n.end.column=e.getCurrentTokenColumn()+t.value.length,e.stepForward(),n;while(t=e.stepForward());return null},this._readTagBackward=function(e){var t=e.getCurrentToken();if(!t)return null;var n=new f;do{if(l(t,\"tag-open\"))return n.closing=l(t,\"end-tag-open\"),n.start.row=e.getCurrentTokenRow(),n.start.column=e.getCurrentTokenColumn(),e.stepBackward(),n;l(t,\"tag-name\")?n.tagName=t.value:l(t,\"tag-close\")&&(n.selfClosing=t.value==\"/>\",n.end.row=e.getCurrentTokenRow(),n.end.column=e.getCurrentTokenColumn()+t.value.length)}while(t=e.stepBackward());return null},this._pop=function(e,t){while(e.length){var n=e[e.length-1];if(!t||n.tagName==t.tagName)return e.pop();if(this.optionalEndTags.hasOwnProperty(n.tagName)){e.pop();continue}return null}},this.getFoldWidgetRange=function(e,t,n){var r=this._getFirstTagInLine(e,n);if(!r)return null;var i=r.closing||r.selfClosing,o=[],a;if(!i){var f=new u(e,n,r.start.column),l={row:n,column:r.start.column+r.tagName.length+2};r.start.row==r.end.row&&(l.column=r.end.column);while(a=this._readTagForward(f)){if(a.selfClosing){if(!o.length)return a.start.column+=a.tagName.length+2,a.end.column-=2,s.fromPoints(a.start,a.end);continue}if(a.closing){this._pop(o,a);if(o.length==0)return s.fromPoints(l,a.start)}else o.push(a)}}else{var f=new u(e,n,r.end.column),c={row:n,column:r.start.column};while(a=this._readTagBackward(f)){if(a.selfClosing){if(!o.length)return a.start.column+=a.tagName.length+2,a.end.column-=2,s.fromPoints(a.start,a.end);continue}if(!a.closing){this._pop(o,a);if(o.length==0)return a.start.column+=a.tagName.length+2,a.start.row==a.end.row&&a.start.column<a.end.column&&(a.start.column=a.end.column),s.fromPoints(a.start,c)}else o.push(a)}}}}).call(a.prototype)}),define(\"ace/mode/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text\",\"ace/mode/xml_highlight_rules\",\"ace/mode/behaviour/xml\",\"ace/mode/folding/xml\",\"ace/worker/worker_client\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text\").Mode,o=e(\"./xml_highlight_rules\").XmlHighlightRules,u=e(\"./behaviour/xml\").XmlBehaviour,a=e(\"./folding/xml\").FoldMode,f=e(\"../worker/worker_client\").WorkerClient,l=function(){this.HighlightRules=o,this.$behaviour=new u,this.foldingRules=new a};r.inherits(l,s),function(){this.voidElements=i.arrayToMap([]),this.blockComment={start:\"<!--\",end:\"-->\"},this.createWorker=function(e){var t=new f([\"ace\"],\"ace/mode/xml_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),t.on(\"error\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/xml\"}.call(l.prototype),t.Mode=l}),define(\"ace/mode/css_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text_highlight_rules\").TextHighlightRules,o=t.supportType=\"align-content|align-items|align-self|all|animation|animation-delay|animation-direction|animation-duration|animation-fill-mode|animation-iteration-count|animation-name|animation-play-state|animation-timing-function|backface-visibility|background|background-attachment|background-blend-mode|background-clip|background-color|background-image|background-origin|background-position|background-repeat|background-size|border|border-bottom|border-bottom-color|border-bottom-left-radius|border-bottom-right-radius|border-bottom-style|border-bottom-width|border-collapse|border-color|border-image|border-image-outset|border-image-repeat|border-image-slice|border-image-source|border-image-width|border-left|border-left-color|border-left-style|border-left-width|border-radius|border-right|border-right-color|border-right-style|border-right-width|border-spacing|border-style|border-top|border-top-color|border-top-left-radius|border-top-right-radius|border-top-style|border-top-width|border-width|bottom|box-shadow|box-sizing|caption-side|clear|clip|color|column-count|column-fill|column-gap|column-rule|column-rule-color|column-rule-style|column-rule-width|column-span|column-width|columns|content|counter-increment|counter-reset|cursor|direction|display|empty-cells|filter|flex|flex-basis|flex-direction|flex-flow|flex-grow|flex-shrink|flex-wrap|float|font|font-family|font-size|font-size-adjust|font-stretch|font-style|font-variant|font-weight|hanging-punctuation|height|justify-content|left|letter-spacing|line-height|list-style|list-style-image|list-style-position|list-style-type|margin|margin-bottom|margin-left|margin-right|margin-top|max-height|max-width|min-height|min-width|nav-down|nav-index|nav-left|nav-right|nav-up|opacity|order|outline|outline-color|outline-offset|outline-style|outline-width|overflow|overflow-x|overflow-y|padding|padding-bottom|padding-left|padding-right|padding-top|page-break-after|page-break-before|page-break-inside|perspective|perspective-origin|position|quotes|resize|right|tab-size|table-layout|text-align|text-align-last|text-decoration|text-decoration-color|text-decoration-line|text-decoration-style|text-indent|text-justify|text-overflow|text-shadow|text-transform|top|transform|transform-origin|transform-style|transition|transition-delay|transition-duration|transition-property|transition-timing-function|unicode-bidi|vertical-align|visibility|white-space|width|word-break|word-spacing|word-wrap|z-index\",u=t.supportFunction=\"rgb|rgba|url|attr|counter|counters\",a=t.supportConstant=\"absolute|after-edge|after|all-scroll|all|alphabetic|always|antialiased|armenian|auto|avoid-column|avoid-page|avoid|balance|baseline|before-edge|before|below|bidi-override|block-line-height|block|bold|bolder|border-box|both|bottom|box|break-all|break-word|capitalize|caps-height|caption|center|central|char|circle|cjk-ideographic|clone|close-quote|col-resize|collapse|column|consider-shifts|contain|content-box|cover|crosshair|cubic-bezier|dashed|decimal-leading-zero|decimal|default|disabled|disc|disregard-shifts|distribute-all-lines|distribute-letter|distribute-space|distribute|dotted|double|e-resize|ease-in|ease-in-out|ease-out|ease|ellipsis|end|exclude-ruby|fill|fixed|georgian|glyphs|grid-height|groove|hand|hanging|hebrew|help|hidden|hiragana-iroha|hiragana|horizontal|icon|ideograph-alpha|ideograph-numeric|ideograph-parenthesis|ideograph-space|ideographic|inactive|include-ruby|inherit|initial|inline-block|inline-box|inline-line-height|inline-table|inline|inset|inside|inter-ideograph|inter-word|invert|italic|justify|katakana-iroha|katakana|keep-all|last|left|lighter|line-edge|line-through|line|linear|list-item|local|loose|lower-alpha|lower-greek|lower-latin|lower-roman|lowercase|lr-tb|ltr|mathematical|max-height|max-size|medium|menu|message-box|middle|move|n-resize|ne-resize|newspaper|no-change|no-close-quote|no-drop|no-open-quote|no-repeat|none|normal|not-allowed|nowrap|nw-resize|oblique|open-quote|outset|outside|overline|padding-box|page|pointer|pre-line|pre-wrap|pre|preserve-3d|progress|relative|repeat-x|repeat-y|repeat|replaced|reset-size|ridge|right|round|row-resize|rtl|s-resize|scroll|se-resize|separate|slice|small-caps|small-caption|solid|space|square|start|static|status-bar|step-end|step-start|steps|stretch|strict|sub|super|sw-resize|table-caption|table-cell|table-column-group|table-column|table-footer-group|table-header-group|table-row-group|table-row|table|tb-rl|text-after-edge|text-before-edge|text-bottom|text-size|text-top|text|thick|thin|transparent|underline|upper-alpha|upper-latin|upper-roman|uppercase|use-script|vertical-ideographic|vertical-text|visible|w-resize|wait|whitespace|z-index|zero\",f=t.supportConstantColor=\"aqua|black|blue|fuchsia|gray|green|lime|maroon|navy|olive|orange|purple|red|silver|teal|white|yellow\",l=t.supportConstantFonts=\"arial|century|comic|courier|cursive|fantasy|garamond|georgia|helvetica|impact|lucida|symbol|system|tahoma|times|trebuchet|utopia|verdana|webdings|sans-serif|serif|monospace\",c=t.numRe=\"\\\\-?(?:(?:[0-9]+)|(?:[0-9]*\\\\.[0-9]+))\",h=t.pseudoElements=\"(\\\\:+)\\\\b(after|before|first-letter|first-line|moz-selection|selection)\\\\b\",p=t.pseudoClasses=\"(:)\\\\b(active|checked|disabled|empty|enabled|first-child|first-of-type|focus|hover|indeterminate|invalid|last-child|last-of-type|link|not|nth-child|nth-last-child|nth-last-of-type|nth-of-type|only-child|only-of-type|required|root|target|valid|visited)\\\\b\",d=function(){var e=this.createKeywordMapper({\"support.function\":u,\"support.constant\":a,\"support.type\":o,\"support.constant.color\":f,\"support.constant.fonts\":l},\"text\",!0);this.$rules={start:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"@.*?{\",push:\"media\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],media:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"\\\\}\",next:\"pop\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],comment:[{token:\"comment\",regex:\"\\\\*\\\\/\",next:\"pop\"},{defaultToken:\"comment\"}],ruleset:[{token:\"paren.rparen\",regex:\"\\\\}\",next:\"pop\"},{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},{token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},{token:[\"constant.numeric\",\"keyword\"],regex:\"(\"+c+\")(ch|cm|deg|em|ex|fr|gd|grad|Hz|in|kHz|mm|ms|pc|pt|px|rad|rem|s|turn|vh|vm|vw|%)\"},{token:\"constant.numeric\",regex:c},{token:\"constant.numeric\",regex:\"#[a-f0-9]{6}\"},{token:\"constant.numeric\",regex:\"#[a-f0-9]{3}\"},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-element.css\"],regex:h},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-class.css\"],regex:p},{token:[\"support.function\",\"string\",\"support.function\"],regex:\"(url\\\\()(.*)(\\\\))\"},{token:e,regex:\"\\\\-?[a-zA-Z_][a-zA-Z0-9_\\\\-]*\"},{caseInsensitive:!0}]},this.normalizeRules()};r.inherits(d,s),t.CssHighlightRules=d}),define(\"ace/mode/css_completions\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={background:{\"#$0\":1},\"background-color\":{\"#$0\":1,transparent:1,fixed:1},\"background-image\":{\"url('/$0')\":1},\"background-repeat\":{repeat:1,\"repeat-x\":1,\"repeat-y\":1,\"no-repeat\":1,inherit:1},\"background-position\":{bottom:2,center:2,left:2,right:2,top:2,inherit:2},\"background-attachment\":{scroll:1,fixed:1},\"background-size\":{cover:1,contain:1},\"background-clip\":{\"border-box\":1,\"padding-box\":1,\"content-box\":1},\"background-origin\":{\"border-box\":1,\"padding-box\":1,\"content-box\":1},border:{\"solid $0\":1,\"dashed $0\":1,\"dotted $0\":1,\"#$0\":1},\"border-color\":{\"#$0\":1},\"border-style\":{solid:2,dashed:2,dotted:2,\"double\":2,groove:2,hidden:2,inherit:2,inset:2,none:2,outset:2,ridged:2},\"border-collapse\":{collapse:1,separate:1},bottom:{px:1,em:1,\"%\":1},clear:{left:1,right:1,both:1,none:1},color:{\"#$0\":1,\"rgb(#$00,0,0)\":1},cursor:{\"default\":1,pointer:1,move:1,text:1,wait:1,help:1,progress:1,\"n-resize\":1,\"ne-resize\":1,\"e-resize\":1,\"se-resize\":1,\"s-resize\":1,\"sw-resize\":1,\"w-resize\":1,\"nw-resize\":1},display:{none:1,block:1,inline:1,\"inline-block\":1,\"table-cell\":1},\"empty-cells\":{show:1,hide:1},\"float\":{left:1,right:1,none:1},\"font-family\":{Arial:2,\"Comic Sans MS\":2,Consolas:2,\"Courier New\":2,Courier:2,Georgia:2,Monospace:2,\"Sans-Serif\":2,\"Segoe UI\":2,Tahoma:2,\"Times New Roman\":2,\"Trebuchet MS\":2,Verdana:1},\"font-size\":{px:1,em:1,\"%\":1},\"font-weight\":{bold:1,normal:1},\"font-style\":{italic:1,normal:1},\"font-variant\":{normal:1,\"small-caps\":1},height:{px:1,em:1,\"%\":1},left:{px:1,em:1,\"%\":1},\"letter-spacing\":{normal:1},\"line-height\":{normal:1},\"list-style-type\":{none:1,disc:1,circle:1,square:1,decimal:1,\"decimal-leading-zero\":1,\"lower-roman\":1,\"upper-roman\":1,\"lower-greek\":1,\"lower-latin\":1,\"upper-latin\":1,georgian:1,\"lower-alpha\":1,\"upper-alpha\":1},margin:{px:1,em:1,\"%\":1},\"margin-right\":{px:1,em:1,\"%\":1},\"margin-left\":{px:1,em:1,\"%\":1},\"margin-top\":{px:1,em:1,\"%\":1},\"margin-bottom\":{px:1,em:1,\"%\":1},\"max-height\":{px:1,em:1,\"%\":1},\"max-width\":{px:1,em:1,\"%\":1},\"min-height\":{px:1,em:1,\"%\":1},\"min-width\":{px:1,em:1,\"%\":1},overflow:{hidden:1,visible:1,auto:1,scroll:1},\"overflow-x\":{hidden:1,visible:1,auto:1,scroll:1},\"overflow-y\":{hidden:1,visible:1,auto:1,scroll:1},padding:{px:1,em:1,\"%\":1},\"padding-top\":{px:1,em:1,\"%\":1},\"padding-right\":{px:1,em:1,\"%\":1},\"padding-bottom\":{px:1,em:1,\"%\":1},\"padding-left\":{px:1,em:1,\"%\":1},\"page-break-after\":{auto:1,always:1,avoid:1,left:1,right:1},\"page-break-before\":{auto:1,always:1,avoid:1,left:1,right:1},position:{absolute:1,relative:1,fixed:1,\"static\":1},right:{px:1,em:1,\"%\":1},\"table-layout\":{fixed:1,auto:1},\"text-decoration\":{none:1,underline:1,\"line-through\":1,blink:1},\"text-align\":{left:1,right:1,center:1,justify:1},\"text-transform\":{capitalize:1,uppercase:1,lowercase:1,none:1},top:{px:1,em:1,\"%\":1},\"vertical-align\":{top:1,bottom:1},visibility:{hidden:1,visible:1},\"white-space\":{nowrap:1,normal:1,pre:1,\"pre-line\":1,\"pre-wrap\":1},width:{px:1,em:1,\"%\":1},\"word-spacing\":{normal:1},filter:{\"alpha(opacity=$0100)\":1},\"text-shadow\":{\"$02px 2px 2px #777\":1},\"text-overflow\":{\"ellipsis-word\":1,clip:1,ellipsis:1},\"-moz-border-radius\":1,\"-moz-border-radius-topright\":1,\"-moz-border-radius-bottomright\":1,\"-moz-border-radius-topleft\":1,\"-moz-border-radius-bottomleft\":1,\"-webkit-border-radius\":1,\"-webkit-border-top-right-radius\":1,\"-webkit-border-top-left-radius\":1,\"-webkit-border-bottom-right-radius\":1,\"-webkit-border-bottom-left-radius\":1,\"-moz-box-shadow\":1,\"-webkit-box-shadow\":1,transform:{\"rotate($00deg)\":1,\"skew($00deg)\":1},\"-moz-transform\":{\"rotate($00deg)\":1,\"skew($00deg)\":1},\"-webkit-transform\":{\"rotate($00deg)\":1,\"skew($00deg)\":1}},i=function(){};(function(){this.completionsDefined=!1,this.defineCompletions=function(){if(document){var e=document.createElement(\"c\").style;for(var t in e){if(typeof e[t]!=\"string\")continue;var n=t.replace(/[A-Z]/g,function(e){return\"-\"+e.toLowerCase()});r.hasOwnProperty(n)||(r[n]=1)}}this.completionsDefined=!0},this.getCompletions=function(e,t,n,r){this.completionsDefined||this.defineCompletions();var i=t.getTokenAt(n.row,n.column);if(!i)return[];if(e===\"ruleset\"){var s=t.getLine(n.row).substr(0,n.column);return/:[^;]+$/.test(s)?(/([\\w\\-]+):[^:]*$/.test(s),this.getPropertyValueCompletions(e,t,n,r)):this.getPropertyCompletions(e,t,n,r)}return[]},this.getPropertyCompletions=function(e,t,n,i){var s=Object.keys(r);return s.map(function(e){return{caption:e,snippet:e+\": $0\",meta:\"property\",score:Number.MAX_VALUE}})},this.getPropertyValueCompletions=function(e,t,n,i){var s=t.getLine(n.row).substr(0,n.column),o=(/([\\w\\-]+):[^:]*$/.exec(s)||{})[1];if(!o)return[];var u=[];return o in r&&typeof r[o]==\"object\"&&(u=Object.keys(r[o])),u.map(function(e){return{caption:e,snippet:e,meta:\"property value\",score:Number.MAX_VALUE}})}}).call(i.prototype),t.CssCompletions=i}),define(\"ace/mode/behaviour/css\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/mode/behaviour/cstyle\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"./cstyle\").CstyleBehaviour,o=e(\"../../token_iterator\").TokenIterator,u=function(){this.inherit(s),this.add(\"colon\",\"insertion\",function(e,t,n,r,i){if(i===\":\"){var s=n.getCursorPosition(),u=new o(r,s.row,s.column),a=u.getCurrentToken();a&&a.value.match(/\\s+/)&&(a=u.stepBackward());if(a&&a.type===\"support.type\"){var f=r.doc.getLine(s.row),l=f.substring(s.column,s.column+1);if(l===\":\")return{text:\"\",selection:[1,1]};if(!f.substring(s.column).match(/^\\s*;/))return{text:\":;\",selection:[1,1]}}}}),this.add(\"colon\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&s===\":\"){var u=n.getCursorPosition(),a=new o(r,u.row,u.column),f=a.getCurrentToken();f&&f.value.match(/\\s+/)&&(f=a.stepBackward());if(f&&f.type===\"support.type\"){var l=r.doc.getLine(i.start.row),c=l.substring(i.end.column,i.end.column+1);if(c===\";\")return i.end.column++,i}}}),this.add(\"semicolon\",\"insertion\",function(e,t,n,r,i){if(i===\";\"){var s=n.getCursorPosition(),o=r.doc.getLine(s.row),u=o.substring(s.column,s.column+1);if(u===\";\")return{text:\"\",selection:[1,1]}}})};r.inherits(u,s),t.CssBehaviour=u}),define(\"ace/mode/css\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/css_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/css_completions\",\"ace/mode/behaviour/css\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./css_highlight_rules\").CssHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./css_completions\").CssCompletions,f=e(\"./behaviour/css\").CssBehaviour,l=e(\"./folding/cstyle\").FoldMode,c=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new f,this.$completer=new a,this.foldingRules=new l};r.inherits(c,i),function(){this.foldingRules=\"cStyle\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e).tokens;if(i.length&&i[i.length-1].type==\"comment\")return r;var s=t.match(/^.*\\{\\s*$/);return s&&(r+=n),r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.getCompletions=function(e,t,n,r){return this.$completer.getCompletions(e,t,n,r)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/css_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/css\"}.call(c.prototype),t.Mode=c}),define(\"ace/mode/html_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/css_highlight_rules\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/xml_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./css_highlight_rules\").CssHighlightRules,o=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,u=e(\"./xml_highlight_rules\").XmlHighlightRules,a=i.createMap({a:\"anchor\",button:\"form\",form:\"form\",img:\"image\",input:\"form\",label:\"form\",option:\"form\",script:\"script\",select:\"form\",textarea:\"form\",style:\"style\",table:\"table\",tbody:\"table\",td:\"table\",tfoot:\"table\",th:\"table\",tr:\"table\"}),f=function(){u.call(this),this.addRules({attributes:[{include:\"tag_whitespace\"},{token:\"entity.other.attribute-name.xml\",regex:\"[-_a-zA-Z0-9:.]+\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\",push:[{include:\"tag_whitespace\"},{token:\"string.unquoted.attribute-value.html\",regex:\"[^<>='\\\"`\\\\s]+\",next:\"pop\"},{token:\"empty\",regex:\"\",next:\"pop\"}]},{include:\"attribute_value\"}],tag:[{token:function(e,t){var n=a[t];return[\"meta.tag.punctuation.\"+(e==\"<\"?\"\":\"end-\")+\"tag-open.xml\",\"meta.tag\"+(n?\".\"+n:\"\")+\".tag-name.xml\"]},regex:\"(</?)([-_a-zA-Z0-9:.]+)\",next:\"tag_stuff\"}],tag_stuff:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}),this.embedTagRules(s,\"css-\",\"style\"),this.embedTagRules((new o({jsx:!1})).getRules(),\"js-\",\"script\"),this.constructor===f&&this.normalizeRules()};r.inherits(f,u),t.HtmlHighlightRules=f}),define(\"ace/mode/folding/mixed\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=t.FoldMode=function(e,t){this.defaultMode=e,this.subModes=t};r.inherits(s,i),function(){this.$getMode=function(e){typeof e!=\"string\"&&(e=e[0]);for(var t in this.subModes)if(e.indexOf(t)===0)return this.subModes[t];return null},this.$tryMode=function(e,t,n,r){var i=this.$getMode(e);return i?i.getFoldWidget(t,n,r):\"\"},this.getFoldWidget=function(e,t,n){return this.$tryMode(e.getState(n-1),e,t,n)||this.$tryMode(e.getState(n),e,t,n)||this.defaultMode.getFoldWidget(e,t,n)},this.getFoldWidgetRange=function(e,t,n){var r=this.$getMode(e.getState(n-1));if(!r||!r.getFoldWidget(e,t,n))r=this.$getMode(e.getState(n));if(!r||!r.getFoldWidget(e,t,n))r=this.defaultMode;return r.getFoldWidgetRange(e,t,n)}}.call(s.prototype)}),define(\"ace/mode/folding/html\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/mixed\",\"ace/mode/folding/xml\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./mixed\").FoldMode,s=e(\"./xml\").FoldMode,o=e(\"./cstyle\").FoldMode,u=t.FoldMode=function(e,t){i.call(this,new s(e,t),{\"js-\":new o,\"css-\":new o})};r.inherits(u,i)}),define(\"ace/mode/html_completions\",[\"require\",\"exports\",\"module\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";function f(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}function l(e,t){var n=new r(e,t.row,t.column),i=n.getCurrentToken();while(i&&!f(i,\"tag-name\"))i=n.stepBackward();if(i)return i.value}function c(e,t){var n=new r(e,t.row,t.column),i=n.getCurrentToken();while(i&&!f(i,\"attribute-name\"))i=n.stepBackward();if(i)return i.value}var r=e(\"../token_iterator\").TokenIterator,i=[\"accesskey\",\"class\",\"contenteditable\",\"contextmenu\",\"dir\",\"draggable\",\"dropzone\",\"hidden\",\"id\",\"inert\",\"itemid\",\"itemprop\",\"itemref\",\"itemscope\",\"itemtype\",\"lang\",\"spellcheck\",\"style\",\"tabindex\",\"title\",\"translate\"],s=[\"onabort\",\"onblur\",\"oncancel\",\"oncanplay\",\"oncanplaythrough\",\"onchange\",\"onclick\",\"onclose\",\"oncontextmenu\",\"oncuechange\",\"ondblclick\",\"ondrag\",\"ondragend\",\"ondragenter\",\"ondragleave\",\"ondragover\",\"ondragstart\",\"ondrop\",\"ondurationchange\",\"onemptied\",\"onended\",\"onerror\",\"onfocus\",\"oninput\",\"oninvalid\",\"onkeydown\",\"onkeypress\",\"onkeyup\",\"onload\",\"onloadeddata\",\"onloadedmetadata\",\"onloadstart\",\"onmousedown\",\"onmousemove\",\"onmouseout\",\"onmouseover\",\"onmouseup\",\"onmousewheel\",\"onpause\",\"onplay\",\"onplaying\",\"onprogress\",\"onratechange\",\"onreset\",\"onscroll\",\"onseeked\",\"onseeking\",\"onselect\",\"onshow\",\"onstalled\",\"onsubmit\",\"onsuspend\",\"ontimeupdate\",\"onvolumechange\",\"onwaiting\"],o=i.concat(s),u={html:{manifest:1},head:{},title:{},base:{href:1,target:1},link:{href:1,hreflang:1,rel:{stylesheet:1,icon:1},media:{all:1,screen:1,print:1},type:{\"text/css\":1,\"image/png\":1,\"image/jpeg\":1,\"image/gif\":1},sizes:1},meta:{\"http-equiv\":{\"content-type\":1},name:{description:1,keywords:1},content:{\"text/html; charset=UTF-8\":1},charset:1},style:{type:1,media:{all:1,screen:1,print:1},scoped:1},script:{charset:1,type:{\"text/javascript\":1},src:1,defer:1,async:1},noscript:{href:1},body:{onafterprint:1,onbeforeprint:1,onbeforeunload:1,onhashchange:1,onmessage:1,onoffline:1,onpopstate:1,onredo:1,onresize:1,onstorage:1,onundo:1,onunload:1},section:{},nav:{},article:{pubdate:1},aside:{},h1:{},h2:{},h3:{},h4:{},h5:{},h6:{},header:{},footer:{},address:{},main:{},p:{},hr:{},pre:{},blockquote:{cite:1},ol:{start:1,reversed:1},ul:{},li:{value:1},dl:{},dt:{},dd:{},figure:{},figcaption:{},div:{},a:{href:1,target:{_blank:1,top:1},ping:1,rel:{nofollow:1,alternate:1,author:1,bookmark:1,help:1,license:1,next:1,noreferrer:1,prefetch:1,prev:1,search:1,tag:1},media:1,hreflang:1,type:1},em:{},strong:{},small:{},s:{},cite:{},q:{cite:1},dfn:{},abbr:{},data:{},time:{datetime:1},code:{},\"var\":{},samp:{},kbd:{},sub:{},sup:{},i:{},b:{},u:{},mark:{},ruby:{},rt:{},rp:{},bdi:{},bdo:{},span:{},br:{},wbr:{},ins:{cite:1,datetime:1},del:{cite:1,datetime:1},img:{alt:1,src:1,height:1,width:1,usemap:1,ismap:1},iframe:{name:1,src:1,height:1,width:1,sandbox:{\"allow-same-origin\":1,\"allow-top-navigation\":1,\"allow-forms\":1,\"allow-scripts\":1},seamless:{seamless:1}},embed:{src:1,height:1,width:1,type:1},object:{param:1,data:1,type:1,height:1,width:1,usemap:1,name:1,form:1,classid:1},param:{name:1,value:1},video:{src:1,autobuffer:1,autoplay:{autoplay:1},loop:{loop:1},controls:{controls:1},width:1,height:1,poster:1,muted:{muted:1},preload:{auto:1,metadata:1,none:1}},audio:{src:1,autobuffer:1,autoplay:{autoplay:1},loop:{loop:1},controls:{controls:1},muted:{muted:1},preload:{auto:1,metadata:1,none:1}},source:{src:1,type:1,media:1},track:{kind:1,src:1,srclang:1,label:1,\"default\":1},canvas:{width:1,height:1},map:{name:1},area:{shape:1,coords:1,href:1,hreflang:1,alt:1,target:1,media:1,rel:1,ping:1,type:1},svg:{},math:{},table:{summary:1},caption:{},colgroup:{span:1},col:{span:1},tbody:{},thead:{},tfoot:{},tr:{},td:{headers:1,rowspan:1,colspan:1},th:{headers:1,rowspan:1,colspan:1,scope:1},form:{\"accept-charset\":1,action:1,autocomplete:1,enctype:{\"multipart/form-data\":1,\"application/x-www-form-urlencoded\":1},method:{get:1,post:1},name:1,novalidate:1,target:{_blank:1,top:1}},fieldset:{disabled:1,form:1,name:1},legend:{},label:{form:1,\"for\":1},input:{type:{text:1,password:1,hidden:1,checkbox:1,submit:1,radio:1,file:1,button:1,reset:1,image:31,color:1,date:1,datetime:1,\"datetime-local\":1,email:1,month:1,number:1,range:1,search:1,tel:1,time:1,url:1,week:1},accept:1,alt:1,autocomplete:{on:1,off:1},autofocus:{autofocus:1},checked:{checked:1},disabled:{disabled:1},form:1,formaction:1,formenctype:{\"application/x-www-form-urlencoded\":1,\"multipart/form-data\":1,\"text/plain\":1},formmethod:{get:1,post:1},formnovalidate:{formnovalidate:1},formtarget:{_blank:1,_self:1,_parent:1,_top:1},height:1,list:1,max:1,maxlength:1,min:1,multiple:{multiple:1},name:1,pattern:1,placeholder:1,readonly:{readonly:1},required:{required:1},size:1,src:1,step:1,width:1,files:1,value:1},button:{autofocus:1,disabled:{disabled:1},form:1,formaction:1,formenctype:1,formmethod:1,formnovalidate:1,formtarget:1,name:1,value:1,type:{button:1,submit:1}},select:{autofocus:1,disabled:1,form:1,multiple:{multiple:1},name:1,size:1,readonly:{readonly:1}},datalist:{},optgroup:{disabled:1,label:1},option:{disabled:1,selected:1,label:1,value:1},textarea:{autofocus:{autofocus:1},disabled:{disabled:1},form:1,maxlength:1,name:1,placeholder:1,readonly:{readonly:1},required:{required:1},rows:1,cols:1,wrap:{on:1,off:1,hard:1,soft:1}},keygen:{autofocus:1,challenge:{challenge:1},disabled:{disabled:1},form:1,keytype:{rsa:1,dsa:1,ec:1},name:1},output:{\"for\":1,form:1,name:1},progress:{value:1,max:1},meter:{value:1,min:1,max:1,low:1,high:1,optimum:1},details:{open:1},summary:{},command:{type:1,label:1,icon:1,disabled:1,checked:1,radiogroup:1,command:1},menu:{type:1,label:1},dialog:{open:1}},a=Object.keys(u),h=function(){};(function(){this.getCompletions=function(e,t,n,r){var i=t.getTokenAt(n.row,n.column);if(!i)return[];if(f(i,\"tag-name\")||f(i,\"tag-open\")||f(i,\"end-tag-open\"))return this.getTagCompletions(e,t,n,r);if(f(i,\"tag-whitespace\")||f(i,\"attribute-name\"))return this.getAttributeCompletions(e,t,n,r);if(f(i,\"attribute-value\"))return this.getAttributeValueCompletions(e,t,n,r);var s=t.getLine(n.row).substr(0,n.column);return/&[a-z]*$/i.test(s)?this.getHTMLEntityCompletions(e,t,n,r):[]},this.getTagCompletions=function(e,t,n,r){return a.map(function(e){return{value:e,meta:\"tag\",score:Number.MAX_VALUE}})},this.getAttributeCompletions=function(e,t,n,r){var i=l(t,n);if(!i)return[];var s=o;return i in u&&(s=s.concat(Object.keys(u[i]))),s.map(function(e){return{caption:e,snippet:e+'=\"$0\"',meta:\"attribute\",score:Number.MAX_VALUE}})},this.getAttributeValueCompletions=function(e,t,n,r){var i=l(t,n),s=c(t,n);if(!i)return[];var o=[];return i in u&&s in u[i]&&typeof u[i][s]==\"object\"&&(o=Object.keys(u[i][s])),o.map(function(e){return{caption:e,snippet:e,meta:\"attribute value\",score:Number.MAX_VALUE}})},this.getHTMLEntityCompletions=function(e,t,n,r){var i=[\"Aacute;\",\"aacute;\",\"Acirc;\",\"acirc;\",\"acute;\",\"AElig;\",\"aelig;\",\"Agrave;\",\"agrave;\",\"alefsym;\",\"Alpha;\",\"alpha;\",\"amp;\",\"and;\",\"ang;\",\"Aring;\",\"aring;\",\"asymp;\",\"Atilde;\",\"atilde;\",\"Auml;\",\"auml;\",\"bdquo;\",\"Beta;\",\"beta;\",\"brvbar;\",\"bull;\",\"cap;\",\"Ccedil;\",\"ccedil;\",\"cedil;\",\"cent;\",\"Chi;\",\"chi;\",\"circ;\",\"clubs;\",\"cong;\",\"copy;\",\"crarr;\",\"cup;\",\"curren;\",\"Dagger;\",\"dagger;\",\"dArr;\",\"darr;\",\"deg;\",\"Delta;\",\"delta;\",\"diams;\",\"divide;\",\"Eacute;\",\"eacute;\",\"Ecirc;\",\"ecirc;\",\"Egrave;\",\"egrave;\",\"empty;\",\"emsp;\",\"ensp;\",\"Epsilon;\",\"epsilon;\",\"equiv;\",\"Eta;\",\"eta;\",\"ETH;\",\"eth;\",\"Euml;\",\"euml;\",\"euro;\",\"exist;\",\"fnof;\",\"forall;\",\"frac12;\",\"frac14;\",\"frac34;\",\"frasl;\",\"Gamma;\",\"gamma;\",\"ge;\",\"gt;\",\"hArr;\",\"harr;\",\"hearts;\",\"hellip;\",\"Iacute;\",\"iacute;\",\"Icirc;\",\"icirc;\",\"iexcl;\",\"Igrave;\",\"igrave;\",\"image;\",\"infin;\",\"int;\",\"Iota;\",\"iota;\",\"iquest;\",\"isin;\",\"Iuml;\",\"iuml;\",\"Kappa;\",\"kappa;\",\"Lambda;\",\"lambda;\",\"lang;\",\"laquo;\",\"lArr;\",\"larr;\",\"lceil;\",\"ldquo;\",\"le;\",\"lfloor;\",\"lowast;\",\"loz;\",\"lrm;\",\"lsaquo;\",\"lsquo;\",\"lt;\",\"macr;\",\"mdash;\",\"micro;\",\"middot;\",\"minus;\",\"Mu;\",\"mu;\",\"nabla;\",\"nbsp;\",\"ndash;\",\"ne;\",\"ni;\",\"not;\",\"notin;\",\"nsub;\",\"Ntilde;\",\"ntilde;\",\"Nu;\",\"nu;\",\"Oacute;\",\"oacute;\",\"Ocirc;\",\"ocirc;\",\"OElig;\",\"oelig;\",\"Ograve;\",\"ograve;\",\"oline;\",\"Omega;\",\"omega;\",\"Omicron;\",\"omicron;\",\"oplus;\",\"or;\",\"ordf;\",\"ordm;\",\"Oslash;\",\"oslash;\",\"Otilde;\",\"otilde;\",\"otimes;\",\"Ouml;\",\"ouml;\",\"para;\",\"part;\",\"permil;\",\"perp;\",\"Phi;\",\"phi;\",\"Pi;\",\"pi;\",\"piv;\",\"plusmn;\",\"pound;\",\"Prime;\",\"prime;\",\"prod;\",\"prop;\",\"Psi;\",\"psi;\",\"quot;\",\"radic;\",\"rang;\",\"raquo;\",\"rArr;\",\"rarr;\",\"rceil;\",\"rdquo;\",\"real;\",\"reg;\",\"rfloor;\",\"Rho;\",\"rho;\",\"rlm;\",\"rsaquo;\",\"rsquo;\",\"sbquo;\",\"Scaron;\",\"scaron;\",\"sdot;\",\"sect;\",\"shy;\",\"Sigma;\",\"sigma;\",\"sigmaf;\",\"sim;\",\"spades;\",\"sub;\",\"sube;\",\"sum;\",\"sup;\",\"sup1;\",\"sup2;\",\"sup3;\",\"supe;\",\"szlig;\",\"Tau;\",\"tau;\",\"there4;\",\"Theta;\",\"theta;\",\"thetasym;\",\"thinsp;\",\"THORN;\",\"thorn;\",\"tilde;\",\"times;\",\"trade;\",\"Uacute;\",\"uacute;\",\"uArr;\",\"uarr;\",\"Ucirc;\",\"ucirc;\",\"Ugrave;\",\"ugrave;\",\"uml;\",\"upsih;\",\"Upsilon;\",\"upsilon;\",\"Uuml;\",\"uuml;\",\"weierp;\",\"Xi;\",\"xi;\",\"Yacute;\",\"yacute;\",\"yen;\",\"Yuml;\",\"yuml;\",\"Zeta;\",\"zeta;\",\"zwj;\",\"zwnj;\"];return i.map(function(e){return{caption:e,snippet:e,meta:\"html entity\",score:Number.MAX_VALUE}})}}).call(h.prototype),t.HtmlCompletions=h}),define(\"ace/mode/html\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text\",\"ace/mode/javascript\",\"ace/mode/css\",\"ace/mode/html_highlight_rules\",\"ace/mode/behaviour/xml\",\"ace/mode/folding/html\",\"ace/mode/html_completions\",\"ace/worker/worker_client\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text\").Mode,o=e(\"./javascript\").Mode,u=e(\"./css\").Mode,a=e(\"./html_highlight_rules\").HtmlHighlightRules,f=e(\"./behaviour/xml\").XmlBehaviour,l=e(\"./folding/html\").FoldMode,c=e(\"./html_completions\").HtmlCompletions,h=e(\"../worker/worker_client\").WorkerClient,p=[\"area\",\"base\",\"br\",\"col\",\"embed\",\"hr\",\"img\",\"input\",\"keygen\",\"link\",\"meta\",\"menuitem\",\"param\",\"source\",\"track\",\"wbr\"],d=[\"li\",\"dt\",\"dd\",\"p\",\"rt\",\"rp\",\"optgroup\",\"option\",\"colgroup\",\"td\",\"th\"],v=function(e){this.fragmentContext=e&&e.fragmentContext,this.HighlightRules=a,this.$behaviour=new f,this.$completer=new c,this.createModeDelegates({\"js-\":o,\"css-\":u}),this.foldingRules=new l(this.voidElements,i.arrayToMap(d))};r.inherits(v,s),function(){this.blockComment={start:\"<!--\",end:\"-->\"},this.voidElements=i.arrayToMap(p),this.getNextLineIndent=function(e,t,n){return this.$getIndent(t)},this.checkOutdent=function(e,t,n){return!1},this.getCompletions=function(e,t,n,r){return this.$completer.getCompletions(e,t,n,r)},this.createWorker=function(e){if(this.constructor!=v)return;var t=new h([\"ace\"],\"ace/mode/html_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),this.fragmentContext&&t.call(\"setOptions\",[{context:this.fragmentContext}]),t.on(\"error\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/html\"}.call(v.prototype),t.Mode=v}),define(\"ace/mode/markdown_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text_highlight_rules\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/xml_highlight_rules\",\"ace/mode/html_highlight_rules\",\"ace/mode/css_highlight_rules\"],function(e,t,n){\"use strict\";function c(e,t){return{token:\"support.function\",regex:\"^\\\\s*```\"+e+\"\\\\s*$\",push:t+\"start\"}}var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text_highlight_rules\").TextHighlightRules,o=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,u=e(\"./xml_highlight_rules\").XmlHighlightRules,a=e(\"./html_highlight_rules\").HtmlHighlightRules,f=e(\"./css_highlight_rules\").CssHighlightRules,l=function(e){return\"(?:[^\"+i.escapeRegExp(e)+\"\\\\\\\\]|\\\\\\\\.)*\"},h=function(){a.call(this),this.$rules.start.unshift({token:\"empty_line\",regex:\"^$\",next:\"allowBlock\"},{token:\"markup.heading.1\",regex:\"^=+(?=\\\\s*$)\"},{token:\"markup.heading.2\",regex:\"^\\\\-+(?=\\\\s*$)\"},{token:function(e){return\"markup.heading.\"+e.length},regex:/^#{1,6}(?=\\s*[^ #]|\\s+#.)/,next:\"header\"},c(\"(?:javascript|js)\",\"jscode-\"),c(\"xml\",\"xmlcode-\"),c(\"html\",\"htmlcode-\"),c(\"css\",\"csscode-\"),{token:\"support.function\",regex:\"^\\\\s*```\\\\s*\\\\S*(?:{.*?\\\\})?\\\\s*$\",next:\"githubblock\"},{token:\"string.blockquote\",regex:\"^\\\\s*>\\\\s*(?:[*+-]|\\\\d+\\\\.)?\\\\s+\",next:\"blockquote\"},{token:\"constant\",regex:\"^ {0,2}(?:(?: ?\\\\* ?){3,}|(?: ?\\\\- ?){3,}|(?: ?\\\\_ ?){3,})\\\\s*$\",next:\"allowBlock\"},{token:\"markup.list\",regex:\"^\\\\s{0,3}(?:[*+-]|\\\\d+\\\\.)\\\\s+\",next:\"listblock-start\"},{include:\"basic\"}),this.addRules({basic:[{token:\"constant.language.escape\",regex:/\\\\[\\\\`*_{}\\[\\]()#+\\-.!]/},{token:\"support.function\",regex:\"(`+)(.*?[^`])(\\\\1)\"},{token:[\"text\",\"constant\",\"text\",\"url\",\"string\",\"text\"],regex:'^([ ]{0,3}\\\\[)([^\\\\]]+)(\\\\]:\\\\s*)([^ ]+)(\\\\s*(?:[\"][^\"]+[\"])?(\\\\s*))$'},{token:[\"text\",\"string\",\"text\",\"constant\",\"text\"],regex:\"(\\\\[)(\"+l(\"]\")+\")(\\\\]\\\\s*\\\\[)(\"+l(\"]\")+\")(\\\\])\"},{token:[\"text\",\"string\",\"text\",\"markup.underline\",\"string\",\"text\"],regex:\"(\\\\[)(\"+l(\"]\")+\")(\\\\]\\\\()\"+'((?:[^\\\\)\\\\s\\\\\\\\]|\\\\\\\\.|\\\\s(?=[^\"]))*)'+'(\\\\s*\"'+l('\"')+'\"\\\\s*)?'+\"(\\\\))\"},{token:\"string.strong\",regex:\"([*]{2}|[_]{2}(?=\\\\S))(.*?\\\\S[*_]*)(\\\\1)\"},{token:\"string.emphasis\",regex:\"([*]|[_](?=\\\\S))(.*?\\\\S[*_]*)(\\\\1)\"},{token:[\"text\",\"url\",\"text\"],regex:\"(<)((?:https?|ftp|dict):[^'\\\">\\\\s]+|(?:mailto:)?[-.\\\\w]+\\\\@[-a-z0-9]+(?:\\\\.[-a-z0-9]+)*\\\\.[a-z]+)(>)\"}],allowBlock:[{token:\"support.function\",regex:\"^ {4}.+\",next:\"allowBlock\"},{token:\"empty_line\",regex:\"^$\",next:\"allowBlock\"},{token:\"empty\",regex:\"\",next:\"start\"}],header:[{regex:\"$\",next:\"start\"},{include:\"basic\"},{defaultToken:\"heading\"}],\"listblock-start\":[{token:\"support.variable\",regex:/(?:\\[[ x]\\])?/,next:\"listblock\"}],listblock:[{token:\"empty_line\",regex:\"^$\",next:\"start\"},{token:\"markup.list\",regex:\"^\\\\s{0,3}(?:[*+-]|\\\\d+\\\\.)\\\\s+\",next:\"listblock-start\"},{include:\"basic\",noEscape:!0},{token:\"support.function\",regex:\"^\\\\s*```\\\\s*[a-zA-Z]*(?:{.*?\\\\})?\\\\s*$\",next:\"githubblock\"},{defaultToken:\"list\"}],blockquote:[{token:\"empty_line\",regex:\"^\\\\s*$\",next:\"start\"},{token:\"string.blockquote\",regex:\"^\\\\s*>\\\\s*(?:[*+-]|\\\\d+\\\\.)?\\\\s+\",next:\"blockquote\"},{include:\"basic\",noEscape:!0},{defaultToken:\"string.blockquote\"}],githubblock:[{token:\"support.function\",regex:\"^\\\\s*```\",next:\"start\"},{token:\"support.function\",regex:\".+\"}]}),this.embedRules(o,\"jscode-\",[{token:\"support.function\",regex:\"^\\\\s*```\",next:\"pop\"}]),this.embedRules(a,\"htmlcode-\",[{token:\"support.function\",regex:\"^\\\\s*```\",next:\"pop\"}]),this.embedRules(f,\"csscode-\",[{token:\"support.function\",regex:\"^\\\\s*```\",next:\"pop\"}]),this.embedRules(u,\"xmlcode-\",[{token:\"support.function\",regex:\"^\\\\s*```\",next:\"pop\"}]),this.normalizeRules()};r.inherits(h,s),t.MarkdownHighlightRules=h}),define(\"ace/mode/folding/markdown\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=e(\"../../range\").Range,o=t.FoldMode=function(){};r.inherits(o,i),function(){this.foldingStartMarker=/^(?:[=-]+\\s*$|#{1,6} |`{3})/,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);return this.foldingStartMarker.test(r)?r[0]==\"`\"?e.bgTokenizer.getState(n)==\"start\"?\"end\":\"start\":\"start\":\"\"},this.getFoldWidgetRange=function(e,t,n){function l(t){return f=e.getTokens(t)[0],f&&f.type.lastIndexOf(c,0)===0}function h(){var e=f.value[0];return e==\"=\"?6:e==\"-\"?5:7-f.value.search(/[^#]/)}var r=e.getLine(n),i=r.length,o=e.getLength(),u=n,a=n;if(!r.match(this.foldingStartMarker))return;if(r[0]==\"`\"){if(e.bgTokenizer.getState(n)!==\"start\"){while(++n<o){r=e.getLine(n);if(r[0]==\"`\"&r.substring(0,3)==\"```\")break}return new s(u,i,n,0)}while(n-->0){r=e.getLine(n);if(r[0]==\"`\"&r.substring(0,3)==\"```\")break}return new s(n,r.length,u,0)}var f,c=\"markup.heading\";if(l(n)){var p=h();while(++n<o){if(!l(n))continue;var d=h();if(d>=p)break}a=n-(!f||[\"=\",\"-\"].indexOf(f.value[0])==-1?1:2);if(a>u)while(a>u&&/^\\s*$/.test(e.getLine(a)))a--;if(a>u){var v=e.getLine(a).length;return new s(u,i,a,v)}}}}.call(o.prototype)}),define(\"ace/mode/markdown\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/javascript\",\"ace/mode/xml\",\"ace/mode/html\",\"ace/mode/markdown_highlight_rules\",\"ace/mode/folding/markdown\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./javascript\").Mode,o=e(\"./xml\").Mode,u=e(\"./html\").Mode,a=e(\"./markdown_highlight_rules\").MarkdownHighlightRules,f=e(\"./folding/markdown\").FoldMode,l=function(){this.HighlightRules=a,this.createModeDelegates({\"js-\":s,\"xml-\":o,\"html-\":u}),this.foldingRules=new f,this.$behaviour=this.$defaultBehaviour};r.inherits(l,i),function(){this.type=\"text\",this.blockComment={start:\"<!--\",end:\"-->\"},this.getNextLineIndent=function(e,t,n){if(e==\"listblock\"){var r=/^(\\s*)(?:([-+*])|(\\d+)\\.)(\\s+)/.exec(t);if(!r)return\"\";var i=r[2];return i||(i=parseInt(r[3],10)+1+\".\"),r[1]+i+r[4]}return this.$getIndent(t)},this.$id=\"ace/mode/markdown\"}.call(l.prototype),t.Mode=l})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-mysql.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/mysql_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,o=e(\"./text_highlight_rules\").TextHighlightRules,u=function(){function i(e){var t=e.start,n=e.escape;return{token:\"string.start\",regex:t,next:[{token:\"constant.language.escape\",regex:n},{token:\"string.end\",next:\"start\",regex:t},{defaultToken:\"string\"}]}}var e=\"alter|and|as|asc|between|count|create|delete|desc|distinct|drop|from|having|in|insert|into|is|join|like|not|on|or|order|select|set|table|union|update|values|where|accessible|action|add|after|algorithm|all|analyze|asensitive|at|authors|auto_increment|autocommit|avg|avg_row_length|before|binary|binlog|both|btree|cache|call|cascade|cascaded|case|catalog_name|chain|change|changed|character|check|checkpoint|checksum|class_origin|client_statistics|close|coalesce|code|collate|collation|collations|column|columns|comment|commit|committed|completion|concurrent|condition|connection|consistent|constraint|contains|continue|contributors|convert|cross|current_date|current_time|current_timestamp|current_user|cursor|data|database|databases|day_hour|day_microsecond|day_minute|day_second|deallocate|dec|declare|default|delay_key_write|delayed|delimiter|des_key_file|describe|deterministic|dev_pop|dev_samp|deviance|directory|disable|discard|distinctrow|div|dual|dumpfile|each|elseif|enable|enclosed|end|ends|engine|engines|enum|errors|escape|escaped|even|event|events|every|execute|exists|exit|explain|extended|fast|fetch|field|fields|first|flush|for|force|foreign|found_rows|full|fulltext|function|general|global|grant|grants|group|groupby_concat|handler|hash|help|high_priority|hosts|hour_microsecond|hour_minute|hour_second|if|ignore|ignore_server_ids|import|index|index_statistics|infile|inner|innodb|inout|insensitive|insert_method|install|interval|invoker|isolation|iterate|key|keys|kill|language|last|leading|leave|left|level|limit|linear|lines|list|load|local|localtime|localtimestamp|lock|logs|low_priority|master|master_heartbeat_period|master_ssl_verify_server_cert|masters|match|max|max_rows|maxvalue|message_text|middleint|migrate|min|min_rows|minute_microsecond|minute_second|mod|mode|modifies|modify|mutex|mysql_errno|natural|next|no|no_write_to_binlog|offline|offset|one|online|open|optimize|option|optionally|out|outer|outfile|pack_keys|parser|partition|partitions|password|phase|plugin|plugins|prepare|preserve|prev|primary|privileges|procedure|processlist|profile|profiles|purge|query|quick|range|read|read_write|reads|real|rebuild|recover|references|regexp|relaylog|release|remove|rename|reorganize|repair|repeatable|replace|require|resignal|restrict|resume|return|returns|revoke|right|rlike|rollback|rollup|row|row_format|rtree|savepoint|schedule|schema|schema_name|schemas|second_microsecond|security|sensitive|separator|serializable|server|session|share|show|signal|slave|slow|smallint|snapshot|soname|spatial|specific|sql|sql_big_result|sql_buffer_result|sql_cache|sql_calc_found_rows|sql_no_cache|sql_small_result|sqlexception|sqlstate|sqlwarning|ssl|start|starting|starts|status|std|stddev|stddev_pop|stddev_samp|storage|straight_join|subclass_origin|sum|suspend|table_name|table_statistics|tables|tablespace|temporary|terminated|to|trailing|transaction|trigger|triggers|truncate|uncommitted|undo|uninstall|unique|unlock|upgrade|usage|use|use_frm|user|user_resources|user_statistics|using|utc_date|utc_time|utc_timestamp|value|variables|varying|view|views|warnings|when|while|with|work|write|xa|xor|year_month|zerofill|begin|do|then|else|loop|repeat\",t=\"by|bool|boolean|bit|blob|decimal|double|enum|float|long|longblob|longtext|medium|mediumblob|mediumint|mediumtext|time|timestamp|tinyblob|tinyint|tinytext|text|bigint|int|int1|int2|int3|int4|int8|integer|float|float4|float8|double|char|varbinary|varchar|varcharacter|precision|date|datetime|year|unsigned|signed|numeric|ucase|lcase|mid|len|round|rank|now|format|coalesce|ifnull|isnull|nvl\",n=\"charset|clear|connect|edit|ego|exit|go|help|nopager|notee|nowarning|pager|print|prompt|quit|rehash|source|status|system|tee\",r=this.createKeywordMapper({\"support.function\":t,keyword:e,constant:\"false|true|null|unknown|date|time|timestamp|ODBCdotTable|zerolessFloat\",\"variable.language\":n},\"identifier\",!0);this.$rules={start:[{token:\"comment\",regex:\"(?:-- |#).*$\"},i({start:'\"',escape:/\\\\[0'\"bnrtZ\\\\%_]?/}),i({start:\"'\",escape:/\\\\[0'\"bnrtZ\\\\%_]?/}),s.getStartRule(\"doc-start\"),{token:\"comment\",regex:/\\/\\*/,next:\"comment\"},{token:\"constant.numeric\",regex:/0[xX][0-9a-fA-F]+|[xX]'[0-9a-fA-F]+'|0[bB][01]+|[bB]'[01]+'/},{token:\"constant.numeric\",regex:\"[+-]?\\\\d+(?:(?:\\\\.\\\\d*)?(?:[eE][+-]?\\\\d+)?)?\\\\b\"},{token:r,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"constant.class\",regex:\"@@?[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"constant.buildin\",regex:\"`[^`]*`\"},{token:\"keyword.operator\",regex:\"\\\\+|\\\\-|\\\\/|\\\\/\\\\/|%|<@>|@>|<@|&|\\\\^|~|<|>|<=|=>|==|!=|<>|=\"},{token:\"paren.lparen\",regex:\"[\\\\(]\"},{token:\"paren.rparen\",regex:\"[\\\\)]\"},{token:\"text\",regex:\"\\\\s+\"}],comment:[{token:\"comment\",regex:\"\\\\*\\\\/\",next:\"start\"},{defaultToken:\"comment\"}]},this.embedRules(s,\"doc-\",[s.getEndRule(\"start\")]),this.normalizeRules()};r.inherits(u,o),t.MysqlHighlightRules=u}),define(\"ace/mode/mysql\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/mysql_highlight_rules\"],function(e,t,n){var r=e(\"../lib/oop\"),i=e(\"../mode/text\").Mode,s=e(\"./mysql_highlight_rules\").MysqlHighlightRules,o=function(){this.HighlightRules=s,this.$behaviour=this.$defaultBehaviour};r.inherits(o,i),function(){this.lineCommentStart=[\"--\",\"#\"],this.blockComment={start:\"/*\",end:\"*/\"},this.$id=\"ace/mode/mysql\"}.call(o.prototype),t.Mode=o})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-objectivec.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/c_cpp_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=t.cFunctions=\"\\\\b(?:hypot(?:f|l)?|s(?:scanf|ystem|nprintf|ca(?:nf|lb(?:n(?:f|l)?|ln(?:f|l)?))|i(?:n(?:h(?:f|l)?|f|l)?|gn(?:al|bit))|tr(?:s(?:tr|pn)|nc(?:py|at|mp)|c(?:spn|hr|oll|py|at|mp)|to(?:imax|d|u(?:l(?:l)?|max)|k|f|l(?:d|l)?)|error|pbrk|ftime|len|rchr|xfrm)|printf|et(?:jmp|vbuf|locale|buf)|qrt(?:f|l)?|w(?:scanf|printf)|rand)|n(?:e(?:arbyint(?:f|l)?|xt(?:toward(?:f|l)?|after(?:f|l)?))|an(?:f|l)?)|c(?:s(?:in(?:h(?:f|l)?|f|l)?|qrt(?:f|l)?)|cos(?:h(?:f)?|f|l)?|imag(?:f|l)?|t(?:ime|an(?:h(?:f|l)?|f|l)?)|o(?:s(?:h(?:f|l)?|f|l)?|nj(?:f|l)?|pysign(?:f|l)?)|p(?:ow(?:f|l)?|roj(?:f|l)?)|e(?:il(?:f|l)?|xp(?:f|l)?)|l(?:o(?:ck|g(?:f|l)?)|earerr)|a(?:sin(?:h(?:f|l)?|f|l)?|cos(?:h(?:f|l)?|f|l)?|tan(?:h(?:f|l)?|f|l)?|lloc|rg(?:f|l)?|bs(?:f|l)?)|real(?:f|l)?|brt(?:f|l)?)|t(?:ime|o(?:upper|lower)|an(?:h(?:f|l)?|f|l)?|runc(?:f|l)?|gamma(?:f|l)?|mp(?:nam|file))|i(?:s(?:space|n(?:ormal|an)|cntrl|inf|digit|u(?:nordered|pper)|p(?:unct|rint)|finite|w(?:space|c(?:ntrl|type)|digit|upper|p(?:unct|rint)|lower|al(?:num|pha)|graph|xdigit|blank)|l(?:ower|ess(?:equal|greater)?)|al(?:num|pha)|gr(?:eater(?:equal)?|aph)|xdigit|blank)|logb(?:f|l)?|max(?:div|abs))|di(?:v|fftime)|_Exit|unget(?:c|wc)|p(?:ow(?:f|l)?|ut(?:s|c(?:har)?|wc(?:har)?)|error|rintf)|e(?:rf(?:c(?:f|l)?|f|l)?|x(?:it|p(?:2(?:f|l)?|f|l|m1(?:f|l)?)?))|v(?:s(?:scanf|nprintf|canf|printf|w(?:scanf|printf))|printf|f(?:scanf|printf|w(?:scanf|printf))|w(?:scanf|printf)|a_(?:start|copy|end|arg))|qsort|f(?:s(?:canf|e(?:tpos|ek))|close|tell|open|dim(?:f|l)?|p(?:classify|ut(?:s|c|w(?:s|c))|rintf)|e(?:holdexcept|set(?:e(?:nv|xceptflag)|round)|clearexcept|testexcept|of|updateenv|r(?:aiseexcept|ror)|get(?:e(?:nv|xceptflag)|round))|flush|w(?:scanf|ide|printf|rite)|loor(?:f|l)?|abs(?:f|l)?|get(?:s|c|pos|w(?:s|c))|re(?:open|e|ad|xp(?:f|l)?)|m(?:in(?:f|l)?|od(?:f|l)?|a(?:f|l|x(?:f|l)?)?))|l(?:d(?:iv|exp(?:f|l)?)|o(?:ngjmp|cal(?:time|econv)|g(?:1(?:p(?:f|l)?|0(?:f|l)?)|2(?:f|l)?|f|l|b(?:f|l)?)?)|abs|l(?:div|abs|r(?:int(?:f|l)?|ound(?:f|l)?))|r(?:int(?:f|l)?|ound(?:f|l)?)|gamma(?:f|l)?)|w(?:scanf|c(?:s(?:s(?:tr|pn)|nc(?:py|at|mp)|c(?:spn|hr|oll|py|at|mp)|to(?:imax|d|u(?:l(?:l)?|max)|k|f|l(?:d|l)?|mbs)|pbrk|ftime|len|r(?:chr|tombs)|xfrm)|to(?:b|mb)|rtomb)|printf|mem(?:set|c(?:hr|py|mp)|move))|a(?:s(?:sert|ctime|in(?:h(?:f|l)?|f|l)?)|cos(?:h(?:f|l)?|f|l)?|t(?:o(?:i|f|l(?:l)?)|exit|an(?:h(?:f|l)?|2(?:f|l)?|f|l)?)|b(?:s|ort))|g(?:et(?:s|c(?:har)?|env|wc(?:har)?)|mtime)|r(?:int(?:f|l)?|ound(?:f|l)?|e(?:name|alloc|wind|m(?:ove|quo(?:f|l)?|ainder(?:f|l)?))|a(?:nd|ise))|b(?:search|towc)|m(?:odf(?:f|l)?|em(?:set|c(?:hr|py|mp)|move)|ktime|alloc|b(?:s(?:init|towcs|rtowcs)|towc|len|r(?:towc|len))))\\\\b\",u=function(){var e=\"break|case|continue|default|do|else|for|goto|if|_Pragma|return|switch|while|catch|operator|try|throw|using\",t=\"asm|__asm__|auto|bool|_Bool|char|_Complex|double|enum|float|_Imaginary|int|long|short|signed|struct|typedef|union|unsigned|void|class|wchar_t|template|char16_t|char32_t\",n=\"const|extern|register|restrict|static|volatile|inline|private|protected|public|friend|explicit|virtual|export|mutable|typename|constexpr|new|delete|alignas|alignof|decltype|noexcept|thread_local\",r=\"and|and_eq|bitand|bitor|compl|not|not_eq|or|or_eq|typeid|xor|xor_eqconst_cast|dynamic_cast|reinterpret_cast|static_cast|sizeof|namespace\",s=\"NULL|true|false|TRUE|FALSE|nullptr\",u=this.$keywords=this.createKeywordMapper({\"keyword.control\":e,\"storage.type\":t,\"storage.modifier\":n,\"keyword.operator\":r,\"variable.language\":\"this\",\"constant.language\":s},\"identifier\"),a=\"[a-zA-Z\\\\$_\\u00a1-\\uffff][a-zA-Z\\\\d\\\\$_\\u00a1-\\uffff]*\\\\b\",f=/\\\\(?:['\"?\\\\abfnrtv]|[0-7]{1,3}|x[a-fA-F\\d]{2}|u[a-fA-F\\d]{4}U[a-fA-F\\d]{8}|.)/.source;this.$rules={start:[{token:\"comment\",regex:\"//$\",next:\"start\"},{token:\"comment\",regex:\"//\",next:\"singleLineComment\"},i.getStartRule(\"doc-start\"),{token:\"comment\",regex:\"\\\\/\\\\*\",next:\"comment\"},{token:\"string\",regex:\"'(?:\"+f+\"|.)?'\"},{token:\"string.start\",regex:'\"',stateName:\"qqstring\",next:[{token:\"string\",regex:/\\\\\\s*$/,next:\"qqstring\"},{token:\"constant.language.escape\",regex:f},{token:\"constant.language.escape\",regex:/%[^'\"\\\\]/},{token:\"string.end\",regex:'\"|$',next:\"start\"},{defaultToken:\"string\"}]},{token:\"string.start\",regex:'R\"\\\\(',stateName:\"rawString\",next:[{token:\"string.end\",regex:'\\\\)\"',next:\"start\"},{defaultToken:\"string\"}]},{token:\"constant.numeric\",regex:\"0[xX][0-9a-fA-F]+(L|l|UL|ul|u|U|F|f|ll|LL|ull|ULL)?\\\\b\"},{token:\"constant.numeric\",regex:\"[+-]?\\\\d+(?:(?:\\\\.\\\\d*)?(?:[eE][+-]?\\\\d+)?)?(L|l|UL|ul|u|U|F|f|ll|LL|ull|ULL)?\\\\b\"},{token:\"keyword\",regex:\"#\\\\s*(?:include|import|pragma|line|define|undef)\\\\b\",next:\"directive\"},{token:\"keyword\",regex:\"#\\\\s*(?:endif|if|ifdef|else|elif|ifndef)\\\\b\"},{token:\"support.function.C99.c\",regex:o},{token:u,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\"},{token:\"keyword.operator\",regex:/--|\\+\\+|<<=|>>=|>>>=|<>|&&|\\|\\||\\?:|[*%\\/+\\-&\\^|~!<>=]=?/},{token:\"punctuation.operator\",regex:\"\\\\?|\\\\:|\\\\,|\\\\;|\\\\.\"},{token:\"paren.lparen\",regex:\"[[({]\"},{token:\"paren.rparen\",regex:\"[\\\\])}]\"},{token:\"text\",regex:\"\\\\s+\"}],comment:[{token:\"comment\",regex:\".*?\\\\*\\\\/\",next:\"start\"},{token:\"comment\",regex:\".+\"}],singleLineComment:[{token:\"comment\",regex:/\\\\$/,next:\"singleLineComment\"},{token:\"comment\",regex:/$/,next:\"start\"},{defaultToken:\"comment\"}],directive:[{token:\"constant.other.multiline\",regex:/\\\\/},{token:\"constant.other.multiline\",regex:/.*\\\\/},{token:\"constant.other\",regex:\"\\\\s*<.+?>\",next:\"start\"},{token:\"constant.other\",regex:'\\\\s*[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]',next:\"start\"},{token:\"constant.other\",regex:\"\\\\s*['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\",next:\"start\"},{token:\"constant.other\",regex:/[^\\\\\\/]+/,next:\"start\"}]},this.embedRules(i,\"doc-\",[i.getEndRule(\"start\")]),this.normalizeRules()};r.inherits(u,s),t.c_cppHighlightRules=u}),define(\"ace/mode/objectivec_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/c_cpp_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./c_cpp_highlight_rules\"),o=s.c_cppHighlightRules,u=function(){var e=\"\\\\\\\\(?:[abefnrtv'\\\"?\\\\\\\\]|[0-3]\\\\d{1,2}|[4-7]\\\\d?|222|x[a-zA-Z0-9]+)\",t=[{regex:\"\\\\b_cmd\\\\b\",token:\"variable.other.selector.objc\"},{regex:\"\\\\b(?:self|super)\\\\b\",token:\"variable.language.objc\"}],n=new o,r=n.getRules();this.$rules={start:[{token:\"comment\",regex:\"\\\\/\\\\/.*$\"},i.getStartRule(\"doc-start\"),{token:\"comment\",regex:\"\\\\/\\\\*\",next:\"comment\"},{token:[\"storage.type.objc\",\"punctuation.definition.storage.type.objc\",\"entity.name.type.objc\",\"text\",\"entity.other.inherited-class.objc\"],regex:\"(@)(interface|protocol)(?!.+;)(\\\\s+[A-Za-z_][A-Za-z0-9_]*)(\\\\s*:\\\\s*)([A-Za-z]+)\"},{token:[\"storage.type.objc\"],regex:\"(@end)\"},{token:[\"storage.type.objc\",\"entity.name.type.objc\",\"entity.other.inherited-class.objc\"],regex:\"(@implementation)(\\\\s+[A-Za-z_][A-Za-z0-9_]*)(\\\\s*?::\\\\s*(?:[A-Za-z][A-Za-z0-9]*))?\"},{token:\"string.begin.objc\",regex:'@\"',next:\"constant_NSString\"},{token:\"storage.type.objc\",regex:\"\\\\bid\\\\s*<\",next:\"protocol_list\"},{token:\"keyword.control.macro.objc\",regex:\"\\\\bNS_DURING|NS_HANDLER|NS_ENDHANDLER\\\\b\"},{token:[\"punctuation.definition.keyword.objc\",\"keyword.control.exception.objc\"],regex:\"(@)(try|catch|finally|throw)\\\\b\"},{token:[\"punctuation.definition.keyword.objc\",\"keyword.other.objc\"],regex:\"(@)(defs|encode)\\\\b\"},{token:[\"storage.type.id.objc\",\"text\"],regex:\"(\\\\bid\\\\b)(\\\\s|\\\\n)?\"},{token:\"storage.type.objc\",regex:\"\\\\bIBOutlet|IBAction|BOOL|SEL|id|unichar|IMP|Class\\\\b\"},{token:[\"punctuation.definition.storage.type.objc\",\"storage.type.objc\"],regex:\"(@)(class|protocol)\\\\b\"},{token:[\"punctuation.definition.storage.type.objc\",\"punctuation\"],regex:\"(@selector)(\\\\s*\\\\()\",next:\"selectors\"},{token:[\"punctuation.definition.storage.modifier.objc\",\"storage.modifier.objc\"],regex:\"(@)(synchronized|public|private|protected|package)\\\\b\"},{token:\"constant.language.objc\",regex:\"\\\\bYES|NO|Nil|nil\\\\b\"},{token:\"support.variable.foundation\",regex:\"\\\\bNSApp\\\\b\"},{token:[\"support.function.cocoa.leopard\"],regex:\"(?:\\\\b)(NS(?:Rect(?:ToCGRect|FromCGRect)|MakeCollectable|S(?:tringFromProtocol|ize(?:ToCGSize|FromCGSize))|Draw(?:NinePartImage|ThreePartImage)|P(?:oint(?:ToCGPoint|FromCGPoint)|rotocolFromString)|EventMaskFromType|Value))(?:\\\\b)\"},{token:[\"support.function.cocoa\"],regex:\"(?:\\\\b)(NS(?:R(?:ound(?:DownToMultipleOfPageSize|UpToMultipleOfPageSize)|un(?:CriticalAlertPanel(?:RelativeToWindow)?|InformationalAlertPanel(?:RelativeToWindow)?|AlertPanel(?:RelativeToWindow)?)|e(?:set(?:MapTable|HashTable)|c(?:ycleZone|t(?:Clip(?:List)?|F(?:ill(?:UsingOperation|List(?:UsingOperation|With(?:Grays|Colors(?:UsingOperation)?))?)?|romString))|ordAllocationEvent)|turnAddress|leaseAlertPanel|a(?:dPixel|l(?:MemoryAvailable|locateCollectable))|gisterServicesProvider)|angeFromString)|Get(?:SizeAndAlignment|CriticalAlertPanel|InformationalAlertPanel|UncaughtExceptionHandler|FileType(?:s)?|WindowServerMemory|AlertPanel)|M(?:i(?:n(?:X|Y)|d(?:X|Y))|ouseInRect|a(?:p(?:Remove|Get|Member|Insert(?:IfAbsent|KnownAbsent)?)|ke(?:R(?:ect|ange)|Size|Point)|x(?:Range|X|Y)))|B(?:itsPer(?:SampleFromDepth|PixelFromDepth)|e(?:stDepth|ep|gin(?:CriticalAlertSheet|InformationalAlertSheet|AlertSheet)))|S(?:ho(?:uldRetainWithZone|w(?:sServicesMenuItem|AnimationEffect))|tringFrom(?:R(?:ect|ange)|MapTable|S(?:ize|elector)|HashTable|Class|Point)|izeFromString|e(?:t(?:ShowsServicesMenuItem|ZoneName|UncaughtExceptionHandler|FocusRingStyle)|lectorFromString|archPathForDirectoriesInDomains)|wap(?:Big(?:ShortToHost|IntToHost|DoubleToHost|FloatToHost|Long(?:ToHost|LongToHost))|Short|Host(?:ShortTo(?:Big|Little)|IntTo(?:Big|Little)|DoubleTo(?:Big|Little)|FloatTo(?:Big|Little)|Long(?:To(?:Big|Little)|LongTo(?:Big|Little)))|Int|Double|Float|L(?:ittle(?:ShortToHost|IntToHost|DoubleToHost|FloatToHost|Long(?:ToHost|LongToHost))|ong(?:Long)?)))|H(?:ighlightRect|o(?:stByteOrder|meDirectory(?:ForUser)?)|eight|ash(?:Remove|Get|Insert(?:IfAbsent|KnownAbsent)?)|FSType(?:CodeFromFileType|OfFile))|N(?:umberOfColorComponents|ext(?:MapEnumeratorPair|HashEnumeratorItem))|C(?:o(?:n(?:tainsRect|vert(?:GlyphsToPackedGlyphs|Swapped(?:DoubleToHost|FloatToHost)|Host(?:DoubleToSwapped|FloatToSwapped)))|unt(?:MapTable|HashTable|Frames|Windows(?:ForContext)?)|py(?:M(?:emoryPages|apTableWithZone)|Bits|HashTableWithZone|Object)|lorSpaceFromDepth|mpare(?:MapTables|HashTables))|lassFromString|reate(?:MapTable(?:WithZone)?|HashTable(?:WithZone)?|Zone|File(?:namePboardType|ContentsPboardType)))|TemporaryDirectory|I(?:s(?:ControllerMarker|EmptyRect|FreedObject)|n(?:setRect|crementExtraRefCount|te(?:r(?:sect(?:sRect|ionR(?:ect|ange))|faceStyleForKey)|gralRect)))|Zone(?:Realloc|Malloc|Name|Calloc|Fr(?:omPointer|ee))|O(?:penStepRootDirectory|ffsetRect)|D(?:i(?:sableScreenUpdates|videRect)|ottedFrameRect|e(?:c(?:imal(?:Round|Multiply|S(?:tring|ubtract)|Normalize|Co(?:py|mpa(?:ct|re))|IsNotANumber|Divide|Power|Add)|rementExtraRefCountWasZero)|faultMallocZone|allocate(?:MemoryPages|Object))|raw(?:Gr(?:oove|ayBezel)|B(?:itmap|utton)|ColorTiledRects|TiledRects|DarkBezel|W(?:hiteBezel|indowBackground)|LightBezel))|U(?:serName|n(?:ionR(?:ect|ange)|registerServicesProvider)|pdateDynamicServices)|Java(?:Bundle(?:Setup|Cleanup)|Setup(?:VirtualMachine)?|Needs(?:ToLoadClasses|VirtualMachine)|ClassesF(?:orBundle|romPath)|ObjectNamedInPath|ProvidesClasses)|P(?:oint(?:InRect|FromString)|erformService|lanarFromDepth|ageSize)|E(?:n(?:d(?:MapTableEnumeration|HashTableEnumeration)|umerate(?:MapTable|HashTable)|ableScreenUpdates)|qual(?:R(?:ects|anges)|Sizes|Points)|raseRect|xtraRefCount)|F(?:ileTypeForHFSTypeCode|ullUserName|r(?:ee(?:MapTable|HashTable)|ame(?:Rect(?:WithWidth(?:UsingOperation)?)?|Address)))|Wi(?:ndowList(?:ForContext)?|dth)|Lo(?:cationInRange|g(?:v|PageSize)?)|A(?:ccessibility(?:R(?:oleDescription(?:ForUIElement)?|aiseBadArgumentException)|Unignored(?:Children(?:ForOnlyChild)?|Descendant|Ancestor)|PostNotification|ActionDescription)|pplication(?:Main|Load)|vailableWindowDepths|ll(?:MapTable(?:Values|Keys)|HashTableObjects|ocate(?:MemoryPages|Collectable|Object)))))(?:\\\\b)\"},{token:[\"support.class.cocoa.leopard\"],regex:\"(?:\\\\b)(NS(?:RuleEditor|G(?:arbageCollector|radient)|MapTable|HashTable|Co(?:ndition|llectionView(?:Item)?)|T(?:oolbarItemGroup|extInputClient|r(?:eeNode|ackingArea))|InvocationOperation|Operation(?:Queue)?|D(?:ictionaryController|ockTile)|P(?:ointer(?:Functions|Array)|athC(?:o(?:ntrol(?:Delegate)?|mponentCell)|ell(?:Delegate)?)|r(?:intPanelAccessorizing|edicateEditor(?:RowTemplate)?))|ViewController|FastEnumeration|Animat(?:ionContext|ablePropertyContainer)))(?:\\\\b)\"},{token:[\"support.class.cocoa\"],regex:\"(?:\\\\b)(NS(?:R(?:u(?:nLoop|ler(?:Marker|View))|e(?:sponder|cursiveLock|lativeSpecifier)|an(?:domSpecifier|geSpecifier))|G(?:etCommand|lyph(?:Generator|Storage|Info)|raphicsContext)|XML(?:Node|D(?:ocument|TD(?:Node)?)|Parser|Element)|M(?:iddleSpecifier|ov(?:ie(?:View)?|eCommand)|utable(?:S(?:tring|et)|C(?:haracterSet|opying)|IndexSet|D(?:ictionary|ata)|URLRequest|ParagraphStyle|A(?:ttributedString|rray))|e(?:ssagePort(?:NameServer)?|nu(?:Item(?:Cell)?|View)?|t(?:hodSignature|adata(?:Item|Query(?:ResultGroup|AttributeValueTuple)?)))|a(?:ch(?:BootstrapServer|Port)|trix))|B(?:itmapImageRep|ox|u(?:ndle|tton(?:Cell)?)|ezierPath|rowser(?:Cell)?)|S(?:hadow|c(?:anner|r(?:ipt(?:SuiteRegistry|C(?:o(?:ercionHandler|mmand(?:Description)?)|lassDescription)|ObjectSpecifier|ExecutionContext|WhoseTest)|oll(?:er|View)|een))|t(?:epper(?:Cell)?|atus(?:Bar|Item)|r(?:ing|eam))|imple(?:HorizontalTypesetter|CString)|o(?:cketPort(?:NameServer)?|und|rtDescriptor)|p(?:e(?:cifierTest|ech(?:Recognizer|Synthesizer)|ll(?:Server|Checker))|litView)|e(?:cureTextField(?:Cell)?|t(?:Command)?|archField(?:Cell)?|rializer|gmentedC(?:ontrol|ell))|lider(?:Cell)?|avePanel)|H(?:ost|TTP(?:Cookie(?:Storage)?|URLResponse)|elpManager)|N(?:ib(?:Con(?:nector|trolConnector)|OutletConnector)?|otification(?:Center|Queue)?|u(?:ll|mber(?:Formatter)?)|etService(?:Browser)?|ameSpecifier)|C(?:ha(?:ngeSpelling|racterSet)|o(?:n(?:stantString|nection|trol(?:ler)?|ditionLock)|d(?:ing|er)|unt(?:Command|edSet)|pying|lor(?:Space|P(?:ick(?:ing(?:Custom|Default)|er)|anel)|Well|List)?|m(?:p(?:oundPredicate|arisonPredicate)|boBox(?:Cell)?))|u(?:stomImageRep|rsor)|IImageRep|ell|l(?:ipView|o(?:seCommand|neCommand)|assDescription)|a(?:ched(?:ImageRep|URLResponse)|lendar(?:Date)?)|reateCommand)|T(?:hread|ypesetter|ime(?:Zone|r)|o(?:olbar(?:Item(?:Validations)?)?|kenField(?:Cell)?)|ext(?:Block|Storage|Container|Tab(?:le(?:Block)?)?|Input|View|Field(?:Cell)?|List|Attachment(?:Cell)?)?|a(?:sk|b(?:le(?:Header(?:Cell|View)|Column|View)|View(?:Item)?))|reeController)|I(?:n(?:dex(?:S(?:pecifier|et)|Path)|put(?:Manager|S(?:tream|erv(?:iceProvider|er(?:MouseTracker)?)))|vocation)|gnoreMisspelledWords|mage(?:Rep|Cell|View)?)|O(?:ut(?:putStream|lineView)|pen(?:GL(?:Context|Pixel(?:Buffer|Format)|View)|Panel)|bj(?:CTypeSerializationCallBack|ect(?:Controller)?))|D(?:i(?:st(?:antObject(?:Request)?|ributed(?:NotificationCenter|Lock))|ctionary|rectoryEnumerator)|ocument(?:Controller)?|e(?:serializer|cimalNumber(?:Behaviors|Handler)?|leteCommand)|at(?:e(?:Components|Picker(?:Cell)?|Formatter)?|a)|ra(?:wer|ggingInfo))|U(?:ser(?:InterfaceValidations|Defaults(?:Controller)?)|RL(?:Re(?:sponse|quest)|Handle(?:Client)?|C(?:onnection|ache|redential(?:Storage)?)|Download(?:Delegate)?|Prot(?:ocol(?:Client)?|ectionSpace)|AuthenticationChallenge(?:Sender)?)?|n(?:iqueIDSpecifier|doManager|archiver))|P(?:ipe|o(?:sitionalSpecifier|pUpButton(?:Cell)?|rt(?:Message|NameServer|Coder)?)|ICTImageRep|ersistentDocument|DFImageRep|a(?:steboard|nel|ragraphStyle|geLayout)|r(?:int(?:Info|er|Operation|Panel)|o(?:cessInfo|tocolChecker|perty(?:Specifier|ListSerialization)|gressIndicator|xy)|edicate))|E(?:numerator|vent|PSImageRep|rror|x(?:ception|istsCommand|pression))|V(?:iew(?:Animation)?|al(?:idated(?:ToobarItem|UserInterfaceItem)|ue(?:Transformer)?))|Keyed(?:Unarchiver|Archiver)|Qui(?:ckDrawView|tCommand)|F(?:ile(?:Manager|Handle|Wrapper)|o(?:nt(?:Manager|Descriptor|Panel)?|rm(?:Cell|atter)))|W(?:hoseSpecifier|indow(?:Controller)?|orkspace)|L(?:o(?:c(?:k(?:ing)?|ale)|gicalTest)|evelIndicator(?:Cell)?|ayoutManager)|A(?:ssertionHandler|nimation|ctionCell|ttributedString|utoreleasePool|TSTypesetter|ppl(?:ication|e(?:Script|Event(?:Manager|Descriptor)))|ffineTransform|lert|r(?:chiver|ray(?:Controller)?))))(?:\\\\b)\"},{token:[\"support.type.cocoa.leopard\"],regex:\"(?:\\\\b)(NS(?:R(?:u(?:nLoop|ler(?:Marker|View))|e(?:sponder|cursiveLock|lativeSpecifier)|an(?:domSpecifier|geSpecifier))|G(?:etCommand|lyph(?:Generator|Storage|Info)|raphicsContext)|XML(?:Node|D(?:ocument|TD(?:Node)?)|Parser|Element)|M(?:iddleSpecifier|ov(?:ie(?:View)?|eCommand)|utable(?:S(?:tring|et)|C(?:haracterSet|opying)|IndexSet|D(?:ictionary|ata)|URLRequest|ParagraphStyle|A(?:ttributedString|rray))|e(?:ssagePort(?:NameServer)?|nu(?:Item(?:Cell)?|View)?|t(?:hodSignature|adata(?:Item|Query(?:ResultGroup|AttributeValueTuple)?)))|a(?:ch(?:BootstrapServer|Port)|trix))|B(?:itmapImageRep|ox|u(?:ndle|tton(?:Cell)?)|ezierPath|rowser(?:Cell)?)|S(?:hadow|c(?:anner|r(?:ipt(?:SuiteRegistry|C(?:o(?:ercionHandler|mmand(?:Description)?)|lassDescription)|ObjectSpecifier|ExecutionContext|WhoseTest)|oll(?:er|View)|een))|t(?:epper(?:Cell)?|atus(?:Bar|Item)|r(?:ing|eam))|imple(?:HorizontalTypesetter|CString)|o(?:cketPort(?:NameServer)?|und|rtDescriptor)|p(?:e(?:cifierTest|ech(?:Recognizer|Synthesizer)|ll(?:Server|Checker))|litView)|e(?:cureTextField(?:Cell)?|t(?:Command)?|archField(?:Cell)?|rializer|gmentedC(?:ontrol|ell))|lider(?:Cell)?|avePanel)|H(?:ost|TTP(?:Cookie(?:Storage)?|URLResponse)|elpManager)|N(?:ib(?:Con(?:nector|trolConnector)|OutletConnector)?|otification(?:Center|Queue)?|u(?:ll|mber(?:Formatter)?)|etService(?:Browser)?|ameSpecifier)|C(?:ha(?:ngeSpelling|racterSet)|o(?:n(?:stantString|nection|trol(?:ler)?|ditionLock)|d(?:ing|er)|unt(?:Command|edSet)|pying|lor(?:Space|P(?:ick(?:ing(?:Custom|Default)|er)|anel)|Well|List)?|m(?:p(?:oundPredicate|arisonPredicate)|boBox(?:Cell)?))|u(?:stomImageRep|rsor)|IImageRep|ell|l(?:ipView|o(?:seCommand|neCommand)|assDescription)|a(?:ched(?:ImageRep|URLResponse)|lendar(?:Date)?)|reateCommand)|T(?:hread|ypesetter|ime(?:Zone|r)|o(?:olbar(?:Item(?:Validations)?)?|kenField(?:Cell)?)|ext(?:Block|Storage|Container|Tab(?:le(?:Block)?)?|Input|View|Field(?:Cell)?|List|Attachment(?:Cell)?)?|a(?:sk|b(?:le(?:Header(?:Cell|View)|Column|View)|View(?:Item)?))|reeController)|I(?:n(?:dex(?:S(?:pecifier|et)|Path)|put(?:Manager|S(?:tream|erv(?:iceProvider|er(?:MouseTracker)?)))|vocation)|gnoreMisspelledWords|mage(?:Rep|Cell|View)?)|O(?:ut(?:putStream|lineView)|pen(?:GL(?:Context|Pixel(?:Buffer|Format)|View)|Panel)|bj(?:CTypeSerializationCallBack|ect(?:Controller)?))|D(?:i(?:st(?:antObject(?:Request)?|ributed(?:NotificationCenter|Lock))|ctionary|rectoryEnumerator)|ocument(?:Controller)?|e(?:serializer|cimalNumber(?:Behaviors|Handler)?|leteCommand)|at(?:e(?:Components|Picker(?:Cell)?|Formatter)?|a)|ra(?:wer|ggingInfo))|U(?:ser(?:InterfaceValidations|Defaults(?:Controller)?)|RL(?:Re(?:sponse|quest)|Handle(?:Client)?|C(?:onnection|ache|redential(?:Storage)?)|Download(?:Delegate)?|Prot(?:ocol(?:Client)?|ectionSpace)|AuthenticationChallenge(?:Sender)?)?|n(?:iqueIDSpecifier|doManager|archiver))|P(?:ipe|o(?:sitionalSpecifier|pUpButton(?:Cell)?|rt(?:Message|NameServer|Coder)?)|ICTImageRep|ersistentDocument|DFImageRep|a(?:steboard|nel|ragraphStyle|geLayout)|r(?:int(?:Info|er|Operation|Panel)|o(?:cessInfo|tocolChecker|perty(?:Specifier|ListSerialization)|gressIndicator|xy)|edicate))|E(?:numerator|vent|PSImageRep|rror|x(?:ception|istsCommand|pression))|V(?:iew(?:Animation)?|al(?:idated(?:ToobarItem|UserInterfaceItem)|ue(?:Transformer)?))|Keyed(?:Unarchiver|Archiver)|Qui(?:ckDrawView|tCommand)|F(?:ile(?:Manager|Handle|Wrapper)|o(?:nt(?:Manager|Descriptor|Panel)?|rm(?:Cell|atter)))|W(?:hoseSpecifier|indow(?:Controller)?|orkspace)|L(?:o(?:c(?:k(?:ing)?|ale)|gicalTest)|evelIndicator(?:Cell)?|ayoutManager)|A(?:ssertionHandler|nimation|ctionCell|ttributedString|utoreleasePool|TSTypesetter|ppl(?:ication|e(?:Script|Event(?:Manager|Descriptor)))|ffineTransform|lert|r(?:chiver|ray(?:Controller)?))))(?:\\\\b)\"},{token:[\"support.class.quartz\"],regex:\"(?:\\\\b)(C(?:I(?:Sampler|Co(?:ntext|lor)|Image(?:Accumulator)?|PlugIn(?:Registration)?|Vector|Kernel|Filter(?:Generator|Shape)?)|A(?:Renderer|MediaTiming(?:Function)?|BasicAnimation|ScrollLayer|Constraint(?:LayoutManager)?|T(?:iledLayer|extLayer|rans(?:ition|action))|OpenGLLayer|PropertyAnimation|KeyframeAnimation|Layer|A(?:nimation(?:Group)?|ction))))(?:\\\\b)\"},{token:[\"support.type.quartz\"],regex:\"(?:\\\\b)(C(?:G(?:Float|Point|Size|Rect)|IFormat|AConstraintAttribute))(?:\\\\b)\"},{token:[\"support.type.cocoa\"],regex:\"(?:\\\\b)(NS(?:R(?:ect(?:Edge)?|ange)|G(?:lyph(?:Relation|LayoutMode)?|radientType)|M(?:odalSession|a(?:trixMode|p(?:Table|Enumerator)))|B(?:itmapImageFileType|orderType|uttonType|ezelStyle|ackingStoreType|rowserColumnResizingType)|S(?:cr(?:oll(?:er(?:Part|Arrow)|ArrowPosition)|eenAuxiliaryOpaque)|tringEncoding|ize|ocketNativeHandle|election(?:Granularity|Direction|Affinity)|wapped(?:Double|Float)|aveOperationType)|Ha(?:sh(?:Table|Enumerator)|ndler(?:2)?)|C(?:o(?:ntrol(?:Size|Tint)|mp(?:ositingOperation|arisonResult))|ell(?:State|Type|ImagePosition|Attribute))|T(?:hreadPrivate|ypesetterGlyphInfo|i(?:ckMarkPosition|tlePosition|meInterval)|o(?:ol(?:TipTag|bar(?:SizeMode|DisplayMode))|kenStyle)|IFFCompression|ext(?:TabType|Alignment)|ab(?:State|leViewDropOperation|ViewType)|rackingRectTag)|ImageInterpolation|Zone|OpenGL(?:ContextAuxiliary|PixelFormatAuxiliary)|D(?:ocumentChangeType|atePickerElementFlags|ra(?:werState|gOperation))|UsableScrollerParts|P(?:oint|r(?:intingPageOrder|ogressIndicator(?:Style|Th(?:ickness|readInfo))))|EventType|KeyValueObservingOptions|Fo(?:nt(?:SymbolicTraits|TraitMask|Action)|cusRingType)|W(?:indow(?:OrderingMode|Depth)|orkspace(?:IconCreationOptions|LaunchOptions)|ritingDirection)|L(?:ineBreakMode|ayout(?:Status|Direction))|A(?:nimation(?:Progress|Effect)|ppl(?:ication(?:TerminateReply|DelegateReply|PrintReply)|eEventManagerSuspensionID)|ffineTransformStruct|lertStyle)))(?:\\\\b)\"},{token:[\"support.constant.cocoa\"],regex:\"(?:\\\\b)(NS(?:NotFound|Ordered(?:Ascending|Descending|Same)))(?:\\\\b)\"},{token:[\"support.constant.notification.cocoa.leopard\"],regex:\"(?:\\\\b)(NS(?:MenuDidBeginTracking|ViewDidUpdateTrackingAreas)?Notification)(?:\\\\b)\"},{token:[\"support.constant.notification.cocoa\"],regex:\"(?:\\\\b)(NS(?:Menu(?:Did(?:RemoveItem|SendAction|ChangeItem|EndTracking|AddItem)|WillSendAction)|S(?:ystemColorsDidChange|plitView(?:DidResizeSubviews|WillResizeSubviews))|C(?:o(?:nt(?:extHelpModeDid(?:Deactivate|Activate)|rolT(?:intDidChange|extDid(?:BeginEditing|Change|EndEditing)))|lor(?:PanelColorDidChange|ListDidChange)|mboBox(?:Selection(?:IsChanging|DidChange)|Will(?:Dismiss|PopUp)))|lassDescriptionNeededForClass)|T(?:oolbar(?:DidRemoveItem|WillAddItem)|ext(?:Storage(?:DidProcessEditing|WillProcessEditing)|Did(?:BeginEditing|Change|EndEditing)|View(?:DidChange(?:Selection|TypingAttributes)|WillChangeNotifyingTextView))|ableView(?:Selection(?:IsChanging|DidChange)|ColumnDid(?:Resize|Move)))|ImageRepRegistryDidChange|OutlineView(?:Selection(?:IsChanging|DidChange)|ColumnDid(?:Resize|Move)|Item(?:Did(?:Collapse|Expand)|Will(?:Collapse|Expand)))|Drawer(?:Did(?:Close|Open)|Will(?:Close|Open))|PopUpButton(?:CellWillPopUp|WillPopUp)|View(?:GlobalFrameDidChange|BoundsDidChange|F(?:ocusDidChange|rameDidChange))|FontSetChanged|W(?:indow(?:Did(?:Resi(?:ze|gn(?:Main|Key))|M(?:iniaturize|ove)|Become(?:Main|Key)|ChangeScreen(?:|Profile)|Deminiaturize|Update|E(?:ndSheet|xpose))|Will(?:M(?:iniaturize|ove)|BeginSheet|Close))|orkspace(?:SessionDid(?:ResignActive|BecomeActive)|Did(?:Mount|TerminateApplication|Unmount|PerformFileOperation|Wake|LaunchApplication)|Will(?:Sleep|Unmount|PowerOff|LaunchApplication)))|A(?:ntialiasThresholdChanged|ppl(?:ication(?:Did(?:ResignActive|BecomeActive|Hide|ChangeScreenParameters|U(?:nhide|pdate)|FinishLaunching)|Will(?:ResignActive|BecomeActive|Hide|Terminate|U(?:nhide|pdate)|FinishLaunching))|eEventManagerWillProcessFirstEvent)))Notification)(?:\\\\b)\"},{token:[\"support.constant.cocoa.leopard\"],regex:\"(?:\\\\b)(NS(?:RuleEditor(?:RowType(?:Simple|Compound)|NestingMode(?:Si(?:ngle|mple)|Compound|List))|GradientDraws(?:BeforeStartingLocation|AfterEndingLocation)|M(?:inusSetExpressionType|a(?:chPortDeallocate(?:ReceiveRight|SendRight|None)|pTable(?:StrongMemory|CopyIn|ZeroingWeakMemory|ObjectPointerPersonality)))|B(?:oxCustom|undleExecutableArchitecture(?:X86|I386|PPC(?:64)?)|etweenPredicateOperatorType|ackgroundStyle(?:Raised|Dark|L(?:ight|owered)))|S(?:tring(?:DrawingTruncatesLastVisibleLine|EncodingConversion(?:ExternalRepresentation|AllowLossy))|ubqueryExpressionType|p(?:e(?:ech(?:SentenceBoundary|ImmediateBoundary|WordBoundary)|llingState(?:GrammarFlag|SpellingFlag))|litViewDividerStyleThi(?:n|ck))|e(?:rvice(?:RequestTimedOutError|M(?:iscellaneousError|alformedServiceDictionaryError)|InvalidPasteboardDataError|ErrorM(?:inimum|aximum)|Application(?:NotFoundError|LaunchFailedError))|gmentStyle(?:Round(?:Rect|ed)|SmallSquare|Capsule|Textured(?:Rounded|Square)|Automatic)))|H(?:UDWindowMask|ashTable(?:StrongMemory|CopyIn|ZeroingWeakMemory|ObjectPointerPersonality))|N(?:oModeColorPanel|etServiceNoAutoRename)|C(?:hangeRedone|o(?:ntainsPredicateOperatorType|l(?:orRenderingIntent(?:RelativeColorimetric|Saturation|Default|Perceptual|AbsoluteColorimetric)|lectorDisabledOption))|ellHit(?:None|ContentArea|TrackableArea|EditableTextArea))|T(?:imeZoneNameStyle(?:S(?:hort(?:Standard|DaylightSaving)|tandard)|DaylightSaving)|extFieldDatePickerStyle|ableViewSelectionHighlightStyle(?:Regular|SourceList)|racking(?:Mouse(?:Moved|EnteredAndExited)|CursorUpdate|InVisibleRect|EnabledDuringMouseDrag|A(?:ssumeInside|ctive(?:In(?:KeyWindow|ActiveApp)|WhenFirstResponder|Always))))|I(?:n(?:tersectSetExpressionType|dexedColorSpaceModel)|mageScale(?:None|Proportionally(?:Down|UpOrDown)|AxesIndependently))|Ope(?:nGLPFAAllowOfflineRenderers|rationQueue(?:DefaultMaxConcurrentOperationCount|Priority(?:High|Normal|Very(?:High|Low)|Low)))|D(?:iacriticInsensitiveSearch|ownloadsDirectory)|U(?:nionSetExpressionType|TF(?:16(?:BigEndianStringEncoding|StringEncoding|LittleEndianStringEncoding)|32(?:BigEndianStringEncoding|StringEncoding|LittleEndianStringEncoding)))|P(?:ointerFunctions(?:Ma(?:chVirtualMemory|llocMemory)|Str(?:ongMemory|uctPersonality)|C(?:StringPersonality|opyIn)|IntegerPersonality|ZeroingWeakMemory|O(?:paque(?:Memory|Personality)|bjectP(?:ointerPersonality|ersonality)))|at(?:hStyle(?:Standard|NavigationBar|PopUp)|ternColorSpaceModel)|rintPanelShows(?:Scaling|Copies|Orientation|P(?:a(?:perSize|ge(?:Range|SetupAccessory))|review)))|Executable(?:RuntimeMismatchError|NotLoadableError|ErrorM(?:inimum|aximum)|L(?:inkError|oadError)|ArchitectureMismatchError)|KeyValueObservingOption(?:Initial|Prior)|F(?:i(?:ndPanelSubstringMatchType(?:StartsWith|Contains|EndsWith|FullWord)|leRead(?:TooLargeError|UnknownStringEncodingError))|orcedOrderingSearch)|Wi(?:ndow(?:BackingLocation(?:MainMemory|Default|VideoMemory)|Sharing(?:Read(?:Only|Write)|None)|CollectionBehavior(?:MoveToActiveSpace|CanJoinAllSpaces|Default))|dthInsensitiveSearch)|AggregateExpressionType))(?:\\\\b)\"},{token:[\"support.constant.cocoa\"],regex:\"(?:\\\\b)(NS(?:R(?:GB(?:ModeColorPanel|ColorSpaceModel)|ight(?:Mouse(?:D(?:own(?:Mask)?|ragged(?:Mask)?)|Up(?:Mask)?)|T(?:ext(?:Movement|Alignment)|ab(?:sBezelBorder|StopType))|ArrowFunctionKey)|ound(?:RectBezelStyle|Bankers|ed(?:BezelStyle|TokenStyle|DisclosureBezelStyle)|Down|Up|Plain|Line(?:CapStyle|JoinStyle))|un(?:StoppedResponse|ContinuesResponse|AbortedResponse)|e(?:s(?:izableWindowMask|et(?:CursorRectsRunLoopOrdering|FunctionKey))|ce(?:ssedBezelStyle|iver(?:sCantHandleCommandScriptError|EvaluationScriptError))|turnTextMovement|doFunctionKey|quiredArgumentsMissingScriptError|l(?:evancyLevelIndicatorStyle|ative(?:Before|After))|gular(?:SquareBezelStyle|ControlSize)|moveTraitFontAction)|a(?:n(?:domSubelement|geDateMode)|tingLevelIndicatorStyle|dio(?:ModeMatrix|Button)))|G(?:IFFileType|lyph(?:Below|Inscribe(?:B(?:elow|ase)|Over(?:strike|Below)|Above)|Layout(?:WithPrevious|A(?:tAPoint|gainstAPoint))|A(?:ttribute(?:BidiLevel|Soft|Inscribe|Elastic)|bove))|r(?:ooveBorder|eaterThan(?:Comparison|OrEqualTo(?:Comparison|PredicateOperatorType)|PredicateOperatorType)|a(?:y(?:ModeColorPanel|ColorSpaceModel)|dient(?:None|Con(?:cave(?:Strong|Weak)|vex(?:Strong|Weak)))|phiteControlTint)))|XML(?:N(?:o(?:tationDeclarationKind|de(?:CompactEmptyElement|IsCDATA|OptionsNone|Use(?:SingleQuotes|DoubleQuotes)|Pre(?:serve(?:NamespaceOrder|C(?:haracterReferences|DATA)|DTD|Prefixes|E(?:ntities|mptyElements)|Quotes|Whitespace|A(?:ttributeOrder|ll))|ttyPrint)|ExpandEmptyElement))|amespaceKind)|CommentKind|TextKind|InvalidKind|D(?:ocument(?:X(?:MLKind|HTMLKind|Include)|HTMLKind|T(?:idy(?:XML|HTML)|extKind)|IncludeContentTypeDeclaration|Validate|Kind)|TDKind)|P(?:arser(?:GTRequiredError|XMLDeclNot(?:StartedError|FinishedError)|Mi(?:splaced(?:XMLDeclarationError|CDATAEndStringError)|xedContentDeclNot(?:StartedError|FinishedError))|S(?:t(?:andaloneValueError|ringNot(?:StartedError|ClosedError))|paceRequiredError|eparatorRequiredError)|N(?:MTOKENRequiredError|o(?:t(?:ationNot(?:StartedError|FinishedError)|WellBalancedError)|DTDError)|amespaceDeclarationError|AMERequiredError)|C(?:haracterRef(?:In(?:DTDError|PrologError|EpilogError)|AtEOFError)|o(?:nditionalSectionNot(?:StartedError|FinishedError)|mment(?:NotFinishedError|ContainsDoubleHyphenError))|DATANotFinishedError)|TagNameMismatchError|In(?:ternalError|valid(?:HexCharacterRefError|C(?:haracter(?:RefError|InEntityError|Error)|onditionalSectionError)|DecimalCharacterRefError|URIError|Encoding(?:NameError|Error)))|OutOfMemoryError|D(?:ocumentStartError|elegateAbortedParseError|OCTYPEDeclNotFinishedError)|U(?:RI(?:RequiredError|FragmentError)|n(?:declaredEntityError|parsedEntityError|knownEncodingError|finishedTagError))|P(?:CDATARequiredError|ublicIdentifierRequiredError|arsedEntityRef(?:MissingSemiError|NoNameError|In(?:Internal(?:SubsetError|Error)|PrologError|EpilogError)|AtEOFError)|r(?:ocessingInstructionNot(?:StartedError|FinishedError)|ematureDocumentEndError))|E(?:n(?:codingNotSupportedError|tity(?:Ref(?:In(?:DTDError|PrologError|EpilogError)|erence(?:MissingSemiError|WithoutNameError)|LoopError|AtEOFError)|BoundaryError|Not(?:StartedError|FinishedError)|Is(?:ParameterError|ExternalError)|ValueRequiredError))|qualExpectedError|lementContentDeclNot(?:StartedError|FinishedError)|xt(?:ernalS(?:tandaloneEntityError|ubsetNotFinishedError)|raContentError)|mptyDocumentError)|L(?:iteralNot(?:StartedError|FinishedError)|T(?:RequiredError|SlashRequiredError)|essThanSymbolInAttributeError)|Attribute(?:RedefinedError|HasNoValueError|Not(?:StartedError|FinishedError)|ListNot(?:StartedError|FinishedError)))|rocessingInstructionKind)|E(?:ntity(?:GeneralKind|DeclarationKind|UnparsedKind|P(?:ar(?:sedKind|ameterKind)|redefined))|lement(?:Declaration(?:MixedKind|UndefinedKind|E(?:lementKind|mptyKind)|Kind|AnyKind)|Kind))|Attribute(?:N(?:MToken(?:sKind|Kind)|otationKind)|CDATAKind|ID(?:Ref(?:sKind|Kind)|Kind)|DeclarationKind|En(?:tit(?:yKind|iesKind)|umerationKind)|Kind))|M(?:i(?:n(?:XEdge|iaturizableWindowMask|YEdge|uteCalendarUnit)|terLineJoinStyle|ddleSubelement|xedState)|o(?:nthCalendarUnit|deSwitchFunctionKey|use(?:Moved(?:Mask)?|E(?:ntered(?:Mask)?|ventSubtype|xited(?:Mask)?))|veToBezierPathElement|mentary(?:ChangeButton|Push(?:Button|InButton)|Light(?:Button)?))|enuFunctionKey|a(?:c(?:intoshInterfaceStyle|OSRomanStringEncoding)|tchesPredicateOperatorType|ppedRead|x(?:XEdge|YEdge))|ACHOperatingSystem)|B(?:MPFileType|o(?:ttomTabsBezelBorder|ldFontMask|rderlessWindowMask|x(?:Se(?:condary|parator)|OldStyle|Primary))|uttLineCapStyle|e(?:zelBorder|velLineJoinStyle|low(?:Bottom|Top)|gin(?:sWith(?:Comparison|PredicateOperatorType)|FunctionKey))|lueControlTint|ack(?:spaceCharacter|tabTextMovement|ingStore(?:Retained|Buffered|Nonretained)|TabCharacter|wardsSearch|groundTab)|r(?:owser(?:NoColumnResizing|UserColumnResizing|AutoColumnResizing)|eakFunctionKey))|S(?:h(?:ift(?:JISStringEncoding|KeyMask)|ow(?:ControlGlyphs|InvisibleGlyphs)|adowlessSquareBezelStyle)|y(?:s(?:ReqFunctionKey|tem(?:D(?:omainMask|efined(?:Mask)?)|FunctionKey))|mbolStringEncoding)|c(?:a(?:nnedOption|le(?:None|ToFit|Proportionally))|r(?:oll(?:er(?:NoPart|Increment(?:Page|Line|Arrow)|Decrement(?:Page|Line|Arrow)|Knob(?:Slot)?|Arrows(?:M(?:inEnd|axEnd)|None|DefaultSetting))|Wheel(?:Mask)?|LockFunctionKey)|eenChangedEventType))|t(?:opFunctionKey|r(?:ingDrawing(?:OneShot|DisableScreenFontSubstitution|Uses(?:DeviceMetrics|FontLeading|LineFragmentOrigin))|eam(?:Status(?:Reading|NotOpen|Closed|Open(?:ing)?|Error|Writing|AtEnd)|Event(?:Has(?:BytesAvailable|SpaceAvailable)|None|OpenCompleted|E(?:ndEncountered|rrorOccurred)))))|i(?:ngle(?:DateMode|UnderlineStyle)|ze(?:DownFontAction|UpFontAction))|olarisOperatingSystem|unOSOperatingSystem|pecialPageOrder|e(?:condCalendarUnit|lect(?:By(?:Character|Paragraph|Word)|i(?:ng(?:Next|Previous)|onAffinity(?:Downstream|Upstream))|edTab|FunctionKey)|gmentSwitchTracking(?:Momentary|Select(?:One|Any)))|quareLineCapStyle|witchButton|ave(?:ToOperation|Op(?:tions(?:Yes|No|Ask)|eration)|AsOperation)|mall(?:SquareBezelStyle|C(?:ontrolSize|apsFontMask)|IconButtonBezelStyle))|H(?:ighlightModeMatrix|SBModeColorPanel|o(?:ur(?:Minute(?:SecondDatePickerElementFlag|DatePickerElementFlag)|CalendarUnit)|rizontalRuler|meFunctionKey)|TTPCookieAcceptPolicy(?:Never|OnlyFromMainDocumentDomain|Always)|e(?:lp(?:ButtonBezelStyle|KeyMask|FunctionKey)|avierFontAction)|PUXOperatingSystem)|Year(?:MonthDa(?:yDatePickerElementFlag|tePickerElementFlag)|CalendarUnit)|N(?:o(?:n(?:StandardCharacterSetFontMask|ZeroWindingRule|activatingPanelMask|LossyASCIIStringEncoding)|Border|t(?:ification(?:SuspensionBehavior(?:Hold|Coalesce|D(?:eliverImmediately|rop))|NoCoalescing|CoalescingOn(?:Sender|Name)|DeliverImmediately|PostToAllSessions)|PredicateType|EqualToPredicateOperatorType)|S(?:cr(?:iptError|ollerParts)|ubelement|pecifierError)|CellMask|T(?:itle|opLevelContainersSpecifierError|abs(?:BezelBorder|NoBorder|LineBorder))|I(?:nterfaceStyle|mage)|UnderlineStyle|FontChangeAction)|u(?:ll(?:Glyph|CellType)|m(?:eric(?:Search|PadKeyMask)|berFormatter(?:Round(?:Half(?:Down|Up|Even)|Ceiling|Down|Up|Floor)|Behavior(?:10|Default)|S(?:cientificStyle|pellOutStyle)|NoStyle|CurrencyStyle|DecimalStyle|P(?:ercentStyle|ad(?:Before(?:Suffix|Prefix)|After(?:Suffix|Prefix))))))|e(?:t(?:Service(?:BadArgumentError|NotFoundError|C(?:ollisionError|ancelledError)|TimeoutError|InvalidError|UnknownError|ActivityInProgress)|workDomainMask)|wlineCharacter|xt(?:StepInterfaceStyle|FunctionKey))|EXTSTEPStringEncoding|a(?:t(?:iveShortGlyphPacking|uralTextAlignment)|rrowFontMask))|C(?:hange(?:ReadOtherContents|GrayCell(?:Mask)?|BackgroundCell(?:Mask)?|Cleared|Done|Undone|Autosaved)|MYK(?:ModeColorPanel|ColorSpaceModel)|ircular(?:BezelStyle|Slider)|o(?:n(?:stantValueExpressionType|t(?:inuousCapacityLevelIndicatorStyle|entsCellMask|ain(?:sComparison|erSpecifierError)|rol(?:Glyph|KeyMask))|densedFontMask)|lor(?:Panel(?:RGBModeMask|GrayModeMask|HSBModeMask|C(?:MYKModeMask|olorListModeMask|ustomPaletteModeMask|rayonModeMask)|WheelModeMask|AllModesMask)|ListModeColorPanel)|reServiceDirectory|m(?:p(?:osite(?:XOR|Source(?:In|O(?:ut|ver)|Atop)|Highlight|C(?:opy|lear)|Destination(?:In|O(?:ut|ver)|Atop)|Plus(?:Darker|Lighter))|ressedFontMask)|mandKeyMask))|u(?:stom(?:SelectorPredicateOperatorType|PaletteModeColorPanel)|r(?:sor(?:Update(?:Mask)?|PointingDevice)|veToBezierPathElement))|e(?:nterT(?:extAlignment|abStopType)|ll(?:State|H(?:ighlighted|as(?:Image(?:Horizontal|OnLeftOrBottom)|OverlappingImage))|ChangesContents|Is(?:Bordered|InsetButton)|Disabled|Editable|LightsBy(?:Gray|Background|Contents)|AllowsMixedState))|l(?:ipPagination|o(?:s(?:ePathBezierPathElement|ableWindowMask)|ckAndCalendarDatePickerStyle)|ear(?:ControlTint|DisplayFunctionKey|LineFunctionKey))|a(?:seInsensitive(?:Search|PredicateOption)|n(?:notCreateScriptCommandError|cel(?:Button|TextMovement))|chesDirectory|lculation(?:NoError|Overflow|DivideByZero|Underflow|LossOfPrecision)|rriageReturnCharacter)|r(?:itical(?:Request|AlertStyle)|ayonModeColorPanel))|T(?:hick(?:SquareBezelStyle|erSquareBezelStyle)|ypesetter(?:Behavior|HorizontalTabAction|ContainerBreakAction|ZeroAdvancementAction|OriginalBehavior|ParagraphBreakAction|WhitespaceAction|L(?:ineBreakAction|atestBehavior))|i(?:ckMark(?:Right|Below|Left|Above)|tledWindowMask|meZoneDatePickerElementFlag)|o(?:olbarItemVisibilityPriority(?:Standard|High|User|Low)|pTabsBezelBorder|ggleButton)|IFF(?:Compression(?:N(?:one|EXT)|CCITTFAX(?:3|4)|OldJPEG|JPEG|PackBits|LZW)|FileType)|e(?:rminate(?:Now|Cancel|Later)|xt(?:Read(?:InapplicableDocumentTypeError|WriteErrorM(?:inimum|aximum))|Block(?:M(?:i(?:nimum(?:Height|Width)|ddleAlignment)|a(?:rgin|ximum(?:Height|Width)))|B(?:o(?:ttomAlignment|rder)|aselineAlignment)|Height|TopAlignment|P(?:ercentageValueType|adding)|Width|AbsoluteValueType)|StorageEdited(?:Characters|Attributes)|CellType|ured(?:RoundedBezelStyle|BackgroundWindowMask|SquareBezelStyle)|Table(?:FixedLayoutAlgorithm|AutomaticLayoutAlgorithm)|Field(?:RoundedBezel|SquareBezel|AndStepperDatePickerStyle)|WriteInapplicableDocumentTypeError|ListPrependEnclosingMarker))|woByteGlyphPacking|ab(?:Character|TextMovement|le(?:tP(?:oint(?:Mask|EventSubtype)?|roximity(?:Mask|EventSubtype)?)|Column(?:NoResizing|UserResizingMask|AutoresizingMask)|View(?:ReverseSequentialColumnAutoresizingStyle|GridNone|S(?:olid(?:HorizontalGridLineMask|VerticalGridLineMask)|equentialColumnAutoresizingStyle)|NoColumnAutoresizing|UniformColumnAutoresizingStyle|FirstColumnOnlyAutoresizingStyle|LastColumnOnlyAutoresizingStyle)))|rackModeMatrix)|I(?:n(?:sert(?:CharFunctionKey|FunctionKey|LineFunctionKey)|t(?:Type|ernalS(?:criptError|pecifierError))|dexSubelement|validIndexSpecifierError|formational(?:Request|AlertStyle)|PredicateOperatorType)|talicFontMask|SO(?:2022JPStringEncoding|Latin(?:1StringEncoding|2StringEncoding))|dentityMappingCharacterCollection|llegalTextMovement|mage(?:R(?:ight|ep(?:MatchesDevice|LoadStatus(?:ReadingHeader|Completed|InvalidData|Un(?:expectedEOF|knownType)|WillNeedAllData)))|Below|C(?:ellType|ache(?:BySize|Never|Default|Always))|Interpolation(?:High|None|Default|Low)|O(?:nly|verlaps)|Frame(?:Gr(?:oove|ayBezel)|Button|None|Photo)|L(?:oadStatus(?:ReadError|C(?:ompleted|ancelled)|InvalidData|UnexpectedEOF)|eft)|A(?:lign(?:Right|Bottom(?:Right|Left)?|Center|Top(?:Right|Left)?|Left)|bove)))|O(?:n(?:State|eByteGlyphPacking|OffButton|lyScrollerArrows)|ther(?:Mouse(?:D(?:own(?:Mask)?|ragged(?:Mask)?)|Up(?:Mask)?)|TextMovement)|SF1OperatingSystem|pe(?:n(?:GL(?:GO(?:Re(?:setLibrary|tainRenderers)|ClearFormatCache|FormatCacheSize)|PFA(?:R(?:obust|endererID)|M(?:inimumPolicy|ulti(?:sample|Screen)|PSafe|aximumPolicy)|BackingStore|S(?:creenMask|te(?:ncilSize|reo)|ingleRenderer|upersample|ample(?:s|Buffers|Alpha))|NoRecovery|C(?:o(?:lor(?:Size|Float)|mpliant)|losestPolicy)|OffScreen|D(?:oubleBuffer|epthSize)|PixelBuffer|VirtualScreenCount|FullScreen|Window|A(?:cc(?:umSize|elerated)|ux(?:Buffers|DepthStencil)|l(?:phaSize|lRenderers))))|StepUnicodeReservedBase)|rationNotSupportedForKeyS(?:criptError|pecifierError))|ffState|KButton|rPredicateType|bjC(?:B(?:itfield|oolType)|S(?:hortType|tr(?:ingType|uctType)|electorType)|NoType|CharType|ObjectType|DoubleType|UnionType|PointerType|VoidType|FloatType|Long(?:Type|longType)|ArrayType))|D(?:i(?:s(?:c(?:losureBezelStyle|reteCapacityLevelIndicatorStyle)|playWindowRunLoopOrdering)|acriticInsensitivePredicateOption|rect(?:Selection|PredicateModifier))|o(?:c(?:ModalWindowMask|ument(?:Directory|ationDirectory))|ubleType|wn(?:TextMovement|ArrowFunctionKey))|e(?:s(?:cendingPageOrder|ktopDirectory)|cimalTabStopType|v(?:ice(?:NColorSpaceModel|IndependentModifierFlagsMask)|eloper(?:Directory|ApplicationDirectory))|fault(?:ControlTint|TokenStyle)|lete(?:Char(?:acter|FunctionKey)|FunctionKey|LineFunctionKey)|moApplicationDirectory)|a(?:yCalendarUnit|teFormatter(?:MediumStyle|Behavior(?:10|Default)|ShortStyle|NoStyle|FullStyle|LongStyle))|ra(?:wer(?:Clos(?:ingState|edState)|Open(?:ingState|State))|gOperation(?:Generic|Move|None|Copy|Delete|Private|Every|Link|All)))|U(?:ser(?:CancelledError|D(?:irectory|omainMask)|FunctionKey)|RL(?:Handle(?:NotLoaded|Load(?:Succeeded|InProgress|Failed))|CredentialPersistence(?:None|Permanent|ForSession))|n(?:scaledWindowMask|cachedRead|i(?:codeStringEncoding|talicFontMask|fiedTitleAndToolbarWindowMask)|d(?:o(?:CloseGroupingRunLoopOrdering|FunctionKey)|e(?:finedDateComponent|rline(?:Style(?:Single|None|Thick|Double)|Pattern(?:Solid|D(?:ot|ash(?:Dot(?:Dot)?)?)))))|known(?:ColorSpaceModel|P(?:ointingDevice|ageOrder)|KeyS(?:criptError|pecifierError))|boldFontMask)|tilityWindowMask|TF8StringEncoding|p(?:dateWindowsRunLoopOrdering|TextMovement|ArrowFunctionKey))|J(?:ustifiedTextAlignment|PEG(?:2000FileType|FileType)|apaneseEUC(?:GlyphPacking|StringEncoding))|P(?:o(?:s(?:t(?:Now|erFontMask|WhenIdle|ASAP)|iti(?:on(?:Replace|Be(?:fore|ginning)|End|After)|ve(?:IntType|DoubleType|FloatType)))|pUp(?:NoArrow|ArrowAt(?:Bottom|Center))|werOffEventType|rtraitOrientation)|NGFileType|ush(?:InCell(?:Mask)?|OnPushOffButton)|e(?:n(?:TipMask|UpperSideMask|PointingDevice|LowerSideMask)|riodic(?:Mask)?)|P(?:S(?:caleField|tatus(?:Title|Field)|aveButton)|N(?:ote(?:Title|Field)|ame(?:Title|Field))|CopiesField|TitleField|ImageButton|OptionsButton|P(?:a(?:perFeedButton|ge(?:Range(?:To|From)|ChoiceMatrix))|reviewButton)|LayoutButton)|lainTextTokenStyle|a(?:useFunctionKey|ragraphSeparatorCharacter|ge(?:DownFunctionKey|UpFunctionKey))|r(?:int(?:ing(?:ReplyLater|Success|Cancelled|Failure)|ScreenFunctionKey|erTable(?:NotFound|OK|Error)|FunctionKey)|o(?:p(?:ertyList(?:XMLFormat|MutableContainers(?:AndLeaves)?|BinaryFormat|Immutable|OpenStepFormat)|rietaryStringEncoding)|gressIndicator(?:BarStyle|SpinningStyle|Preferred(?:SmallThickness|Thickness|LargeThickness|AquaThickness)))|e(?:ssedTab|vFunctionKey))|L(?:HeightForm|CancelButton|TitleField|ImageButton|O(?:KButton|rientationMatrix)|UnitsButton|PaperNameButton|WidthForm))|E(?:n(?:terCharacter|d(?:sWith(?:Comparison|PredicateOperatorType)|FunctionKey))|v(?:e(?:nOddWindingRule|rySubelement)|aluatedObjectExpressionType)|qualTo(?:Comparison|PredicateOperatorType)|ra(?:serPointingDevice|CalendarUnit|DatePickerElementFlag)|x(?:clude(?:10|QuickDrawElementsIconCreationOption)|pandedFontMask|ecuteFunctionKey))|V(?:i(?:ew(?:M(?:in(?:XMargin|YMargin)|ax(?:XMargin|YMargin))|HeightSizable|NotSizable|WidthSizable)|aPanelFontAction)|erticalRuler|a(?:lidationErrorM(?:inimum|aximum)|riableExpressionType))|Key(?:SpecifierEvaluationScriptError|Down(?:Mask)?|Up(?:Mask)?|PathExpressionType|Value(?:MinusSetMutation|SetSetMutation|Change(?:Re(?:placement|moval)|Setting|Insertion)|IntersectSetMutation|ObservingOption(?:New|Old)|UnionSetMutation|ValidationError))|QTMovie(?:NormalPlayback|Looping(?:BackAndForthPlayback|Playback))|F(?:1(?:1FunctionKey|7FunctionKey|2FunctionKey|8FunctionKey|3FunctionKey|9FunctionKey|4FunctionKey|5FunctionKey|FunctionKey|0FunctionKey|6FunctionKey)|7FunctionKey|i(?:nd(?:PanelAction(?:Replace(?:A(?:ndFind|ll(?:InSelection)?))?|S(?:howFindPanel|e(?:tFindString|lectAll(?:InSelection)?))|Next|Previous)|FunctionKey)|tPagination|le(?:Read(?:No(?:SuchFileError|PermissionError)|CorruptFileError|In(?:validFileNameError|applicableStringEncodingError)|Un(?:supportedSchemeError|knownError))|HandlingPanel(?:CancelButton|OKButton)|NoSuchFileError|ErrorM(?:inimum|aximum)|Write(?:NoPermissionError|In(?:validFileNameError|applicableStringEncodingError)|OutOfSpaceError|Un(?:supportedSchemeError|knownError))|LockingError)|xedPitchFontMask)|2(?:1FunctionKey|7FunctionKey|2FunctionKey|8FunctionKey|3FunctionKey|9FunctionKey|4FunctionKey|5FunctionKey|FunctionKey|0FunctionKey|6FunctionKey)|o(?:nt(?:Mo(?:noSpaceTrait|dernSerifsClass)|BoldTrait|S(?:ymbolicClass|criptsClass|labSerifsClass|ansSerifClass)|C(?:o(?:ndensedTrait|llectionApplicationOnlyMask)|larendonSerifsClass)|TransitionalSerifsClass|I(?:ntegerAdvancementsRenderingMode|talicTrait)|O(?:ldStyleSerifsClass|rnamentalsClass)|DefaultRenderingMode|U(?:nknownClass|IOptimizedTrait)|Panel(?:S(?:hadowEffectModeMask|t(?:andardModesMask|rikethroughEffectModeMask)|izeModeMask)|CollectionModeMask|TextColorEffectModeMask|DocumentColorEffectModeMask|UnderlineEffectModeMask|FaceModeMask|All(?:ModesMask|EffectsModeMask))|ExpandedTrait|VerticalTrait|F(?:amilyClassMask|reeformSerifsClass)|Antialiased(?:RenderingMode|IntegerAdvancementsRenderingMode))|cusRing(?:Below|Type(?:None|Default|Exterior)|Only|Above)|urByteGlyphPacking|rm(?:attingError(?:M(?:inimum|aximum))?|FeedCharacter))|8FunctionKey|unction(?:ExpressionType|KeyMask)|3(?:1FunctionKey|2FunctionKey|3FunctionKey|4FunctionKey|5FunctionKey|FunctionKey|0FunctionKey)|9FunctionKey|4FunctionKey|P(?:RevertButton|S(?:ize(?:Title|Field)|etButton)|CurrentField|Preview(?:Button|Field))|l(?:oat(?:ingPointSamplesBitmapFormat|Type)|agsChanged(?:Mask)?)|axButton|5FunctionKey|6FunctionKey)|W(?:heelModeColorPanel|indow(?:s(?:NTOperatingSystem|CP125(?:1StringEncoding|2StringEncoding|3StringEncoding|4StringEncoding|0StringEncoding)|95(?:InterfaceStyle|OperatingSystem))|M(?:iniaturizeButton|ovedEventType)|Below|CloseButton|ToolbarButton|ZoomButton|Out|DocumentIconButton|ExposedEventType|Above)|orkspaceLaunch(?:NewInstance|InhibitingBackgroundOnly|Default|PreferringClassic|WithoutA(?:ctivation|ddingToRecents)|A(?:sync|nd(?:Hide(?:Others)?|Print)|llowingClassicStartup))|eek(?:day(?:CalendarUnit|OrdinalCalendarUnit)|CalendarUnit)|a(?:ntsBidiLevels|rningAlertStyle)|r(?:itingDirection(?:RightToLeft|Natural|LeftToRight)|apCalendarComponents))|L(?:i(?:stModeMatrix|ne(?:Moves(?:Right|Down|Up|Left)|B(?:order|reakBy(?:C(?:harWrapping|lipping)|Truncating(?:Middle|Head|Tail)|WordWrapping))|S(?:eparatorCharacter|weep(?:Right|Down|Up|Left))|ToBezierPathElement|DoesntMove|arSlider)|teralSearch|kePredicateOperatorType|ghterFontAction|braryDirectory)|ocalDomainMask|e(?:ssThan(?:Comparison|OrEqualTo(?:Comparison|PredicateOperatorType)|PredicateOperatorType)|ft(?:Mouse(?:D(?:own(?:Mask)?|ragged(?:Mask)?)|Up(?:Mask)?)|T(?:ext(?:Movement|Alignment)|ab(?:sBezelBorder|StopType))|ArrowFunctionKey))|a(?:yout(?:RightToLeft|NotDone|CantFit|OutOfGlyphs|Done|LeftToRight)|ndscapeOrientation)|ABColorSpaceModel)|A(?:sc(?:iiWithDoubleByteEUCGlyphPacking|endingPageOrder)|n(?:y(?:Type|PredicateModifier|EventMask)|choredSearch|imation(?:Blocking|Nonblocking(?:Threaded)?|E(?:ffect(?:DisappearingItemDefault|Poof)|ase(?:In(?:Out)?|Out))|Linear)|dPredicateType)|t(?:Bottom|tachmentCharacter|omicWrite|Top)|SCIIStringEncoding|d(?:obe(?:GB1CharacterCollection|CNS1CharacterCollection|Japan(?:1CharacterCollection|2CharacterCollection)|Korea1CharacterCollection)|dTraitFontAction|minApplicationDirectory)|uto(?:saveOperation|Pagination)|pp(?:lication(?:SupportDirectory|D(?:irectory|e(?:fined(?:Mask)?|legateReply(?:Success|Cancel|Failure)|activatedEventType))|ActivatedEventType)|KitDefined(?:Mask)?)|l(?:ternateKeyMask|pha(?:ShiftKeyMask|NonpremultipliedBitmapFormat|FirstBitmapFormat)|ert(?:SecondButtonReturn|ThirdButtonReturn|OtherReturn|DefaultReturn|ErrorReturn|FirstButtonReturn|AlternateReturn)|l(?:ScrollerParts|DomainsMask|PredicateModifier|LibrariesDirectory|ApplicationsDirectory))|rgument(?:sWrongScriptError|EvaluationScriptError)|bove(?:Bottom|Top)|WTEventType)))(?:\\\\b)\"},{token:\"support.function.C99.c\",regex:s.cFunctions},{token:n.getKeywords(),regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"punctuation.section.scope.begin.objc\",regex:\"\\\\[\",next:\"bracketed_content\"},{token:\"meta.function.objc\",regex:\"^(?:-|\\\\+)\\\\s*\"}],constant_NSString:[{token:\"constant.character.escape.objc\",regex:e},{token:\"invalid.illegal.unknown-escape.objc\",regex:\"\\\\\\\\.\"},{token:\"string\",regex:'[^\"\\\\\\\\]+'},{token:\"punctuation.definition.string.end\",regex:'\"',next:\"start\"}],protocol_list:[{token:\"punctuation.section.scope.end.objc\",regex:\">\",next:\"start\"},{token:\"support.other.protocol.objc\",regex:\"\\bNS(?:GlyphStorage|M(?:utableCopying|enuItem)|C(?:hangeSpelling|o(?:ding|pying|lorPicking(?:Custom|Default)))|T(?:oolbarItemValidations|ext(?:Input|AttachmentCell))|I(?:nputServ(?:iceProvider|erMouseTracker)|gnoreMisspelledWords)|Obj(?:CTypeSerializationCallBack|ect)|D(?:ecimalNumberBehaviors|raggingInfo)|U(?:serInterfaceValidations|RL(?:HandleClient|DownloadDelegate|ProtocolClient|AuthenticationChallengeSender))|Validated(?:ToobarItem|UserInterfaceItem)|Locking)\\b\"}],selectors:[{token:\"support.function.any-method.name-of-parameter.objc\",regex:\"\\\\b(?:[a-zA-Z_:][\\\\w]*)+\"},{token:\"punctuation\",regex:\"\\\\)\",next:\"start\"}],bracketed_content:[{token:\"punctuation.section.scope.end.objc\",regex:\"]\",next:\"start\"},{token:[\"support.function.any-method.objc\"],regex:\"(?:predicateWithFormat:| NSPredicate predicateWithFormat:)\",next:\"start\"},{token:\"support.function.any-method.objc\",regex:\"\\\\w+(?::|(?=]))\",next:\"start\"}],bracketed_strings:[{token:\"punctuation.section.scope.end.objc\",regex:\"]\",next:\"start\"},{token:\"keyword.operator.logical.predicate.cocoa\",regex:\"\\\\b(?:AND|OR|NOT|IN)\\\\b\"},{token:[\"invalid.illegal.unknown-method.objc\",\"punctuation.separator.arguments.objc\"],regex:\"\\\\b(\\\\w+)(:)\"},{regex:\"\\\\b(?:ALL|ANY|SOME|NONE)\\\\b\",token:\"constant.language.predicate.cocoa\"},{regex:\"\\\\b(?:NULL|NIL|SELF|TRUE|YES|FALSE|NO|FIRST|LAST|SIZE)\\\\b\",token:\"constant.language.predicate.cocoa\"},{regex:\"\\\\b(?:MATCHES|CONTAINS|BEGINSWITH|ENDSWITH|BETWEEN)\\\\b\",token:\"keyword.operator.comparison.predicate.cocoa\"},{regex:\"\\\\bC(?:ASEINSENSITIVE|I)\\\\b\",token:\"keyword.other.modifier.predicate.cocoa\"},{regex:\"\\\\b(?:ANYKEY|SUBQUERY|CAST|TRUEPREDICATE|FALSEPREDICATE)\\\\b\",token:\"keyword.other.predicate.cocoa\"},{regex:e,token:\"constant.character.escape.objc\"},{regex:\"\\\\\\\\.\",token:\"invalid.illegal.unknown-escape.objc\"},{token:\"string\",regex:'[^\"\\\\\\\\]'},{token:\"punctuation.definition.string.end.objc\",regex:'\"',next:\"predicates\"}],comment:[{token:\"comment\",regex:\".*?\\\\*\\\\/\",next:\"start\"},{token:\"comment\",regex:\".+\"}],methods:[{token:\"meta.function.objc\",regex:\"(?=\\\\{|#)|;\",next:\"start\"}]};for(var u in r)this.$rules[u]?this.$rules[u].push&&this.$rules[u].push.apply(this.$rules[u],r[u]):this.$rules[u]=r[u];this.$rules.bracketed_content=this.$rules.bracketed_content.concat(this.$rules.start,t),this.embedRules(i,\"doc-\",[i.getEndRule(\"start\")])};r.inherits(u,o),t.ObjectiveCHighlightRules=u}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/objectivec\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/objectivec_highlight_rules\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./objectivec_highlight_rules\").ObjectiveCHighlightRules,o=e(\"./folding/cstyle\").FoldMode,u=function(){this.HighlightRules=s,this.foldingRules=new o,this.$behaviour=this.$defaultBehaviour};r.inherits(u,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\"},this.$id=\"ace/mode/objectivec\"}.call(u.prototype),t.Mode=u})\n"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-perl.js",
    "content": "define(\"ace/mode/perl_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){var e=\"base|constant|continue|else|elsif|for|foreach|format|goto|if|last|local|my|next|no|package|parent|redo|require|scalar|sub|unless|until|while|use|vars\",t=\"ARGV|ENV|INC|SIG\",n=\"getprotobynumber|getprotobyname|getservbyname|gethostbyaddr|gethostbyname|getservbyport|getnetbyaddr|getnetbyname|getsockname|getpeername|setpriority|getprotoent|setprotoent|getpriority|endprotoent|getservent|setservent|endservent|sethostent|socketpair|getsockopt|gethostent|endhostent|setsockopt|setnetent|quotemeta|localtime|prototype|getnetent|endnetent|rewinddir|wantarray|getpwuid|closedir|getlogin|readlink|endgrent|getgrgid|getgrnam|shmwrite|shutdown|readline|endpwent|setgrent|readpipe|formline|truncate|dbmclose|syswrite|setpwent|getpwnam|getgrent|getpwent|ucfirst|sysread|setpgrp|shmread|sysseek|sysopen|telldir|defined|opendir|connect|lcfirst|getppid|binmode|syscall|sprintf|getpgrp|readdir|seekdir|waitpid|reverse|unshift|symlink|dbmopen|semget|msgrcv|rename|listen|chroot|msgsnd|shmctl|accept|unpack|exists|fileno|shmget|system|unlink|printf|gmtime|msgctl|semctl|values|rindex|substr|splice|length|msgget|select|socket|return|caller|delete|alarm|ioctl|index|undef|lstat|times|srand|chown|fcntl|close|write|umask|rmdir|study|sleep|chomp|untie|print|utime|mkdir|atan2|split|crypt|flock|chmod|BEGIN|bless|chdir|semop|shift|reset|link|stat|chop|grep|fork|dump|join|open|tell|pipe|exit|glob|warn|each|bind|sort|pack|eval|push|keys|getc|kill|seek|sqrt|send|wait|rand|tied|read|time|exec|recv|eof|chr|int|ord|exp|pos|pop|sin|log|abs|oct|hex|tie|cos|vec|END|ref|map|die|uc|lc|do\",r=this.createKeywordMapper({keyword:e,\"constant.language\":t,\"support.function\":n},\"identifier\");this.$rules={start:[{token:\"comment.doc\",regex:\"^=(?:begin|item)\\\\b\",next:\"block_comment\"},{token:\"string.regexp\",regex:\"[/](?:(?:\\\\[(?:\\\\\\\\]|[^\\\\]])+\\\\])|(?:\\\\\\\\/|[^\\\\]/]))*[/]\\\\w*\\\\s*(?=[).,;]|$)\"},{token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},{token:\"string\",regex:'[\"].*\\\\\\\\$',next:\"qqstring\"},{token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},{token:\"string\",regex:\"['].*\\\\\\\\$\",next:\"qstring\"},{token:\"constant.numeric\",regex:\"0x[0-9a-fA-F]+\\\\b\"},{token:\"constant.numeric\",regex:\"[+-]?\\\\d+(?:(?:\\\\.\\\\d*)?(?:[eE][+-]?\\\\d+)?)?\\\\b\"},{token:r,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"keyword.operator\",regex:\"%#|\\\\$#|\\\\.\\\\.\\\\.|\\\\|\\\\|=|>>=|<<=|<=>|&&=|=>|!~|\\\\^=|&=|\\\\|=|\\\\.=|x=|%=|\\\\/=|\\\\*=|\\\\-=|\\\\+=|=~|\\\\*\\\\*|\\\\-\\\\-|\\\\.\\\\.|\\\\|\\\\||&&|\\\\+\\\\+|\\\\->|!=|==|>=|<=|>>|<<|,|=|\\\\?\\\\:|\\\\^|\\\\||x|%|\\\\/|\\\\*|<|&|\\\\\\\\|~|!|>|\\\\.|\\\\-|\\\\+|\\\\-C|\\\\-b|\\\\-S|\\\\-u|\\\\-t|\\\\-p|\\\\-l|\\\\-d|\\\\-f|\\\\-g|\\\\-s|\\\\-z|\\\\-k|\\\\-e|\\\\-O|\\\\-T|\\\\-B|\\\\-M|\\\\-A|\\\\-X|\\\\-W|\\\\-c|\\\\-R|\\\\-o|\\\\-x|\\\\-w|\\\\-r|\\\\b(?:and|cmp|eq|ge|gt|le|lt|ne|not|or|xor)\"},{token:\"comment\",regex:\"#.*$\"},{token:\"lparen\",regex:\"[[({]\"},{token:\"rparen\",regex:\"[\\\\])}]\"},{token:\"text\",regex:\"\\\\s+\"}],qqstring:[{token:\"string\",regex:'(?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?\"',next:\"start\"},{token:\"string\",regex:\".+\"}],qstring:[{token:\"string\",regex:\"(?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?'\",next:\"start\"},{token:\"string\",regex:\".+\"}],block_comment:[{token:\"comment.doc\",regex:\"^=cut\\\\b\",next:\"start\"},{defaultToken:\"comment.doc\"}]}};r.inherits(s,i),t.PerlHighlightRules=s}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/perl\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/perl_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./perl_highlight_rules\").PerlHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"./folding/cstyle\").FoldMode,a=function(){this.HighlightRules=s,this.$outdent=new o,this.foldingRules=new u({start:\"^=(begin|item)\\\\b\",end:\"^=(cut)\\\\b\"}),this.$behaviour=this.$defaultBehaviour};r.inherits(a,i),function(){this.lineCommentStart=\"#\",this.blockComment=[{start:\"=begin\",end:\"=cut\",lineStartOnly:!0},{start:\"=item\",end:\"=cut\",lineStartOnly:!0}],this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"){var o=t.match(/^.*[\\{\\(\\[:]\\s*$/);o&&(r+=n)}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.$id=\"ace/mode/perl\"}.call(a.prototype),t.Mode=a})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-php.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/css_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text_highlight_rules\").TextHighlightRules,o=t.supportType=\"align-content|align-items|align-self|all|animation|animation-delay|animation-direction|animation-duration|animation-fill-mode|animation-iteration-count|animation-name|animation-play-state|animation-timing-function|backface-visibility|background|background-attachment|background-blend-mode|background-clip|background-color|background-image|background-origin|background-position|background-repeat|background-size|border|border-bottom|border-bottom-color|border-bottom-left-radius|border-bottom-right-radius|border-bottom-style|border-bottom-width|border-collapse|border-color|border-image|border-image-outset|border-image-repeat|border-image-slice|border-image-source|border-image-width|border-left|border-left-color|border-left-style|border-left-width|border-radius|border-right|border-right-color|border-right-style|border-right-width|border-spacing|border-style|border-top|border-top-color|border-top-left-radius|border-top-right-radius|border-top-style|border-top-width|border-width|bottom|box-shadow|box-sizing|caption-side|clear|clip|color|column-count|column-fill|column-gap|column-rule|column-rule-color|column-rule-style|column-rule-width|column-span|column-width|columns|content|counter-increment|counter-reset|cursor|direction|display|empty-cells|filter|flex|flex-basis|flex-direction|flex-flow|flex-grow|flex-shrink|flex-wrap|float|font|font-family|font-size|font-size-adjust|font-stretch|font-style|font-variant|font-weight|hanging-punctuation|height|justify-content|left|letter-spacing|line-height|list-style|list-style-image|list-style-position|list-style-type|margin|margin-bottom|margin-left|margin-right|margin-top|max-height|max-width|min-height|min-width|nav-down|nav-index|nav-left|nav-right|nav-up|opacity|order|outline|outline-color|outline-offset|outline-style|outline-width|overflow|overflow-x|overflow-y|padding|padding-bottom|padding-left|padding-right|padding-top|page-break-after|page-break-before|page-break-inside|perspective|perspective-origin|position|quotes|resize|right|tab-size|table-layout|text-align|text-align-last|text-decoration|text-decoration-color|text-decoration-line|text-decoration-style|text-indent|text-justify|text-overflow|text-shadow|text-transform|top|transform|transform-origin|transform-style|transition|transition-delay|transition-duration|transition-property|transition-timing-function|unicode-bidi|vertical-align|visibility|white-space|width|word-break|word-spacing|word-wrap|z-index\",u=t.supportFunction=\"rgb|rgba|url|attr|counter|counters\",a=t.supportConstant=\"absolute|after-edge|after|all-scroll|all|alphabetic|always|antialiased|armenian|auto|avoid-column|avoid-page|avoid|balance|baseline|before-edge|before|below|bidi-override|block-line-height|block|bold|bolder|border-box|both|bottom|box|break-all|break-word|capitalize|caps-height|caption|center|central|char|circle|cjk-ideographic|clone|close-quote|col-resize|collapse|column|consider-shifts|contain|content-box|cover|crosshair|cubic-bezier|dashed|decimal-leading-zero|decimal|default|disabled|disc|disregard-shifts|distribute-all-lines|distribute-letter|distribute-space|distribute|dotted|double|e-resize|ease-in|ease-in-out|ease-out|ease|ellipsis|end|exclude-ruby|fill|fixed|georgian|glyphs|grid-height|groove|hand|hanging|hebrew|help|hidden|hiragana-iroha|hiragana|horizontal|icon|ideograph-alpha|ideograph-numeric|ideograph-parenthesis|ideograph-space|ideographic|inactive|include-ruby|inherit|initial|inline-block|inline-box|inline-line-height|inline-table|inline|inset|inside|inter-ideograph|inter-word|invert|italic|justify|katakana-iroha|katakana|keep-all|last|left|lighter|line-edge|line-through|line|linear|list-item|local|loose|lower-alpha|lower-greek|lower-latin|lower-roman|lowercase|lr-tb|ltr|mathematical|max-height|max-size|medium|menu|message-box|middle|move|n-resize|ne-resize|newspaper|no-change|no-close-quote|no-drop|no-open-quote|no-repeat|none|normal|not-allowed|nowrap|nw-resize|oblique|open-quote|outset|outside|overline|padding-box|page|pointer|pre-line|pre-wrap|pre|preserve-3d|progress|relative|repeat-x|repeat-y|repeat|replaced|reset-size|ridge|right|round|row-resize|rtl|s-resize|scroll|se-resize|separate|slice|small-caps|small-caption|solid|space|square|start|static|status-bar|step-end|step-start|steps|stretch|strict|sub|super|sw-resize|table-caption|table-cell|table-column-group|table-column|table-footer-group|table-header-group|table-row-group|table-row|table|tb-rl|text-after-edge|text-before-edge|text-bottom|text-size|text-top|text|thick|thin|transparent|underline|upper-alpha|upper-latin|upper-roman|uppercase|use-script|vertical-ideographic|vertical-text|visible|w-resize|wait|whitespace|z-index|zero\",f=t.supportConstantColor=\"aqua|black|blue|fuchsia|gray|green|lime|maroon|navy|olive|orange|purple|red|silver|teal|white|yellow\",l=t.supportConstantFonts=\"arial|century|comic|courier|cursive|fantasy|garamond|georgia|helvetica|impact|lucida|symbol|system|tahoma|times|trebuchet|utopia|verdana|webdings|sans-serif|serif|monospace\",c=t.numRe=\"\\\\-?(?:(?:[0-9]+)|(?:[0-9]*\\\\.[0-9]+))\",h=t.pseudoElements=\"(\\\\:+)\\\\b(after|before|first-letter|first-line|moz-selection|selection)\\\\b\",p=t.pseudoClasses=\"(:)\\\\b(active|checked|disabled|empty|enabled|first-child|first-of-type|focus|hover|indeterminate|invalid|last-child|last-of-type|link|not|nth-child|nth-last-child|nth-last-of-type|nth-of-type|only-child|only-of-type|required|root|target|valid|visited)\\\\b\",d=function(){var e=this.createKeywordMapper({\"support.function\":u,\"support.constant\":a,\"support.type\":o,\"support.constant.color\":f,\"support.constant.fonts\":l},\"text\",!0);this.$rules={start:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"@.*?{\",push:\"media\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],media:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"\\\\}\",next:\"pop\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],comment:[{token:\"comment\",regex:\"\\\\*\\\\/\",next:\"pop\"},{defaultToken:\"comment\"}],ruleset:[{token:\"paren.rparen\",regex:\"\\\\}\",next:\"pop\"},{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},{token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},{token:[\"constant.numeric\",\"keyword\"],regex:\"(\"+c+\")(ch|cm|deg|em|ex|fr|gd|grad|Hz|in|kHz|mm|ms|pc|pt|px|rad|rem|s|turn|vh|vm|vw|%)\"},{token:\"constant.numeric\",regex:c},{token:\"constant.numeric\",regex:\"#[a-f0-9]{6}\"},{token:\"constant.numeric\",regex:\"#[a-f0-9]{3}\"},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-element.css\"],regex:h},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-class.css\"],regex:p},{token:[\"support.function\",\"string\",\"support.function\"],regex:\"(url\\\\()(.*)(\\\\))\"},{token:e,regex:\"\\\\-?[a-zA-Z_][a-zA-Z0-9_\\\\-]*\"},{caseInsensitive:!0}]},this.normalizeRules()};r.inherits(d,s),t.CssHighlightRules=d}),define(\"ace/mode/javascript_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";function a(){var e=o.replace(\"\\\\d\",\"\\\\d\\\\-\"),t={onMatch:function(e,t,n){var r=e.charAt(1)==\"/\"?2:1;if(r==1)t!=this.nextState?n.unshift(this.next,this.nextState,0):n.unshift(this.next),n[2]++;else if(r==2&&t==this.nextState){n[1]--;if(!n[1]||n[1]<0)n.shift(),n.shift()}return[{type:\"meta.tag.punctuation.\"+(r==1?\"\":\"end-\")+\"tag-open.xml\",value:e.slice(0,r)},{type:\"meta.tag.tag-name.xml\",value:e.substr(r)}]},regex:\"</?\"+e+\"\",next:\"jsxAttributes\",nextState:\"jsx\"};this.$rules.start.unshift(t);var n={regex:\"{\",token:\"paren.quasi.start\",push:\"start\"};this.$rules.jsx=[n,t,{include:\"reference\"},{defaultToken:\"string\"}],this.$rules.jsxAttributes=[{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",onMatch:function(e,t,n){return t==n[0]&&n.shift(),e.length==2&&(n[0]==this.nextState&&n[1]--,(!n[1]||n[1]<0)&&n.splice(0,2)),this.next=n[0]||\"start\",[{type:this.token,value:e}]},nextState:\"jsx\"},n,f(\"jsxAttributes\"),{token:\"entity.other.attribute-name.xml\",regex:e},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"},{token:\"string.attribute-value.xml\",regex:\"'\",stateName:\"jsx_attr_q\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',stateName:\"jsx_attr_qq\",push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},t],this.$rules.reference=[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}]}function f(e){return[{token:\"comment\",regex:/\\/\\*/,next:[i.getTagRule(),{token:\"comment\",regex:\"\\\\*\\\\/\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]},{token:\"comment\",regex:\"\\\\/\\\\/\",next:[i.getTagRule(),{token:\"comment\",regex:\"$|^\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]}]}var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=\"[a-zA-Z\\\\$_\\u00a1-\\uffff][a-zA-Z\\\\d\\\\$_\\u00a1-\\uffff]*\",u=function(e){var t=this.createKeywordMapper({\"variable.language\":\"Array|Boolean|Date|Function|Iterator|Number|Object|RegExp|String|Proxy|Namespace|QName|XML|XMLList|ArrayBuffer|Float32Array|Float64Array|Int16Array|Int32Array|Int8Array|Uint16Array|Uint32Array|Uint8Array|Uint8ClampedArray|Error|EvalError|InternalError|RangeError|ReferenceError|StopIteration|SyntaxError|TypeError|URIError|decodeURI|decodeURIComponent|encodeURI|encodeURIComponent|eval|isFinite|isNaN|parseFloat|parseInt|JSON|Math|this|arguments|prototype|window|document\",keyword:\"const|yield|import|get|set|async|await|break|case|catch|continue|default|delete|do|else|finally|for|function|if|in|of|instanceof|new|return|switch|throw|try|typeof|let|var|while|with|debugger|__parent__|__count__|escape|unescape|with|__proto__|class|enum|extends|super|export|implements|private|public|interface|package|protected|static\",\"storage.type\":\"const|let|var|function\",\"constant.language\":\"null|Infinity|NaN|undefined\",\"support.function\":\"alert\",\"constant.language.boolean\":\"true|false\"},\"identifier\"),n=\"case|do|else|finally|in|instanceof|return|throw|try|typeof|yield|void\",r=\"\\\\\\\\(?:x[0-9a-fA-F]{2}|u[0-9a-fA-F]{4}|u{[0-9a-fA-F]{1,6}}|[0-2][0-7]{0,2}|3[0-7][0-7]?|[4-7][0-7]?|.)\";this.$rules={no_regex:[i.getStartRule(\"doc-start\"),f(\"no_regex\"),{token:\"string\",regex:\"'(?=.)\",next:\"qstring\"},{token:\"string\",regex:'\"(?=.)',next:\"qqstring\"},{token:\"constant.numeric\",regex:/0(?:[xX][0-9a-fA-F]+|[bB][01]+)\\b/},{token:\"constant.numeric\",regex:/[+-]?\\d[\\d_]*(?:(?:\\.\\d*)?(?:[eE][+-]?\\d+)?)?\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\"],regex:\"(\"+o+\")(\\\\.)(prototype)(\\\\.)(\"+o+\")(\\\\s*)(=)\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s+)(\\\\w+)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(function)(\\\\s+)(\"+o+\")(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"punctuation.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"text\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"keyword\",regex:\"(?:\"+n+\")\\\\b\",next:\"start\"},{token:[\"support.constant\"],regex:/that\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function.firebug\"],regex:/(console)(\\.)(warn|info|log|error|time|trace|timeEnd|assert)\\b/},{token:t,regex:o},{token:\"punctuation.operator\",regex:/[.](?![.])/,next:\"property\"},{token:\"keyword.operator\",regex:/--|\\+\\+|\\.{3}|===|==|=|!=|!==|<+=?|>+=?|!|&&|\\|\\||\\?:|[!$%&*+\\-~\\/^]=?/,next:\"start\"},{token:\"punctuation.operator\",regex:/[?:,;.]/,next:\"start\"},{token:\"paren.lparen\",regex:/[\\[({]/,next:\"start\"},{token:\"paren.rparen\",regex:/[\\])}]/},{token:\"comment\",regex:/^#!.*$/}],property:[{token:\"text\",regex:\"\\\\s+\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(?:(\\\\s+)(\\\\w+))?(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"punctuation.operator\",regex:/[.](?![.])/},{token:\"support.function\",regex:/(s(?:h(?:ift|ow(?:Mod(?:elessDialog|alDialog)|Help))|croll(?:X|By(?:Pages|Lines)?|Y|To)?|t(?:op|rike)|i(?:n|zeToContent|debar|gnText)|ort|u(?:p|b(?:str(?:ing)?)?)|pli(?:ce|t)|e(?:nd|t(?:Re(?:sizable|questHeader)|M(?:i(?:nutes|lliseconds)|onth)|Seconds|Ho(?:tKeys|urs)|Year|Cursor|Time(?:out)?|Interval|ZOptions|Date|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Date|FullYear)|FullYear|Active)|arch)|qrt|lice|avePreferences|mall)|h(?:ome|andleEvent)|navigate|c(?:har(?:CodeAt|At)|o(?:s|n(?:cat|textual|firm)|mpile)|eil|lear(?:Timeout|Interval)?|a(?:ptureEvents|ll)|reate(?:StyleSheet|Popup|EventObject))|t(?:o(?:GMTString|S(?:tring|ource)|U(?:TCString|pperCase)|Lo(?:caleString|werCase))|est|a(?:n|int(?:Enabled)?))|i(?:s(?:NaN|Finite)|ndexOf|talics)|d(?:isableExternalCapture|ump|etachEvent)|u(?:n(?:shift|taint|escape|watch)|pdateCommands)|j(?:oin|avaEnabled)|p(?:o(?:p|w)|ush|lugins.refresh|a(?:ddings|rse(?:Int|Float)?)|r(?:int|ompt|eference))|e(?:scape|nableExternalCapture|val|lementFromPoint|x(?:p|ec(?:Script|Command)?))|valueOf|UTC|queryCommand(?:State|Indeterm|Enabled|Value)|f(?:i(?:nd|le(?:ModifiedDate|Size|CreatedDate|UpdatedDate)|xed)|o(?:nt(?:size|color)|rward)|loor|romCharCode)|watch|l(?:ink|o(?:ad|g)|astIndexOf)|a(?:sin|nchor|cos|t(?:tachEvent|ob|an(?:2)?)|pply|lert|b(?:s|ort))|r(?:ou(?:nd|teEvents)|e(?:size(?:By|To)|calc|turnValue|place|verse|l(?:oad|ease(?:Capture|Events)))|andom)|g(?:o|et(?:ResponseHeader|M(?:i(?:nutes|lliseconds)|onth)|Se(?:conds|lection)|Hours|Year|Time(?:zoneOffset)?|Da(?:y|te)|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Da(?:y|te)|FullYear)|FullYear|A(?:ttention|llResponseHeaders)))|m(?:in|ove(?:B(?:y|elow)|To(?:Absolute)?|Above)|ergeAttributes|a(?:tch|rgins|x))|b(?:toa|ig|o(?:ld|rderWidths)|link|ack))\\b(?=\\()/},{token:\"support.function.dom\",regex:/(s(?:ub(?:stringData|mit)|plitText|e(?:t(?:NamedItem|Attribute(?:Node)?)|lect))|has(?:ChildNodes|Feature)|namedItem|c(?:l(?:ick|o(?:se|neNode))|reate(?:C(?:omment|DATASection|aption)|T(?:Head|extNode|Foot)|DocumentFragment|ProcessingInstruction|E(?:ntityReference|lement)|Attribute))|tabIndex|i(?:nsert(?:Row|Before|Cell|Data)|tem)|open|delete(?:Row|C(?:ell|aption)|T(?:Head|Foot)|Data)|focus|write(?:ln)?|a(?:dd|ppend(?:Child|Data))|re(?:set|place(?:Child|Data)|move(?:NamedItem|Child|Attribute(?:Node)?)?)|get(?:NamedItem|Element(?:sBy(?:Name|TagName|ClassName)|ById)|Attribute(?:Node)?)|blur)\\b(?=\\()/},{token:\"support.constant\",regex:/(s(?:ystemLanguage|cr(?:ipts|ollbars|een(?:X|Y|Top|Left))|t(?:yle(?:Sheets)?|atus(?:Text|bar)?)|ibling(?:Below|Above)|ource|uffixes|e(?:curity(?:Policy)?|l(?:ection|f)))|h(?:istory|ost(?:name)?|as(?:h|Focus))|y|X(?:MLDocument|SLDocument)|n(?:ext|ame(?:space(?:s|URI)|Prop))|M(?:IN_VALUE|AX_VALUE)|c(?:haracterSet|o(?:n(?:structor|trollers)|okieEnabled|lorDepth|mp(?:onents|lete))|urrent|puClass|l(?:i(?:p(?:boardData)?|entInformation)|osed|asses)|alle(?:e|r)|rypto)|t(?:o(?:olbar|p)|ext(?:Transform|Indent|Decoration|Align)|ags)|SQRT(?:1_2|2)|i(?:n(?:ner(?:Height|Width)|put)|ds|gnoreCase)|zIndex|o(?:scpu|n(?:readystatechange|Line)|uter(?:Height|Width)|p(?:sProfile|ener)|ffscreenBuffering)|NEGATIVE_INFINITY|d(?:i(?:splay|alog(?:Height|Top|Width|Left|Arguments)|rectories)|e(?:scription|fault(?:Status|Ch(?:ecked|arset)|View)))|u(?:ser(?:Profile|Language|Agent)|n(?:iqueID|defined)|pdateInterval)|_content|p(?:ixelDepth|ort|ersonalbar|kcs11|l(?:ugins|atform)|a(?:thname|dding(?:Right|Bottom|Top|Left)|rent(?:Window|Layer)?|ge(?:X(?:Offset)?|Y(?:Offset)?))|r(?:o(?:to(?:col|type)|duct(?:Sub)?|mpter)|e(?:vious|fix)))|e(?:n(?:coding|abledPlugin)|x(?:ternal|pando)|mbeds)|v(?:isibility|endor(?:Sub)?|Linkcolor)|URLUnencoded|P(?:I|OSITIVE_INFINITY)|f(?:ilename|o(?:nt(?:Size|Family|Weight)|rmName)|rame(?:s|Element)|gColor)|E|whiteSpace|l(?:i(?:stStyleType|n(?:eHeight|kColor))|o(?:ca(?:tion(?:bar)?|lName)|wsrc)|e(?:ngth|ft(?:Context)?)|a(?:st(?:M(?:odified|atch)|Index|Paren)|yer(?:s|X)|nguage))|a(?:pp(?:MinorVersion|Name|Co(?:deName|re)|Version)|vail(?:Height|Top|Width|Left)|ll|r(?:ity|guments)|Linkcolor|bove)|r(?:ight(?:Context)?|e(?:sponse(?:XML|Text)|adyState))|global|x|m(?:imeTypes|ultiline|enubar|argin(?:Right|Bottom|Top|Left))|L(?:N(?:10|2)|OG(?:10E|2E))|b(?:o(?:ttom|rder(?:Width|RightWidth|BottomWidth|Style|Color|TopWidth|LeftWidth))|ufferDepth|elow|ackground(?:Color|Image)))\\b/},{token:\"identifier\",regex:o},{regex:\"\",token:\"empty\",next:\"no_regex\"}],start:[i.getStartRule(\"doc-start\"),f(\"start\"),{token:\"string.regexp\",regex:\"\\\\/\",next:\"regex\"},{token:\"text\",regex:\"\\\\s+|^$\",next:\"start\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],regex:[{token:\"regexp.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"string.regexp\",regex:\"/[sxngimy]*\",next:\"no_regex\"},{token:\"invalid\",regex:/\\{\\d+\\b,?\\d*\\}[+*]|[+*$^?][+*]|[$^][?]|\\?{3,}/},{token:\"constant.language.escape\",regex:/\\(\\?[:=!]|\\)|\\{\\d+\\b,?\\d*\\}|[+*]\\?|[()$^+*?.]/},{token:\"constant.language.delimiter\",regex:/\\|/},{token:\"constant.language.escape\",regex:/\\[\\^?/,next:\"regex_character_class\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp\"}],regex_character_class:[{token:\"regexp.charclass.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"constant.language.escape\",regex:\"]\",next:\"regex\"},{token:\"constant.language.escape\",regex:\"-\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp.charachterclass\"}],function_arguments:[{token:\"variable.parameter\",regex:o},{token:\"punctuation.operator\",regex:\"[, ]+\"},{token:\"punctuation.operator\",regex:\"$\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],qqstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qqstring\"},{token:\"string\",regex:'\"|$',next:\"no_regex\"},{defaultToken:\"string\"}],qstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qstring\"},{token:\"string\",regex:\"'|$\",next:\"no_regex\"},{defaultToken:\"string\"}]};if(!e||!e.noES6)this.$rules.no_regex.unshift({regex:\"[{}]\",onMatch:function(e,t,n){this.next=e==\"{\"?this.nextState:\"\";if(e==\"{\"&&n.length)n.unshift(\"start\",t);else if(e==\"}\"&&n.length){n.shift(),this.next=n.shift();if(this.next.indexOf(\"string\")!=-1||this.next.indexOf(\"jsx\")!=-1)return\"paren.quasi.end\"}return e==\"{\"?\"paren.lparen\":\"paren.rparen\"},nextState:\"start\"},{token:\"string.quasi.start\",regex:/`/,push:[{token:\"constant.language.escape\",regex:r},{token:\"paren.quasi.start\",regex:/\\${/,push:\"start\"},{token:\"string.quasi.end\",regex:/`/,next:\"pop\"},{defaultToken:\"string.quasi\"}]}),(!e||e.jsx!=0)&&a.call(this);this.embedRules(i,\"doc-\",[i.getEndRule(\"no_regex\")]),this.normalizeRules()};r.inherits(u,s),t.JavaScriptHighlightRules=u}),define(\"ace/mode/xml_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(e){var t=\"[_:a-zA-Z\\u00c0-\\uffff][-_:.a-zA-Z0-9\\u00c0-\\uffff]*\";this.$rules={start:[{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\",next:\"cdata\"},{token:[\"punctuation.xml-decl.xml\",\"keyword.xml-decl.xml\"],regex:\"(<\\\\?)(xml)(?=[\\\\s])\",next:\"xml_decl\",caseInsensitive:!0},{token:[\"punctuation.instruction.xml\",\"keyword.instruction.xml\"],regex:\"(<\\\\?)(\"+t+\")\",next:\"processing_instruction\"},{token:\"comment.xml\",regex:\"<\\\\!--\",next:\"comment\"},{token:[\"xml-pe.doctype.xml\",\"xml-pe.doctype.xml\"],regex:\"(<\\\\!)(DOCTYPE)(?=[\\\\s])\",next:\"doctype\",caseInsensitive:!0},{include:\"tag\"},{token:\"text.end-tag-open.xml\",regex:\"</\"},{token:\"text.tag-open.xml\",regex:\"<\"},{include:\"reference\"},{defaultToken:\"text.xml\"}],xml_decl:[{token:\"entity.other.attribute-name.decl-attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.decl-attribute-equals.xml\",regex:\"=\"},{include:\"whitespace\"},{include:\"string\"},{token:\"punctuation.xml-decl.xml\",regex:\"\\\\?>\",next:\"start\"}],processing_instruction:[{token:\"punctuation.instruction.xml\",regex:\"\\\\?>\",next:\"start\"},{defaultToken:\"instruction.xml\"}],doctype:[{include:\"whitespace\"},{include:\"string\"},{token:\"xml-pe.doctype.xml\",regex:\">\",next:\"start\"},{token:\"xml-pe.xml\",regex:\"[-_a-zA-Z0-9:]+\"},{token:\"punctuation.int-subset\",regex:\"\\\\[\",push:\"int_subset\"}],int_subset:[{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"punctuation.int-subset.xml\",regex:\"]\",next:\"pop\"},{token:[\"punctuation.markup-decl.xml\",\"keyword.markup-decl.xml\"],regex:\"(<\\\\!)(\"+t+\")\",push:[{token:\"text\",regex:\"\\\\s+\"},{token:\"punctuation.markup-decl.xml\",regex:\">\",next:\"pop\"},{include:\"string\"}]}],cdata:[{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\",next:\"start\"},{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"text.xml\",regex:\"(?:[^\\\\]]|\\\\](?!\\\\]>))+\"}],comment:[{token:\"comment.xml\",regex:\"-->\",next:\"start\"},{defaultToken:\"comment.xml\"}],reference:[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],attr_reference:[{token:\"constant.language.escape.reference.attribute-value.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],tag:[{token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.tag-name.xml\"],regex:\"(?:(<)|(</))((?:\"+t+\":)?\"+t+\")\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}],tag_whitespace:[{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"}],whitespace:[{token:\"text.whitespace.xml\",regex:\"\\\\s+\"}],string:[{token:\"string.xml\",regex:\"'\",push:[{token:\"string.xml\",regex:\"'\",next:\"pop\"},{defaultToken:\"string.xml\"}]},{token:\"string.xml\",regex:'\"',push:[{token:\"string.xml\",regex:'\"',next:\"pop\"},{defaultToken:\"string.xml\"}]}],attributes:[{token:\"entity.other.attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{include:\"tag_whitespace\"},{include:\"attribute_value\"}],attribute_value:[{token:\"string.attribute-value.xml\",regex:\"'\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]}]},this.constructor===s&&this.normalizeRules()};(function(){this.embedTagRules=function(e,t,n){this.$rules.tag.unshift({token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(<)(\"+n+\"(?=\\\\s|>|$))\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:t+\"start\"}]}),this.$rules[n+\"-end\"]=[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\",onMatch:function(e,t,n){return n.splice(0),this.token}}],this.embedRules(e,t,[{token:[\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(</)(\"+n+\"(?=\\\\s|>|$))\",next:n+\"-end\"},{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\"},{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\"}])}}).call(i.prototype),r.inherits(s,i),t.XmlHighlightRules=s}),define(\"ace/mode/html_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/css_highlight_rules\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/xml_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./css_highlight_rules\").CssHighlightRules,o=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,u=e(\"./xml_highlight_rules\").XmlHighlightRules,a=i.createMap({a:\"anchor\",button:\"form\",form:\"form\",img:\"image\",input:\"form\",label:\"form\",option:\"form\",script:\"script\",select:\"form\",textarea:\"form\",style:\"style\",table:\"table\",tbody:\"table\",td:\"table\",tfoot:\"table\",th:\"table\",tr:\"table\"}),f=function(){u.call(this),this.addRules({attributes:[{include:\"tag_whitespace\"},{token:\"entity.other.attribute-name.xml\",regex:\"[-_a-zA-Z0-9:.]+\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\",push:[{include:\"tag_whitespace\"},{token:\"string.unquoted.attribute-value.html\",regex:\"[^<>='\\\"`\\\\s]+\",next:\"pop\"},{token:\"empty\",regex:\"\",next:\"pop\"}]},{include:\"attribute_value\"}],tag:[{token:function(e,t){var n=a[t];return[\"meta.tag.punctuation.\"+(e==\"<\"?\"\":\"end-\")+\"tag-open.xml\",\"meta.tag\"+(n?\".\"+n:\"\")+\".tag-name.xml\"]},regex:\"(</?)([-_a-zA-Z0-9:.]+)\",next:\"tag_stuff\"}],tag_stuff:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}),this.embedTagRules(s,\"css-\",\"style\"),this.embedTagRules((new o({jsx:!1})).getRules(),\"js-\",\"script\"),this.constructor===f&&this.normalizeRules()};r.inherits(f,u),t.HtmlHighlightRules=f}),define(\"ace/mode/php_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\",\"ace/mode/html_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,o=e(\"./text_highlight_rules\").TextHighlightRules,u=e(\"./html_highlight_rules\").HtmlHighlightRules,a=function(){var e=s,t=i.arrayToMap(\"abs|acos|acosh|addcslashes|addslashes|aggregate|aggregate_info|aggregate_methods|aggregate_methods_by_list|aggregate_methods_by_regexp|aggregate_properties|aggregate_properties_by_list|aggregate_properties_by_regexp|aggregation_info|amqpconnection|amqpexchange|amqpqueue|apache_child_terminate|apache_get_modules|apache_get_version|apache_getenv|apache_lookup_uri|apache_note|apache_request_headers|apache_reset_timeout|apache_response_headers|apache_setenv|apc_add|apc_bin_dump|apc_bin_dumpfile|apc_bin_load|apc_bin_loadfile|apc_cache_info|apc_cas|apc_clear_cache|apc_compile_file|apc_dec|apc_define_constants|apc_delete|apc_delete_file|apc_exists|apc_fetch|apc_inc|apc_load_constants|apc_sma_info|apc_store|apciterator|apd_breakpoint|apd_callstack|apd_clunk|apd_continue|apd_croak|apd_dump_function_table|apd_dump_persistent_resources|apd_dump_regular_resources|apd_echo|apd_get_active_symbols|apd_set_pprof_trace|apd_set_session|apd_set_session_trace|apd_set_session_trace_socket|appenditerator|array|array_change_key_case|array_chunk|array_combine|array_count_values|array_diff|array_diff_assoc|array_diff_key|array_diff_uassoc|array_diff_ukey|array_fill|array_fill_keys|array_filter|array_flip|array_intersect|array_intersect_assoc|array_intersect_key|array_intersect_uassoc|array_intersect_ukey|array_key_exists|array_keys|array_map|array_merge|array_merge_recursive|array_multisort|array_pad|array_pop|array_product|array_push|array_rand|array_reduce|array_replace|array_replace_recursive|array_reverse|array_search|array_shift|array_slice|array_splice|array_sum|array_udiff|array_udiff_assoc|array_udiff_uassoc|array_uintersect|array_uintersect_assoc|array_uintersect_uassoc|array_unique|array_unshift|array_values|array_walk|array_walk_recursive|arrayaccess|arrayiterator|arrayobject|arsort|asin|asinh|asort|assert|assert_options|atan|atan2|atanh|audioproperties|badfunctioncallexception|badmethodcallexception|base64_decode|base64_encode|base_convert|basename|bbcode_add_element|bbcode_add_smiley|bbcode_create|bbcode_destroy|bbcode_parse|bbcode_set_arg_parser|bbcode_set_flags|bcadd|bccomp|bcdiv|bcmod|bcmul|bcompiler_load|bcompiler_load_exe|bcompiler_parse_class|bcompiler_read|bcompiler_write_class|bcompiler_write_constant|bcompiler_write_exe_footer|bcompiler_write_file|bcompiler_write_footer|bcompiler_write_function|bcompiler_write_functions_from_file|bcompiler_write_header|bcompiler_write_included_filename|bcpow|bcpowmod|bcscale|bcsqrt|bcsub|bin2hex|bind_textdomain_codeset|bindec|bindtextdomain|bson_decode|bson_encode|bumpValue|bzclose|bzcompress|bzdecompress|bzerrno|bzerror|bzerrstr|bzflush|bzopen|bzread|bzwrite|cachingiterator|cairo|cairo_create|cairo_font_face_get_type|cairo_font_face_status|cairo_font_options_create|cairo_font_options_equal|cairo_font_options_get_antialias|cairo_font_options_get_hint_metrics|cairo_font_options_get_hint_style|cairo_font_options_get_subpixel_order|cairo_font_options_hash|cairo_font_options_merge|cairo_font_options_set_antialias|cairo_font_options_set_hint_metrics|cairo_font_options_set_hint_style|cairo_font_options_set_subpixel_order|cairo_font_options_status|cairo_format_stride_for_width|cairo_image_surface_create|cairo_image_surface_create_for_data|cairo_image_surface_create_from_png|cairo_image_surface_get_data|cairo_image_surface_get_format|cairo_image_surface_get_height|cairo_image_surface_get_stride|cairo_image_surface_get_width|cairo_matrix_create_scale|cairo_matrix_create_translate|cairo_matrix_invert|cairo_matrix_multiply|cairo_matrix_rotate|cairo_matrix_transform_distance|cairo_matrix_transform_point|cairo_matrix_translate|cairo_pattern_add_color_stop_rgb|cairo_pattern_add_color_stop_rgba|cairo_pattern_create_for_surface|cairo_pattern_create_linear|cairo_pattern_create_radial|cairo_pattern_create_rgb|cairo_pattern_create_rgba|cairo_pattern_get_color_stop_count|cairo_pattern_get_color_stop_rgba|cairo_pattern_get_extend|cairo_pattern_get_filter|cairo_pattern_get_linear_points|cairo_pattern_get_matrix|cairo_pattern_get_radial_circles|cairo_pattern_get_rgba|cairo_pattern_get_surface|cairo_pattern_get_type|cairo_pattern_set_extend|cairo_pattern_set_filter|cairo_pattern_set_matrix|cairo_pattern_status|cairo_pdf_surface_create|cairo_pdf_surface_set_size|cairo_ps_get_levels|cairo_ps_level_to_string|cairo_ps_surface_create|cairo_ps_surface_dsc_begin_page_setup|cairo_ps_surface_dsc_begin_setup|cairo_ps_surface_dsc_comment|cairo_ps_surface_get_eps|cairo_ps_surface_restrict_to_level|cairo_ps_surface_set_eps|cairo_ps_surface_set_size|cairo_scaled_font_create|cairo_scaled_font_extents|cairo_scaled_font_get_ctm|cairo_scaled_font_get_font_face|cairo_scaled_font_get_font_matrix|cairo_scaled_font_get_font_options|cairo_scaled_font_get_scale_matrix|cairo_scaled_font_get_type|cairo_scaled_font_glyph_extents|cairo_scaled_font_status|cairo_scaled_font_text_extents|cairo_surface_copy_page|cairo_surface_create_similar|cairo_surface_finish|cairo_surface_flush|cairo_surface_get_content|cairo_surface_get_device_offset|cairo_surface_get_font_options|cairo_surface_get_type|cairo_surface_mark_dirty|cairo_surface_mark_dirty_rectangle|cairo_surface_set_device_offset|cairo_surface_set_fallback_resolution|cairo_surface_show_page|cairo_surface_status|cairo_surface_write_to_png|cairo_svg_surface_create|cairo_svg_surface_restrict_to_version|cairo_svg_version_to_string|cairoantialias|cairocontent|cairocontext|cairoexception|cairoextend|cairofillrule|cairofilter|cairofontface|cairofontoptions|cairofontslant|cairofonttype|cairofontweight|cairoformat|cairogradientpattern|cairohintmetrics|cairohintstyle|cairoimagesurface|cairolineargradient|cairolinecap|cairolinejoin|cairomatrix|cairooperator|cairopath|cairopattern|cairopatterntype|cairopdfsurface|cairopslevel|cairopssurface|cairoradialgradient|cairoscaledfont|cairosolidpattern|cairostatus|cairosubpixelorder|cairosurface|cairosurfacepattern|cairosurfacetype|cairosvgsurface|cairosvgversion|cairotoyfontface|cal_days_in_month|cal_from_jd|cal_info|cal_to_jd|calcul_hmac|calculhmac|call_user_func|call_user_func_array|call_user_method|call_user_method_array|callbackfilteriterator|ceil|chdb|chdb_create|chdir|checkdate|checkdnsrr|chgrp|chmod|chop|chown|chr|chroot|chunk_split|class_alias|class_exists|class_implements|class_parents|class_uses|classkit_import|classkit_method_add|classkit_method_copy|classkit_method_redefine|classkit_method_remove|classkit_method_rename|clearstatcache|clone|closedir|closelog|collator|com|com_addref|com_create_guid|com_event_sink|com_get|com_get_active_object|com_invoke|com_isenum|com_load|com_load_typelib|com_message_pump|com_print_typeinfo|com_propget|com_propput|com_propset|com_release|com_set|compact|connection_aborted|connection_status|connection_timeout|constant|construct|construct|construct|convert_cyr_string|convert_uudecode|convert_uuencode|copy|cos|cosh|count|count_chars|countable|counter_bump|counter_bump_value|counter_create|counter_get|counter_get_meta|counter_get_named|counter_get_value|counter_reset|counter_reset_value|crack_check|crack_closedict|crack_getlastmessage|crack_opendict|crc32|create_function|crypt|ctype_alnum|ctype_alpha|ctype_cntrl|ctype_digit|ctype_graph|ctype_lower|ctype_print|ctype_punct|ctype_space|ctype_upper|ctype_xdigit|cubrid_affected_rows|cubrid_bind|cubrid_client_encoding|cubrid_close|cubrid_close_prepare|cubrid_close_request|cubrid_col_get|cubrid_col_size|cubrid_column_names|cubrid_column_types|cubrid_commit|cubrid_connect|cubrid_connect_with_url|cubrid_current_oid|cubrid_data_seek|cubrid_db_name|cubrid_disconnect|cubrid_drop|cubrid_errno|cubrid_error|cubrid_error_code|cubrid_error_code_facility|cubrid_error_msg|cubrid_execute|cubrid_fetch|cubrid_fetch_array|cubrid_fetch_assoc|cubrid_fetch_field|cubrid_fetch_lengths|cubrid_fetch_object|cubrid_fetch_row|cubrid_field_flags|cubrid_field_len|cubrid_field_name|cubrid_field_seek|cubrid_field_table|cubrid_field_type|cubrid_free_result|cubrid_get|cubrid_get_autocommit|cubrid_get_charset|cubrid_get_class_name|cubrid_get_client_info|cubrid_get_db_parameter|cubrid_get_server_info|cubrid_insert_id|cubrid_is_instance|cubrid_list_dbs|cubrid_load_from_glo|cubrid_lob_close|cubrid_lob_export|cubrid_lob_get|cubrid_lob_send|cubrid_lob_size|cubrid_lock_read|cubrid_lock_write|cubrid_move_cursor|cubrid_new_glo|cubrid_next_result|cubrid_num_cols|cubrid_num_fields|cubrid_num_rows|cubrid_ping|cubrid_prepare|cubrid_put|cubrid_query|cubrid_real_escape_string|cubrid_result|cubrid_rollback|cubrid_save_to_glo|cubrid_schema|cubrid_send_glo|cubrid_seq_drop|cubrid_seq_insert|cubrid_seq_put|cubrid_set_add|cubrid_set_autocommit|cubrid_set_db_parameter|cubrid_set_drop|cubrid_unbuffered_query|cubrid_version|curl_close|curl_copy_handle|curl_errno|curl_error|curl_exec|curl_getinfo|curl_init|curl_multi_add_handle|curl_multi_close|curl_multi_exec|curl_multi_getcontent|curl_multi_info_read|curl_multi_init|curl_multi_remove_handle|curl_multi_select|curl_setopt|curl_setopt_array|curl_version|current|cyrus_authenticate|cyrus_bind|cyrus_close|cyrus_connect|cyrus_query|cyrus_unbind|date|date_add|date_create|date_create_from_format|date_date_set|date_default_timezone_get|date_default_timezone_set|date_diff|date_format|date_get_last_errors|date_interval_create_from_date_string|date_interval_format|date_isodate_set|date_modify|date_offset_get|date_parse|date_parse_from_format|date_sub|date_sun_info|date_sunrise|date_sunset|date_time_set|date_timestamp_get|date_timestamp_set|date_timezone_get|date_timezone_set|dateinterval|dateperiod|datetime|datetimezone|db2_autocommit|db2_bind_param|db2_client_info|db2_close|db2_column_privileges|db2_columns|db2_commit|db2_conn_error|db2_conn_errormsg|db2_connect|db2_cursor_type|db2_escape_string|db2_exec|db2_execute|db2_fetch_array|db2_fetch_assoc|db2_fetch_both|db2_fetch_object|db2_fetch_row|db2_field_display_size|db2_field_name|db2_field_num|db2_field_precision|db2_field_scale|db2_field_type|db2_field_width|db2_foreign_keys|db2_free_result|db2_free_stmt|db2_get_option|db2_last_insert_id|db2_lob_read|db2_next_result|db2_num_fields|db2_num_rows|db2_pclose|db2_pconnect|db2_prepare|db2_primary_keys|db2_procedure_columns|db2_procedures|db2_result|db2_rollback|db2_server_info|db2_set_option|db2_special_columns|db2_statistics|db2_stmt_error|db2_stmt_errormsg|db2_table_privileges|db2_tables|dba_close|dba_delete|dba_exists|dba_fetch|dba_firstkey|dba_handlers|dba_insert|dba_key_split|dba_list|dba_nextkey|dba_open|dba_optimize|dba_popen|dba_replace|dba_sync|dbase_add_record|dbase_close|dbase_create|dbase_delete_record|dbase_get_header_info|dbase_get_record|dbase_get_record_with_names|dbase_numfields|dbase_numrecords|dbase_open|dbase_pack|dbase_replace_record|dbplus_add|dbplus_aql|dbplus_chdir|dbplus_close|dbplus_curr|dbplus_errcode|dbplus_errno|dbplus_find|dbplus_first|dbplus_flush|dbplus_freealllocks|dbplus_freelock|dbplus_freerlocks|dbplus_getlock|dbplus_getunique|dbplus_info|dbplus_last|dbplus_lockrel|dbplus_next|dbplus_open|dbplus_prev|dbplus_rchperm|dbplus_rcreate|dbplus_rcrtexact|dbplus_rcrtlike|dbplus_resolve|dbplus_restorepos|dbplus_rkeys|dbplus_ropen|dbplus_rquery|dbplus_rrename|dbplus_rsecindex|dbplus_runlink|dbplus_rzap|dbplus_savepos|dbplus_setindex|dbplus_setindexbynumber|dbplus_sql|dbplus_tcl|dbplus_tremove|dbplus_undo|dbplus_undoprepare|dbplus_unlockrel|dbplus_unselect|dbplus_update|dbplus_xlockrel|dbplus_xunlockrel|dbx_close|dbx_compare|dbx_connect|dbx_error|dbx_escape_string|dbx_fetch_row|dbx_query|dbx_sort|dcgettext|dcngettext|deaggregate|debug_backtrace|debug_print_backtrace|debug_zval_dump|decbin|dechex|decoct|define|define_syslog_variables|defined|deg2rad|delete|dgettext|die|dio_close|dio_fcntl|dio_open|dio_read|dio_seek|dio_stat|dio_tcsetattr|dio_truncate|dio_write|dir|directoryiterator|dirname|disk_free_space|disk_total_space|diskfreespace|dl|dngettext|dns_check_record|dns_get_mx|dns_get_record|dom_import_simplexml|domainexception|domattr|domattribute_name|domattribute_set_value|domattribute_specified|domattribute_value|domcharacterdata|domcomment|domdocument|domdocument_add_root|domdocument_create_attribute|domdocument_create_cdata_section|domdocument_create_comment|domdocument_create_element|domdocument_create_element_ns|domdocument_create_entity_reference|domdocument_create_processing_instruction|domdocument_create_text_node|domdocument_doctype|domdocument_document_element|domdocument_dump_file|domdocument_dump_mem|domdocument_get_element_by_id|domdocument_get_elements_by_tagname|domdocument_html_dump_mem|domdocument_xinclude|domdocumentfragment|domdocumenttype|domdocumenttype_entities|domdocumenttype_internal_subset|domdocumenttype_name|domdocumenttype_notations|domdocumenttype_public_id|domdocumenttype_system_id|domelement|domelement_get_attribute|domelement_get_attribute_node|domelement_get_elements_by_tagname|domelement_has_attribute|domelement_remove_attribute|domelement_set_attribute|domelement_set_attribute_node|domelement_tagname|domentity|domentityreference|domexception|domimplementation|domnamednodemap|domnode|domnode_add_namespace|domnode_append_child|domnode_append_sibling|domnode_attributes|domnode_child_nodes|domnode_clone_node|domnode_dump_node|domnode_first_child|domnode_get_content|domnode_has_attributes|domnode_has_child_nodes|domnode_insert_before|domnode_is_blank_node|domnode_last_child|domnode_next_sibling|domnode_node_name|domnode_node_type|domnode_node_value|domnode_owner_document|domnode_parent_node|domnode_prefix|domnode_previous_sibling|domnode_remove_child|domnode_replace_child|domnode_replace_node|domnode_set_content|domnode_set_name|domnode_set_namespace|domnode_unlink_node|domnodelist|domnotation|domprocessinginstruction|domprocessinginstruction_data|domprocessinginstruction_target|domtext|domxml_new_doc|domxml_open_file|domxml_open_mem|domxml_version|domxml_xmltree|domxml_xslt_stylesheet|domxml_xslt_stylesheet_doc|domxml_xslt_stylesheet_file|domxml_xslt_version|domxpath|domxsltstylesheet_process|domxsltstylesheet_result_dump_file|domxsltstylesheet_result_dump_mem|dotnet|dotnet_load|doubleval|each|easter_date|easter_days|echo|empty|emptyiterator|enchant_broker_describe|enchant_broker_dict_exists|enchant_broker_free|enchant_broker_free_dict|enchant_broker_get_error|enchant_broker_init|enchant_broker_list_dicts|enchant_broker_request_dict|enchant_broker_request_pwl_dict|enchant_broker_set_ordering|enchant_dict_add_to_personal|enchant_dict_add_to_session|enchant_dict_check|enchant_dict_describe|enchant_dict_get_error|enchant_dict_is_in_session|enchant_dict_quick_check|enchant_dict_store_replacement|enchant_dict_suggest|end|ereg|ereg_replace|eregi|eregi_replace|error_get_last|error_log|error_reporting|errorexception|escapeshellarg|escapeshellcmd|eval|event_add|event_base_free|event_base_loop|event_base_loopbreak|event_base_loopexit|event_base_new|event_base_priority_init|event_base_set|event_buffer_base_set|event_buffer_disable|event_buffer_enable|event_buffer_fd_set|event_buffer_free|event_buffer_new|event_buffer_priority_set|event_buffer_read|event_buffer_set_callback|event_buffer_timeout_set|event_buffer_watermark_set|event_buffer_write|event_del|event_free|event_new|event_set|exception|exec|exif_imagetype|exif_read_data|exif_tagname|exif_thumbnail|exit|exp|expect_expectl|expect_popen|explode|expm1|export|export|extension_loaded|extract|ezmlm_hash|fam_cancel_monitor|fam_close|fam_monitor_collection|fam_monitor_directory|fam_monitor_file|fam_next_event|fam_open|fam_pending|fam_resume_monitor|fam_suspend_monitor|fbsql_affected_rows|fbsql_autocommit|fbsql_blob_size|fbsql_change_user|fbsql_clob_size|fbsql_close|fbsql_commit|fbsql_connect|fbsql_create_blob|fbsql_create_clob|fbsql_create_db|fbsql_data_seek|fbsql_database|fbsql_database_password|fbsql_db_query|fbsql_db_status|fbsql_drop_db|fbsql_errno|fbsql_error|fbsql_fetch_array|fbsql_fetch_assoc|fbsql_fetch_field|fbsql_fetch_lengths|fbsql_fetch_object|fbsql_fetch_row|fbsql_field_flags|fbsql_field_len|fbsql_field_name|fbsql_field_seek|fbsql_field_table|fbsql_field_type|fbsql_free_result|fbsql_get_autostart_info|fbsql_hostname|fbsql_insert_id|fbsql_list_dbs|fbsql_list_fields|fbsql_list_tables|fbsql_next_result|fbsql_num_fields|fbsql_num_rows|fbsql_password|fbsql_pconnect|fbsql_query|fbsql_read_blob|fbsql_read_clob|fbsql_result|fbsql_rollback|fbsql_rows_fetched|fbsql_select_db|fbsql_set_characterset|fbsql_set_lob_mode|fbsql_set_password|fbsql_set_transaction|fbsql_start_db|fbsql_stop_db|fbsql_table_name|fbsql_tablename|fbsql_username|fbsql_warnings|fclose|fdf_add_doc_javascript|fdf_add_template|fdf_close|fdf_create|fdf_enum_values|fdf_errno|fdf_error|fdf_get_ap|fdf_get_attachment|fdf_get_encoding|fdf_get_file|fdf_get_flags|fdf_get_opt|fdf_get_status|fdf_get_value|fdf_get_version|fdf_header|fdf_next_field_name|fdf_open|fdf_open_string|fdf_remove_item|fdf_save|fdf_save_string|fdf_set_ap|fdf_set_encoding|fdf_set_file|fdf_set_flags|fdf_set_javascript_action|fdf_set_on_import_javascript|fdf_set_opt|fdf_set_status|fdf_set_submit_form_action|fdf_set_target_frame|fdf_set_value|fdf_set_version|feof|fflush|fgetc|fgetcsv|fgets|fgetss|file|file_exists|file_get_contents|file_put_contents|fileatime|filectime|filegroup|fileinode|filemtime|fileowner|fileperms|filepro|filepro_fieldcount|filepro_fieldname|filepro_fieldtype|filepro_fieldwidth|filepro_retrieve|filepro_rowcount|filesize|filesystemiterator|filetype|filter_has_var|filter_id|filter_input|filter_input_array|filter_list|filter_var|filter_var_array|filteriterator|finfo_buffer|finfo_close|finfo_file|finfo_open|finfo_set_flags|floatval|flock|floor|flush|fmod|fnmatch|fopen|forward_static_call|forward_static_call_array|fpassthru|fprintf|fputcsv|fputs|fread|frenchtojd|fribidi_log2vis|fscanf|fseek|fsockopen|fstat|ftell|ftok|ftp_alloc|ftp_cdup|ftp_chdir|ftp_chmod|ftp_close|ftp_connect|ftp_delete|ftp_exec|ftp_fget|ftp_fput|ftp_get|ftp_get_option|ftp_login|ftp_mdtm|ftp_mkdir|ftp_nb_continue|ftp_nb_fget|ftp_nb_fput|ftp_nb_get|ftp_nb_put|ftp_nlist|ftp_pasv|ftp_put|ftp_pwd|ftp_quit|ftp_raw|ftp_rawlist|ftp_rename|ftp_rmdir|ftp_set_option|ftp_site|ftp_size|ftp_ssl_connect|ftp_systype|ftruncate|func_get_arg|func_get_args|func_num_args|function_exists|fwrite|gc_collect_cycles|gc_disable|gc_enable|gc_enabled|gd_info|gearmanclient|gearmanjob|gearmantask|gearmanworker|geoip_continent_code_by_name|geoip_country_code3_by_name|geoip_country_code_by_name|geoip_country_name_by_name|geoip_database_info|geoip_db_avail|geoip_db_filename|geoip_db_get_all_info|geoip_id_by_name|geoip_isp_by_name|geoip_org_by_name|geoip_record_by_name|geoip_region_by_name|geoip_region_name_by_code|geoip_time_zone_by_country_and_region|getMeta|getNamed|getValue|get_browser|get_called_class|get_cfg_var|get_class|get_class_methods|get_class_vars|get_current_user|get_declared_classes|get_declared_interfaces|get_declared_traits|get_defined_constants|get_defined_functions|get_defined_vars|get_extension_funcs|get_headers|get_html_translation_table|get_include_path|get_included_files|get_loaded_extensions|get_magic_quotes_gpc|get_magic_quotes_runtime|get_meta_tags|get_object_vars|get_parent_class|get_required_files|get_resource_type|getallheaders|getconstant|getconstants|getconstructor|getcwd|getdate|getdefaultproperties|getdoccomment|getendline|getenv|getextension|getextensionname|getfilename|gethostbyaddr|gethostbyname|gethostbynamel|gethostname|getimagesize|getinterfacenames|getinterfaces|getlastmod|getmethod|getmethods|getmodifiers|getmxrr|getmygid|getmyinode|getmypid|getmyuid|getname|getnamespacename|getopt|getparentclass|getproperties|getproperty|getprotobyname|getprotobynumber|getrandmax|getrusage|getservbyname|getservbyport|getshortname|getstartline|getstaticproperties|getstaticpropertyvalue|gettext|gettimeofday|gettype|glob|globiterator|gmagick|gmagickdraw|gmagickpixel|gmdate|gmmktime|gmp_abs|gmp_add|gmp_and|gmp_clrbit|gmp_cmp|gmp_com|gmp_div|gmp_div_q|gmp_div_qr|gmp_div_r|gmp_divexact|gmp_fact|gmp_gcd|gmp_gcdext|gmp_hamdist|gmp_init|gmp_intval|gmp_invert|gmp_jacobi|gmp_legendre|gmp_mod|gmp_mul|gmp_neg|gmp_nextprime|gmp_or|gmp_perfect_square|gmp_popcount|gmp_pow|gmp_powm|gmp_prob_prime|gmp_random|gmp_scan0|gmp_scan1|gmp_setbit|gmp_sign|gmp_sqrt|gmp_sqrtrem|gmp_strval|gmp_sub|gmp_testbit|gmp_xor|gmstrftime|gnupg_adddecryptkey|gnupg_addencryptkey|gnupg_addsignkey|gnupg_cleardecryptkeys|gnupg_clearencryptkeys|gnupg_clearsignkeys|gnupg_decrypt|gnupg_decryptverify|gnupg_encrypt|gnupg_encryptsign|gnupg_export|gnupg_geterror|gnupg_getprotocol|gnupg_import|gnupg_init|gnupg_keyinfo|gnupg_setarmor|gnupg_seterrormode|gnupg_setsignmode|gnupg_sign|gnupg_verify|gopher_parsedir|grapheme_extract|grapheme_stripos|grapheme_stristr|grapheme_strlen|grapheme_strpos|grapheme_strripos|grapheme_strrpos|grapheme_strstr|grapheme_substr|gregoriantojd|gupnp_context_get_host_ip|gupnp_context_get_port|gupnp_context_get_subscription_timeout|gupnp_context_host_path|gupnp_context_new|gupnp_context_set_subscription_timeout|gupnp_context_timeout_add|gupnp_context_unhost_path|gupnp_control_point_browse_start|gupnp_control_point_browse_stop|gupnp_control_point_callback_set|gupnp_control_point_new|gupnp_device_action_callback_set|gupnp_device_info_get|gupnp_device_info_get_service|gupnp_root_device_get_available|gupnp_root_device_get_relative_location|gupnp_root_device_new|gupnp_root_device_set_available|gupnp_root_device_start|gupnp_root_device_stop|gupnp_service_action_get|gupnp_service_action_return|gupnp_service_action_return_error|gupnp_service_action_set|gupnp_service_freeze_notify|gupnp_service_info_get|gupnp_service_info_get_introspection|gupnp_service_introspection_get_state_variable|gupnp_service_notify|gupnp_service_proxy_action_get|gupnp_service_proxy_action_set|gupnp_service_proxy_add_notify|gupnp_service_proxy_callback_set|gupnp_service_proxy_get_subscribed|gupnp_service_proxy_remove_notify|gupnp_service_proxy_set_subscribed|gupnp_service_thaw_notify|gzclose|gzcompress|gzdecode|gzdeflate|gzencode|gzeof|gzfile|gzgetc|gzgets|gzgetss|gzinflate|gzopen|gzpassthru|gzputs|gzread|gzrewind|gzseek|gztell|gzuncompress|gzwrite|halt_compiler|haruannotation|haruannotation_setborderstyle|haruannotation_sethighlightmode|haruannotation_seticon|haruannotation_setopened|harudestination|harudestination_setfit|harudestination_setfitb|harudestination_setfitbh|harudestination_setfitbv|harudestination_setfith|harudestination_setfitr|harudestination_setfitv|harudestination_setxyz|harudoc|harudoc_addpage|harudoc_addpagelabel|harudoc_construct|harudoc_createoutline|harudoc_getcurrentencoder|harudoc_getcurrentpage|harudoc_getencoder|harudoc_getfont|harudoc_getinfoattr|harudoc_getpagelayout|harudoc_getpagemode|harudoc_getstreamsize|harudoc_insertpage|harudoc_loadjpeg|harudoc_loadpng|harudoc_loadraw|harudoc_loadttc|harudoc_loadttf|harudoc_loadtype1|harudoc_output|harudoc_readfromstream|harudoc_reseterror|harudoc_resetstream|harudoc_save|harudoc_savetostream|harudoc_setcompressionmode|harudoc_setcurrentencoder|harudoc_setencryptionmode|harudoc_setinfoattr|harudoc_setinfodateattr|harudoc_setopenaction|harudoc_setpagelayout|harudoc_setpagemode|harudoc_setpagesconfiguration|harudoc_setpassword|harudoc_setpermission|harudoc_usecnsencodings|harudoc_usecnsfonts|harudoc_usecntencodings|harudoc_usecntfonts|harudoc_usejpencodings|harudoc_usejpfonts|harudoc_usekrencodings|harudoc_usekrfonts|haruencoder|haruencoder_getbytetype|haruencoder_gettype|haruencoder_getunicode|haruencoder_getwritingmode|haruexception|harufont|harufont_getascent|harufont_getcapheight|harufont_getdescent|harufont_getencodingname|harufont_getfontname|harufont_gettextwidth|harufont_getunicodewidth|harufont_getxheight|harufont_measuretext|haruimage|haruimage_getbitspercomponent|haruimage_getcolorspace|haruimage_getheight|haruimage_getsize|haruimage_getwidth|haruimage_setcolormask|haruimage_setmaskimage|haruoutline|haruoutline_setdestination|haruoutline_setopened|harupage|harupage_arc|harupage_begintext|harupage_circle|harupage_closepath|harupage_concat|harupage_createdestination|harupage_createlinkannotation|harupage_createtextannotation|harupage_createurlannotation|harupage_curveto|harupage_curveto2|harupage_curveto3|harupage_drawimage|harupage_ellipse|harupage_endpath|harupage_endtext|harupage_eofill|harupage_eofillstroke|harupage_fill|harupage_fillstroke|harupage_getcharspace|harupage_getcmykfill|harupage_getcmykstroke|harupage_getcurrentfont|harupage_getcurrentfontsize|harupage_getcurrentpos|harupage_getcurrenttextpos|harupage_getdash|harupage_getfillingcolorspace|harupage_getflatness|harupage_getgmode|harupage_getgrayfill|harupage_getgraystroke|harupage_getheight|harupage_gethorizontalscaling|harupage_getlinecap|harupage_getlinejoin|harupage_getlinewidth|harupage_getmiterlimit|harupage_getrgbfill|harupage_getrgbstroke|harupage_getstrokingcolorspace|harupage_gettextleading|harupage_gettextmatrix|harupage_gettextrenderingmode|harupage_gettextrise|harupage_gettextwidth|harupage_gettransmatrix|harupage_getwidth|harupage_getwordspace|harupage_lineto|harupage_measuretext|harupage_movetextpos|harupage_moveto|harupage_movetonextline|harupage_rectangle|harupage_setcharspace|harupage_setcmykfill|harupage_setcmykstroke|harupage_setdash|harupage_setflatness|harupage_setfontandsize|harupage_setgrayfill|harupage_setgraystroke|harupage_setheight|harupage_sethorizontalscaling|harupage_setlinecap|harupage_setlinejoin|harupage_setlinewidth|harupage_setmiterlimit|harupage_setrgbfill|harupage_setrgbstroke|harupage_setrotate|harupage_setsize|harupage_setslideshow|harupage_settextleading|harupage_settextmatrix|harupage_settextrenderingmode|harupage_settextrise|harupage_setwidth|harupage_setwordspace|harupage_showtext|harupage_showtextnextline|harupage_stroke|harupage_textout|harupage_textrect|hasconstant|hash|hash_algos|hash_copy|hash_file|hash_final|hash_hmac|hash_hmac_file|hash_init|hash_update|hash_update_file|hash_update_stream|hasmethod|hasproperty|header|header_register_callback|header_remove|headers_list|headers_sent|hebrev|hebrevc|hex2bin|hexdec|highlight_file|highlight_string|html_entity_decode|htmlentities|htmlspecialchars|htmlspecialchars_decode|http_build_cookie|http_build_query|http_build_str|http_build_url|http_cache_etag|http_cache_last_modified|http_chunked_decode|http_date|http_deflate|http_get|http_get_request_body|http_get_request_body_stream|http_get_request_headers|http_head|http_inflate|http_match_etag|http_match_modified|http_match_request_header|http_negotiate_charset|http_negotiate_content_type|http_negotiate_language|http_parse_cookie|http_parse_headers|http_parse_message|http_parse_params|http_persistent_handles_clean|http_persistent_handles_count|http_persistent_handles_ident|http_post_data|http_post_fields|http_put_data|http_put_file|http_put_stream|http_redirect|http_request|http_request_body_encode|http_request_method_exists|http_request_method_name|http_request_method_register|http_request_method_unregister|http_response_code|http_send_content_disposition|http_send_content_type|http_send_data|http_send_file|http_send_last_modified|http_send_status|http_send_stream|http_support|http_throttle|httpdeflatestream|httpdeflatestream_construct|httpdeflatestream_factory|httpdeflatestream_finish|httpdeflatestream_flush|httpdeflatestream_update|httpinflatestream|httpinflatestream_construct|httpinflatestream_factory|httpinflatestream_finish|httpinflatestream_flush|httpinflatestream_update|httpmessage|httpmessage_addheaders|httpmessage_construct|httpmessage_detach|httpmessage_factory|httpmessage_fromenv|httpmessage_fromstring|httpmessage_getbody|httpmessage_getheader|httpmessage_getheaders|httpmessage_gethttpversion|httpmessage_getparentmessage|httpmessage_getrequestmethod|httpmessage_getrequesturl|httpmessage_getresponsecode|httpmessage_getresponsestatus|httpmessage_gettype|httpmessage_guesscontenttype|httpmessage_prepend|httpmessage_reverse|httpmessage_send|httpmessage_setbody|httpmessage_setheaders|httpmessage_sethttpversion|httpmessage_setrequestmethod|httpmessage_setrequesturl|httpmessage_setresponsecode|httpmessage_setresponsestatus|httpmessage_settype|httpmessage_tomessagetypeobject|httpmessage_tostring|httpquerystring|httpquerystring_construct|httpquerystring_get|httpquerystring_mod|httpquerystring_set|httpquerystring_singleton|httpquerystring_toarray|httpquerystring_tostring|httpquerystring_xlate|httprequest|httprequest_addcookies|httprequest_addheaders|httprequest_addpostfields|httprequest_addpostfile|httprequest_addputdata|httprequest_addquerydata|httprequest_addrawpostdata|httprequest_addssloptions|httprequest_clearhistory|httprequest_construct|httprequest_enablecookies|httprequest_getcontenttype|httprequest_getcookies|httprequest_getheaders|httprequest_gethistory|httprequest_getmethod|httprequest_getoptions|httprequest_getpostfields|httprequest_getpostfiles|httprequest_getputdata|httprequest_getputfile|httprequest_getquerydata|httprequest_getrawpostdata|httprequest_getrawrequestmessage|httprequest_getrawresponsemessage|httprequest_getrequestmessage|httprequest_getresponsebody|httprequest_getresponsecode|httprequest_getresponsecookies|httprequest_getresponsedata|httprequest_getresponseheader|httprequest_getresponseinfo|httprequest_getresponsemessage|httprequest_getresponsestatus|httprequest_getssloptions|httprequest_geturl|httprequest_resetcookies|httprequest_send|httprequest_setcontenttype|httprequest_setcookies|httprequest_setheaders|httprequest_setmethod|httprequest_setoptions|httprequest_setpostfields|httprequest_setpostfiles|httprequest_setputdata|httprequest_setputfile|httprequest_setquerydata|httprequest_setrawpostdata|httprequest_setssloptions|httprequest_seturl|httprequestpool|httprequestpool_attach|httprequestpool_construct|httprequestpool_destruct|httprequestpool_detach|httprequestpool_getattachedrequests|httprequestpool_getfinishedrequests|httprequestpool_reset|httprequestpool_send|httprequestpool_socketperform|httprequestpool_socketselect|httpresponse|httpresponse_capture|httpresponse_getbuffersize|httpresponse_getcache|httpresponse_getcachecontrol|httpresponse_getcontentdisposition|httpresponse_getcontenttype|httpresponse_getdata|httpresponse_getetag|httpresponse_getfile|httpresponse_getgzip|httpresponse_getheader|httpresponse_getlastmodified|httpresponse_getrequestbody|httpresponse_getrequestbodystream|httpresponse_getrequestheaders|httpresponse_getstream|httpresponse_getthrottledelay|httpresponse_guesscontenttype|httpresponse_redirect|httpresponse_send|httpresponse_setbuffersize|httpresponse_setcache|httpresponse_setcachecontrol|httpresponse_setcontentdisposition|httpresponse_setcontenttype|httpresponse_setdata|httpresponse_setetag|httpresponse_setfile|httpresponse_setgzip|httpresponse_setheader|httpresponse_setlastmodified|httpresponse_setstream|httpresponse_setthrottledelay|httpresponse_status|hw_array2objrec|hw_changeobject|hw_children|hw_childrenobj|hw_close|hw_connect|hw_connection_info|hw_cp|hw_deleteobject|hw_docbyanchor|hw_docbyanchorobj|hw_document_attributes|hw_document_bodytag|hw_document_content|hw_document_setcontent|hw_document_size|hw_dummy|hw_edittext|hw_error|hw_errormsg|hw_free_document|hw_getanchors|hw_getanchorsobj|hw_getandlock|hw_getchildcoll|hw_getchildcollobj|hw_getchilddoccoll|hw_getchilddoccollobj|hw_getobject|hw_getobjectbyquery|hw_getobjectbyquerycoll|hw_getobjectbyquerycollobj|hw_getobjectbyqueryobj|hw_getparents|hw_getparentsobj|hw_getrellink|hw_getremote|hw_getremotechildren|hw_getsrcbydestobj|hw_gettext|hw_getusername|hw_identify|hw_incollections|hw_info|hw_inscoll|hw_insdoc|hw_insertanchors|hw_insertdocument|hw_insertobject|hw_mapid|hw_modifyobject|hw_mv|hw_new_document|hw_objrec2array|hw_output_document|hw_pconnect|hw_pipedocument|hw_root|hw_setlinkroot|hw_stat|hw_unlock|hw_who|hwapi_attribute|hwapi_attribute_key|hwapi_attribute_langdepvalue|hwapi_attribute_value|hwapi_attribute_values|hwapi_checkin|hwapi_checkout|hwapi_children|hwapi_content|hwapi_content_mimetype|hwapi_content_read|hwapi_copy|hwapi_dbstat|hwapi_dcstat|hwapi_dstanchors|hwapi_dstofsrcanchor|hwapi_error_count|hwapi_error_reason|hwapi_find|hwapi_ftstat|hwapi_hgcsp|hwapi_hwstat|hwapi_identify|hwapi_info|hwapi_insert|hwapi_insertanchor|hwapi_insertcollection|hwapi_insertdocument|hwapi_link|hwapi_lock|hwapi_move|hwapi_new_content|hwapi_object|hwapi_object_assign|hwapi_object_attreditable|hwapi_object_count|hwapi_object_insert|hwapi_object_new|hwapi_object_remove|hwapi_object_title|hwapi_object_value|hwapi_objectbyanchor|hwapi_parents|hwapi_reason_description|hwapi_reason_type|hwapi_remove|hwapi_replace|hwapi_setcommittedversion|hwapi_srcanchors|hwapi_srcsofdst|hwapi_unlock|hwapi_user|hwapi_userlist|hypot|ibase_add_user|ibase_affected_rows|ibase_backup|ibase_blob_add|ibase_blob_cancel|ibase_blob_close|ibase_blob_create|ibase_blob_echo|ibase_blob_get|ibase_blob_import|ibase_blob_info|ibase_blob_open|ibase_close|ibase_commit|ibase_commit_ret|ibase_connect|ibase_db_info|ibase_delete_user|ibase_drop_db|ibase_errcode|ibase_errmsg|ibase_execute|ibase_fetch_assoc|ibase_fetch_object|ibase_fetch_row|ibase_field_info|ibase_free_event_handler|ibase_free_query|ibase_free_result|ibase_gen_id|ibase_maintain_db|ibase_modify_user|ibase_name_result|ibase_num_fields|ibase_num_params|ibase_param_info|ibase_pconnect|ibase_prepare|ibase_query|ibase_restore|ibase_rollback|ibase_rollback_ret|ibase_server_info|ibase_service_attach|ibase_service_detach|ibase_set_event_handler|ibase_timefmt|ibase_trans|ibase_wait_event|iconv|iconv_get_encoding|iconv_mime_decode|iconv_mime_decode_headers|iconv_mime_encode|iconv_set_encoding|iconv_strlen|iconv_strpos|iconv_strrpos|iconv_substr|id3_get_frame_long_name|id3_get_frame_short_name|id3_get_genre_id|id3_get_genre_list|id3_get_genre_name|id3_get_tag|id3_get_version|id3_remove_tag|id3_set_tag|id3v2attachedpictureframe|id3v2frame|id3v2tag|idate|idn_to_ascii|idn_to_unicode|idn_to_utf8|ifx_affected_rows|ifx_blobinfile_mode|ifx_byteasvarchar|ifx_close|ifx_connect|ifx_copy_blob|ifx_create_blob|ifx_create_char|ifx_do|ifx_error|ifx_errormsg|ifx_fetch_row|ifx_fieldproperties|ifx_fieldtypes|ifx_free_blob|ifx_free_char|ifx_free_result|ifx_get_blob|ifx_get_char|ifx_getsqlca|ifx_htmltbl_result|ifx_nullformat|ifx_num_fields|ifx_num_rows|ifx_pconnect|ifx_prepare|ifx_query|ifx_textasvarchar|ifx_update_blob|ifx_update_char|ifxus_close_slob|ifxus_create_slob|ifxus_free_slob|ifxus_open_slob|ifxus_read_slob|ifxus_seek_slob|ifxus_tell_slob|ifxus_write_slob|ignore_user_abort|iis_add_server|iis_get_dir_security|iis_get_script_map|iis_get_server_by_comment|iis_get_server_by_path|iis_get_server_rights|iis_get_service_state|iis_remove_server|iis_set_app_settings|iis_set_dir_security|iis_set_script_map|iis_set_server_rights|iis_start_server|iis_start_service|iis_stop_server|iis_stop_service|image2wbmp|image_type_to_extension|image_type_to_mime_type|imagealphablending|imageantialias|imagearc|imagechar|imagecharup|imagecolorallocate|imagecolorallocatealpha|imagecolorat|imagecolorclosest|imagecolorclosestalpha|imagecolorclosesthwb|imagecolordeallocate|imagecolorexact|imagecolorexactalpha|imagecolormatch|imagecolorresolve|imagecolorresolvealpha|imagecolorset|imagecolorsforindex|imagecolorstotal|imagecolortransparent|imageconvolution|imagecopy|imagecopymerge|imagecopymergegray|imagecopyresampled|imagecopyresized|imagecreate|imagecreatefromgd|imagecreatefromgd2|imagecreatefromgd2part|imagecreatefromgif|imagecreatefromjpeg|imagecreatefrompng|imagecreatefromstring|imagecreatefromwbmp|imagecreatefromxbm|imagecreatefromxpm|imagecreatetruecolor|imagedashedline|imagedestroy|imageellipse|imagefill|imagefilledarc|imagefilledellipse|imagefilledpolygon|imagefilledrectangle|imagefilltoborder|imagefilter|imagefontheight|imagefontwidth|imageftbbox|imagefttext|imagegammacorrect|imagegd|imagegd2|imagegif|imagegrabscreen|imagegrabwindow|imageinterlace|imageistruecolor|imagejpeg|imagelayereffect|imageline|imageloadfont|imagepalettecopy|imagepng|imagepolygon|imagepsbbox|imagepsencodefont|imagepsextendfont|imagepsfreefont|imagepsloadfont|imagepsslantfont|imagepstext|imagerectangle|imagerotate|imagesavealpha|imagesetbrush|imagesetpixel|imagesetstyle|imagesetthickness|imagesettile|imagestring|imagestringup|imagesx|imagesy|imagetruecolortopalette|imagettfbbox|imagettftext|imagetypes|imagewbmp|imagexbm|imagick|imagick_adaptiveblurimage|imagick_adaptiveresizeimage|imagick_adaptivesharpenimage|imagick_adaptivethresholdimage|imagick_addimage|imagick_addnoiseimage|imagick_affinetransformimage|imagick_animateimages|imagick_annotateimage|imagick_appendimages|imagick_averageimages|imagick_blackthresholdimage|imagick_blurimage|imagick_borderimage|imagick_charcoalimage|imagick_chopimage|imagick_clear|imagick_clipimage|imagick_clippathimage|imagick_clone|imagick_clutimage|imagick_coalesceimages|imagick_colorfloodfillimage|imagick_colorizeimage|imagick_combineimages|imagick_commentimage|imagick_compareimagechannels|imagick_compareimagelayers|imagick_compareimages|imagick_compositeimage|imagick_construct|imagick_contrastimage|imagick_contraststretchimage|imagick_convolveimage|imagick_cropimage|imagick_cropthumbnailimage|imagick_current|imagick_cyclecolormapimage|imagick_decipherimage|imagick_deconstructimages|imagick_deleteimageartifact|imagick_despeckleimage|imagick_destroy|imagick_displayimage|imagick_displayimages|imagick_distortimage|imagick_drawimage|imagick_edgeimage|imagick_embossimage|imagick_encipherimage|imagick_enhanceimage|imagick_equalizeimage|imagick_evaluateimage|imagick_extentimage|imagick_flattenimages|imagick_flipimage|imagick_floodfillpaintimage|imagick_flopimage|imagick_frameimage|imagick_fximage|imagick_gammaimage|imagick_gaussianblurimage|imagick_getcolorspace|imagick_getcompression|imagick_getcompressionquality|imagick_getcopyright|imagick_getfilename|imagick_getfont|imagick_getformat|imagick_getgravity|imagick_gethomeurl|imagick_getimage|imagick_getimagealphachannel|imagick_getimageartifact|imagick_getimagebackgroundcolor|imagick_getimageblob|imagick_getimageblueprimary|imagick_getimagebordercolor|imagick_getimagechanneldepth|imagick_getimagechanneldistortion|imagick_getimagechanneldistortions|imagick_getimagechannelextrema|imagick_getimagechannelmean|imagick_getimagechannelrange|imagick_getimagechannelstatistics|imagick_getimageclipmask|imagick_getimagecolormapcolor|imagick_getimagecolors|imagick_getimagecolorspace|imagick_getimagecompose|imagick_getimagecompression|imagick_getimagecompressionquality|imagick_getimagedelay|imagick_getimagedepth|imagick_getimagedispose|imagick_getimagedistortion|imagick_getimageextrema|imagick_getimagefilename|imagick_getimageformat|imagick_getimagegamma|imagick_getimagegeometry|imagick_getimagegravity|imagick_getimagegreenprimary|imagick_getimageheight|imagick_getimagehistogram|imagick_getimageindex|imagick_getimageinterlacescheme|imagick_getimageinterpolatemethod|imagick_getimageiterations|imagick_getimagelength|imagick_getimagemagicklicense|imagick_getimagematte|imagick_getimagemattecolor|imagick_getimageorientation|imagick_getimagepage|imagick_getimagepixelcolor|imagick_getimageprofile|imagick_getimageprofiles|imagick_getimageproperties|imagick_getimageproperty|imagick_getimageredprimary|imagick_getimageregion|imagick_getimagerenderingintent|imagick_getimageresolution|imagick_getimagesblob|imagick_getimagescene|imagick_getimagesignature|imagick_getimagesize|imagick_getimagetickspersecond|imagick_getimagetotalinkdensity|imagick_getimagetype|imagick_getimageunits|imagick_getimagevirtualpixelmethod|imagick_getimagewhitepoint|imagick_getimagewidth|imagick_getinterlacescheme|imagick_getiteratorindex|imagick_getnumberimages|imagick_getoption|imagick_getpackagename|imagick_getpage|imagick_getpixeliterator|imagick_getpixelregioniterator|imagick_getpointsize|imagick_getquantumdepth|imagick_getquantumrange|imagick_getreleasedate|imagick_getresource|imagick_getresourcelimit|imagick_getsamplingfactors|imagick_getsize|imagick_getsizeoffset|imagick_getversion|imagick_hasnextimage|imagick_haspreviousimage|imagick_identifyimage|imagick_implodeimage|imagick_labelimage|imagick_levelimage|imagick_linearstretchimage|imagick_liquidrescaleimage|imagick_magnifyimage|imagick_mapimage|imagick_mattefloodfillimage|imagick_medianfilterimage|imagick_mergeimagelayers|imagick_minifyimage|imagick_modulateimage|imagick_montageimage|imagick_morphimages|imagick_mosaicimages|imagick_motionblurimage|imagick_negateimage|imagick_newimage|imagick_newpseudoimage|imagick_nextimage|imagick_normalizeimage|imagick_oilpaintimage|imagick_opaquepaintimage|imagick_optimizeimagelayers|imagick_orderedposterizeimage|imagick_paintfloodfillimage|imagick_paintopaqueimage|imagick_painttransparentimage|imagick_pingimage|imagick_pingimageblob|imagick_pingimagefile|imagick_polaroidimage|imagick_posterizeimage|imagick_previewimages|imagick_previousimage|imagick_profileimage|imagick_quantizeimage|imagick_quantizeimages|imagick_queryfontmetrics|imagick_queryfonts|imagick_queryformats|imagick_radialblurimage|imagick_raiseimage|imagick_randomthresholdimage|imagick_readimage|imagick_readimageblob|imagick_readimagefile|imagick_recolorimage|imagick_reducenoiseimage|imagick_removeimage|imagick_removeimageprofile|imagick_render|imagick_resampleimage|imagick_resetimagepage|imagick_resizeimage|imagick_rollimage|imagick_rotateimage|imagick_roundcorners|imagick_sampleimage|imagick_scaleimage|imagick_separateimagechannel|imagick_sepiatoneimage|imagick_setbackgroundcolor|imagick_setcolorspace|imagick_setcompression|imagick_setcompressionquality|imagick_setfilename|imagick_setfirstiterator|imagick_setfont|imagick_setformat|imagick_setgravity|imagick_setimage|imagick_setimagealphachannel|imagick_setimageartifact|imagick_setimagebackgroundcolor|imagick_setimagebias|imagick_setimageblueprimary|imagick_setimagebordercolor|imagick_setimagechanneldepth|imagick_setimageclipmask|imagick_setimagecolormapcolor|imagick_setimagecolorspace|imagick_setimagecompose|imagick_setimagecompression|imagick_setimagecompressionquality|imagick_setimagedelay|imagick_setimagedepth|imagick_setimagedispose|imagick_setimageextent|imagick_setimagefilename|imagick_setimageformat|imagick_setimagegamma|imagick_setimagegravity|imagick_setimagegreenprimary|imagick_setimageindex|imagick_setimageinterlacescheme|imagick_setimageinterpolatemethod|imagick_setimageiterations|imagick_setimagematte|imagick_setimagemattecolor|imagick_setimageopacity|imagick_setimageorientation|imagick_setimagepage|imagick_setimageprofile|imagick_setimageproperty|imagick_setimageredprimary|imagick_setimagerenderingintent|imagick_setimageresolution|imagick_setimagescene|imagick_setimagetickspersecond|imagick_setimagetype|imagick_setimageunits|imagick_setimagevirtualpixelmethod|imagick_setimagewhitepoint|imagick_setinterlacescheme|imagick_setiteratorindex|imagick_setlastiterator|imagick_setoption|imagick_setpage|imagick_setpointsize|imagick_setresolution|imagick_setresourcelimit|imagick_setsamplingfactors|imagick_setsize|imagick_setsizeoffset|imagick_settype|imagick_shadeimage|imagick_shadowimage|imagick_sharpenimage|imagick_shaveimage|imagick_shearimage|imagick_sigmoidalcontrastimage|imagick_sketchimage|imagick_solarizeimage|imagick_spliceimage|imagick_spreadimage|imagick_steganoimage|imagick_stereoimage|imagick_stripimage|imagick_swirlimage|imagick_textureimage|imagick_thresholdimage|imagick_thumbnailimage|imagick_tintimage|imagick_transformimage|imagick_transparentpaintimage|imagick_transposeimage|imagick_transverseimage|imagick_trimimage|imagick_uniqueimagecolors|imagick_unsharpmaskimage|imagick_valid|imagick_vignetteimage|imagick_waveimage|imagick_whitethresholdimage|imagick_writeimage|imagick_writeimagefile|imagick_writeimages|imagick_writeimagesfile|imagickdraw|imagickdraw_affine|imagickdraw_annotation|imagickdraw_arc|imagickdraw_bezier|imagickdraw_circle|imagickdraw_clear|imagickdraw_clone|imagickdraw_color|imagickdraw_comment|imagickdraw_composite|imagickdraw_construct|imagickdraw_destroy|imagickdraw_ellipse|imagickdraw_getclippath|imagickdraw_getcliprule|imagickdraw_getclipunits|imagickdraw_getfillcolor|imagickdraw_getfillopacity|imagickdraw_getfillrule|imagickdraw_getfont|imagickdraw_getfontfamily|imagickdraw_getfontsize|imagickdraw_getfontstyle|imagickdraw_getfontweight|imagickdraw_getgravity|imagickdraw_getstrokeantialias|imagickdraw_getstrokecolor|imagickdraw_getstrokedasharray|imagickdraw_getstrokedashoffset|imagickdraw_getstrokelinecap|imagickdraw_getstrokelinejoin|imagickdraw_getstrokemiterlimit|imagickdraw_getstrokeopacity|imagickdraw_getstrokewidth|imagickdraw_gettextalignment|imagickdraw_gettextantialias|imagickdraw_gettextdecoration|imagickdraw_gettextencoding|imagickdraw_gettextundercolor|imagickdraw_getvectorgraphics|imagickdraw_line|imagickdraw_matte|imagickdraw_pathclose|imagickdraw_pathcurvetoabsolute|imagickdraw_pathcurvetoquadraticbezierabsolute|imagickdraw_pathcurvetoquadraticbezierrelative|imagickdraw_pathcurvetoquadraticbeziersmoothabsolute|imagickdraw_pathcurvetoquadraticbeziersmoothrelative|imagickdraw_pathcurvetorelative|imagickdraw_pathcurvetosmoothabsolute|imagickdraw_pathcurvetosmoothrelative|imagickdraw_pathellipticarcabsolute|imagickdraw_pathellipticarcrelative|imagickdraw_pathfinish|imagickdraw_pathlinetoabsolute|imagickdraw_pathlinetohorizontalabsolute|imagickdraw_pathlinetohorizontalrelative|imagickdraw_pathlinetorelative|imagickdraw_pathlinetoverticalabsolute|imagickdraw_pathlinetoverticalrelative|imagickdraw_pathmovetoabsolute|imagickdraw_pathmovetorelative|imagickdraw_pathstart|imagickdraw_point|imagickdraw_polygon|imagickdraw_polyline|imagickdraw_pop|imagickdraw_popclippath|imagickdraw_popdefs|imagickdraw_poppattern|imagickdraw_push|imagickdraw_pushclippath|imagickdraw_pushdefs|imagickdraw_pushpattern|imagickdraw_rectangle|imagickdraw_render|imagickdraw_rotate|imagickdraw_roundrectangle|imagickdraw_scale|imagickdraw_setclippath|imagickdraw_setcliprule|imagickdraw_setclipunits|imagickdraw_setfillalpha|imagickdraw_setfillcolor|imagickdraw_setfillopacity|imagickdraw_setfillpatternurl|imagickdraw_setfillrule|imagickdraw_setfont|imagickdraw_setfontfamily|imagickdraw_setfontsize|imagickdraw_setfontstretch|imagickdraw_setfontstyle|imagickdraw_setfontweight|imagickdraw_setgravity|imagickdraw_setstrokealpha|imagickdraw_setstrokeantialias|imagickdraw_setstrokecolor|imagickdraw_setstrokedasharray|imagickdraw_setstrokedashoffset|imagickdraw_setstrokelinecap|imagickdraw_setstrokelinejoin|imagickdraw_setstrokemiterlimit|imagickdraw_setstrokeopacity|imagickdraw_setstrokepatternurl|imagickdraw_setstrokewidth|imagickdraw_settextalignment|imagickdraw_settextantialias|imagickdraw_settextdecoration|imagickdraw_settextencoding|imagickdraw_settextundercolor|imagickdraw_setvectorgraphics|imagickdraw_setviewbox|imagickdraw_skewx|imagickdraw_skewy|imagickdraw_translate|imagickpixel|imagickpixel_clear|imagickpixel_construct|imagickpixel_destroy|imagickpixel_getcolor|imagickpixel_getcolorasstring|imagickpixel_getcolorcount|imagickpixel_getcolorvalue|imagickpixel_gethsl|imagickpixel_issimilar|imagickpixel_setcolor|imagickpixel_setcolorvalue|imagickpixel_sethsl|imagickpixeliterator|imagickpixeliterator_clear|imagickpixeliterator_construct|imagickpixeliterator_destroy|imagickpixeliterator_getcurrentiteratorrow|imagickpixeliterator_getiteratorrow|imagickpixeliterator_getnextiteratorrow|imagickpixeliterator_getpreviousiteratorrow|imagickpixeliterator_newpixeliterator|imagickpixeliterator_newpixelregioniterator|imagickpixeliterator_resetiterator|imagickpixeliterator_setiteratorfirstrow|imagickpixeliterator_setiteratorlastrow|imagickpixeliterator_setiteratorrow|imagickpixeliterator_synciterator|imap_8bit|imap_alerts|imap_append|imap_base64|imap_binary|imap_body|imap_bodystruct|imap_check|imap_clearflag_full|imap_close|imap_create|imap_createmailbox|imap_delete|imap_deletemailbox|imap_errors|imap_expunge|imap_fetch_overview|imap_fetchbody|imap_fetchheader|imap_fetchmime|imap_fetchstructure|imap_fetchtext|imap_gc|imap_get_quota|imap_get_quotaroot|imap_getacl|imap_getmailboxes|imap_getsubscribed|imap_header|imap_headerinfo|imap_headers|imap_last_error|imap_list|imap_listmailbox|imap_listscan|imap_listsubscribed|imap_lsub|imap_mail|imap_mail_compose|imap_mail_copy|imap_mail_move|imap_mailboxmsginfo|imap_mime_header_decode|imap_msgno|imap_num_msg|imap_num_recent|imap_open|imap_ping|imap_qprint|imap_rename|imap_renamemailbox|imap_reopen|imap_rfc822_parse_adrlist|imap_rfc822_parse_headers|imap_rfc822_write_address|imap_savebody|imap_scan|imap_scanmailbox|imap_search|imap_set_quota|imap_setacl|imap_setflag_full|imap_sort|imap_status|imap_subscribe|imap_thread|imap_timeout|imap_uid|imap_undelete|imap_unsubscribe|imap_utf7_decode|imap_utf7_encode|imap_utf8|implementsinterface|implode|import_request_variables|in_array|include|include_once|inclued_get_data|inet_ntop|inet_pton|infiniteiterator|ingres_autocommit|ingres_autocommit_state|ingres_charset|ingres_close|ingres_commit|ingres_connect|ingres_cursor|ingres_errno|ingres_error|ingres_errsqlstate|ingres_escape_string|ingres_execute|ingres_fetch_array|ingres_fetch_assoc|ingres_fetch_object|ingres_fetch_proc_return|ingres_fetch_row|ingres_field_length|ingres_field_name|ingres_field_nullable|ingres_field_precision|ingres_field_scale|ingres_field_type|ingres_free_result|ingres_next_error|ingres_num_fields|ingres_num_rows|ingres_pconnect|ingres_prepare|ingres_query|ingres_result_seek|ingres_rollback|ingres_set_environment|ingres_unbuffered_query|ini_alter|ini_get|ini_get_all|ini_restore|ini_set|innamespace|inotify_add_watch|inotify_init|inotify_queue_len|inotify_read|inotify_rm_watch|interface_exists|intl_error_name|intl_get_error_code|intl_get_error_message|intl_is_failure|intldateformatter|intval|invalidargumentexception|invoke|invokeargs|ip2long|iptcembed|iptcparse|is_a|is_array|is_bool|is_callable|is_dir|is_double|is_executable|is_file|is_finite|is_float|is_infinite|is_int|is_integer|is_link|is_long|is_nan|is_null|is_numeric|is_object|is_readable|is_real|is_resource|is_scalar|is_soap_fault|is_string|is_subclass_of|is_uploaded_file|is_writable|is_writeable|isabstract|iscloneable|isdisabled|isfinal|isinstance|isinstantiable|isinterface|isinternal|isiterateable|isset|issubclassof|isuserdefined|iterator|iterator_apply|iterator_count|iterator_to_array|iteratoraggregate|iteratoriterator|java_last_exception_clear|java_last_exception_get|jddayofweek|jdmonthname|jdtofrench|jdtogregorian|jdtojewish|jdtojulian|jdtounix|jewishtojd|join|jpeg2wbmp|json_decode|json_encode|json_last_error|jsonserializable|judy|judy_type|judy_version|juliantojd|kadm5_chpass_principal|kadm5_create_principal|kadm5_delete_principal|kadm5_destroy|kadm5_flush|kadm5_get_policies|kadm5_get_principal|kadm5_get_principals|kadm5_init_with_password|kadm5_modify_principal|key|krsort|ksort|lcfirst|lcg_value|lchgrp|lchown|ldap_8859_to_t61|ldap_add|ldap_bind|ldap_close|ldap_compare|ldap_connect|ldap_count_entries|ldap_delete|ldap_dn2ufn|ldap_err2str|ldap_errno|ldap_error|ldap_explode_dn|ldap_first_attribute|ldap_first_entry|ldap_first_reference|ldap_free_result|ldap_get_attributes|ldap_get_dn|ldap_get_entries|ldap_get_option|ldap_get_values|ldap_get_values_len|ldap_list|ldap_mod_add|ldap_mod_del|ldap_mod_replace|ldap_modify|ldap_next_attribute|ldap_next_entry|ldap_next_reference|ldap_parse_reference|ldap_parse_result|ldap_read|ldap_rename|ldap_sasl_bind|ldap_search|ldap_set_option|ldap_set_rebind_proc|ldap_sort|ldap_start_tls|ldap_t61_to_8859|ldap_unbind|lengthexception|levenshtein|libxml_clear_errors|libxml_disable_entity_loader|libxml_get_errors|libxml_get_last_error|libxml_set_streams_context|libxml_use_internal_errors|libxmlerror|limititerator|link|linkinfo|list|locale|localeconv|localtime|log|log10|log1p|logicexception|long2ip|lstat|ltrim|lzf_compress|lzf_decompress|lzf_optimized_for|m_checkstatus|m_completeauthorizations|m_connect|m_connectionerror|m_deletetrans|m_destroyconn|m_destroyengine|m_getcell|m_getcellbynum|m_getcommadelimited|m_getheader|m_initconn|m_initengine|m_iscommadelimited|m_maxconntimeout|m_monitor|m_numcolumns|m_numrows|m_parsecommadelimited|m_responsekeys|m_responseparam|m_returnstatus|m_setblocking|m_setdropfile|m_setip|m_setssl|m_setssl_cafile|m_setssl_files|m_settimeout|m_sslcert_gen_hash|m_transactionssent|m_transinqueue|m_transkeyval|m_transnew|m_transsend|m_uwait|m_validateidentifier|m_verifyconnection|m_verifysslcert|magic_quotes_runtime|mail|mailparse_determine_best_xfer_encoding|mailparse_msg_create|mailparse_msg_extract_part|mailparse_msg_extract_part_file|mailparse_msg_extract_whole_part_file|mailparse_msg_free|mailparse_msg_get_part|mailparse_msg_get_part_data|mailparse_msg_get_structure|mailparse_msg_parse|mailparse_msg_parse_file|mailparse_rfc822_parse_addresses|mailparse_stream_encode|mailparse_uudecode_all|main|max|maxdb_affected_rows|maxdb_autocommit|maxdb_bind_param|maxdb_bind_result|maxdb_change_user|maxdb_character_set_name|maxdb_client_encoding|maxdb_close|maxdb_close_long_data|maxdb_commit|maxdb_connect|maxdb_connect_errno|maxdb_connect_error|maxdb_data_seek|maxdb_debug|maxdb_disable_reads_from_master|maxdb_disable_rpl_parse|maxdb_dump_debug_info|maxdb_embedded_connect|maxdb_enable_reads_from_master|maxdb_enable_rpl_parse|maxdb_errno|maxdb_error|maxdb_escape_string|maxdb_execute|maxdb_fetch|maxdb_fetch_array|maxdb_fetch_assoc|maxdb_fetch_field|maxdb_fetch_field_direct|maxdb_fetch_fields|maxdb_fetch_lengths|maxdb_fetch_object|maxdb_fetch_row|maxdb_field_count|maxdb_field_seek|maxdb_field_tell|maxdb_free_result|maxdb_get_client_info|maxdb_get_client_version|maxdb_get_host_info|maxdb_get_metadata|maxdb_get_proto_info|maxdb_get_server_info|maxdb_get_server_version|maxdb_info|maxdb_init|maxdb_insert_id|maxdb_kill|maxdb_master_query|maxdb_more_results|maxdb_multi_query|maxdb_next_result|maxdb_num_fields|maxdb_num_rows|maxdb_options|maxdb_param_count|maxdb_ping|maxdb_prepare|maxdb_query|maxdb_real_connect|maxdb_real_escape_string|maxdb_real_query|maxdb_report|maxdb_rollback|maxdb_rpl_parse_enabled|maxdb_rpl_probe|maxdb_rpl_query_type|maxdb_select_db|maxdb_send_long_data|maxdb_send_query|maxdb_server_end|maxdb_server_init|maxdb_set_opt|maxdb_sqlstate|maxdb_ssl_set|maxdb_stat|maxdb_stmt_affected_rows|maxdb_stmt_bind_param|maxdb_stmt_bind_result|maxdb_stmt_close|maxdb_stmt_close_long_data|maxdb_stmt_data_seek|maxdb_stmt_errno|maxdb_stmt_error|maxdb_stmt_execute|maxdb_stmt_fetch|maxdb_stmt_free_result|maxdb_stmt_init|maxdb_stmt_num_rows|maxdb_stmt_param_count|maxdb_stmt_prepare|maxdb_stmt_reset|maxdb_stmt_result_metadata|maxdb_stmt_send_long_data|maxdb_stmt_sqlstate|maxdb_stmt_store_result|maxdb_store_result|maxdb_thread_id|maxdb_thread_safe|maxdb_use_result|maxdb_warning_count|mb_check_encoding|mb_convert_case|mb_convert_encoding|mb_convert_kana|mb_convert_variables|mb_decode_mimeheader|mb_decode_numericentity|mb_detect_encoding|mb_detect_order|mb_encode_mimeheader|mb_encode_numericentity|mb_encoding_aliases|mb_ereg|mb_ereg_match|mb_ereg_replace|mb_ereg_search|mb_ereg_search_getpos|mb_ereg_search_getregs|mb_ereg_search_init|mb_ereg_search_pos|mb_ereg_search_regs|mb_ereg_search_setpos|mb_eregi|mb_eregi_replace|mb_get_info|mb_http_input|mb_http_output|mb_internal_encoding|mb_language|mb_list_encodings|mb_output_handler|mb_parse_str|mb_preferred_mime_name|mb_regex_encoding|mb_regex_set_options|mb_send_mail|mb_split|mb_strcut|mb_strimwidth|mb_stripos|mb_stristr|mb_strlen|mb_strpos|mb_strrchr|mb_strrichr|mb_strripos|mb_strrpos|mb_strstr|mb_strtolower|mb_strtoupper|mb_strwidth|mb_substitute_character|mb_substr|mb_substr_count|mcrypt_cbc|mcrypt_cfb|mcrypt_create_iv|mcrypt_decrypt|mcrypt_ecb|mcrypt_enc_get_algorithms_name|mcrypt_enc_get_block_size|mcrypt_enc_get_iv_size|mcrypt_enc_get_key_size|mcrypt_enc_get_modes_name|mcrypt_enc_get_supported_key_sizes|mcrypt_enc_is_block_algorithm|mcrypt_enc_is_block_algorithm_mode|mcrypt_enc_is_block_mode|mcrypt_enc_self_test|mcrypt_encrypt|mcrypt_generic|mcrypt_generic_deinit|mcrypt_generic_end|mcrypt_generic_init|mcrypt_get_block_size|mcrypt_get_cipher_name|mcrypt_get_iv_size|mcrypt_get_key_size|mcrypt_list_algorithms|mcrypt_list_modes|mcrypt_module_close|mcrypt_module_get_algo_block_size|mcrypt_module_get_algo_key_size|mcrypt_module_get_supported_key_sizes|mcrypt_module_is_block_algorithm|mcrypt_module_is_block_algorithm_mode|mcrypt_module_is_block_mode|mcrypt_module_open|mcrypt_module_self_test|mcrypt_ofb|md5|md5_file|mdecrypt_generic|memcache|memcache_debug|memcached|memory_get_peak_usage|memory_get_usage|messageformatter|metaphone|method_exists|mhash|mhash_count|mhash_get_block_size|mhash_get_hash_name|mhash_keygen_s2k|microtime|mime_content_type|min|ming_keypress|ming_setcubicthreshold|ming_setscale|ming_setswfcompression|ming_useconstants|ming_useswfversion|mkdir|mktime|money_format|mongo|mongobindata|mongocode|mongocollection|mongoconnectionexception|mongocursor|mongocursorexception|mongocursortimeoutexception|mongodate|mongodb|mongodbref|mongoexception|mongogridfs|mongogridfscursor|mongogridfsexception|mongogridfsfile|mongoid|mongoint32|mongoint64|mongomaxkey|mongominkey|mongoregex|mongotimestamp|move_uploaded_file|mpegfile|mqseries_back|mqseries_begin|mqseries_close|mqseries_cmit|mqseries_conn|mqseries_connx|mqseries_disc|mqseries_get|mqseries_inq|mqseries_open|mqseries_put|mqseries_put1|mqseries_set|mqseries_strerror|msession_connect|msession_count|msession_create|msession_destroy|msession_disconnect|msession_find|msession_get|msession_get_array|msession_get_data|msession_inc|msession_list|msession_listvar|msession_lock|msession_plugin|msession_randstr|msession_set|msession_set_array|msession_set_data|msession_timeout|msession_uniq|msession_unlock|msg_get_queue|msg_queue_exists|msg_receive|msg_remove_queue|msg_send|msg_set_queue|msg_stat_queue|msql|msql_affected_rows|msql_close|msql_connect|msql_create_db|msql_createdb|msql_data_seek|msql_db_query|msql_dbname|msql_drop_db|msql_error|msql_fetch_array|msql_fetch_field|msql_fetch_object|msql_fetch_row|msql_field_flags|msql_field_len|msql_field_name|msql_field_seek|msql_field_table|msql_field_type|msql_fieldflags|msql_fieldlen|msql_fieldname|msql_fieldtable|msql_fieldtype|msql_free_result|msql_list_dbs|msql_list_fields|msql_list_tables|msql_num_fields|msql_num_rows|msql_numfields|msql_numrows|msql_pconnect|msql_query|msql_regcase|msql_result|msql_select_db|msql_tablename|mssql_bind|mssql_close|mssql_connect|mssql_data_seek|mssql_execute|mssql_fetch_array|mssql_fetch_assoc|mssql_fetch_batch|mssql_fetch_field|mssql_fetch_object|mssql_fetch_row|mssql_field_length|mssql_field_name|mssql_field_seek|mssql_field_type|mssql_free_result|mssql_free_statement|mssql_get_last_message|mssql_guid_string|mssql_init|mssql_min_error_severity|mssql_min_message_severity|mssql_next_result|mssql_num_fields|mssql_num_rows|mssql_pconnect|mssql_query|mssql_result|mssql_rows_affected|mssql_select_db|mt_getrandmax|mt_rand|mt_srand|multipleiterator|mysql_affected_rows|mysql_client_encoding|mysql_close|mysql_connect|mysql_create_db|mysql_data_seek|mysql_db_name|mysql_db_query|mysql_drop_db|mysql_errno|mysql_error|mysql_escape_string|mysql_fetch_array|mysql_fetch_assoc|mysql_fetch_field|mysql_fetch_lengths|mysql_fetch_object|mysql_fetch_row|mysql_field_flags|mysql_field_len|mysql_field_name|mysql_field_seek|mysql_field_table|mysql_field_type|mysql_free_result|mysql_get_client_info|mysql_get_host_info|mysql_get_proto_info|mysql_get_server_info|mysql_info|mysql_insert_id|mysql_list_dbs|mysql_list_fields|mysql_list_processes|mysql_list_tables|mysql_num_fields|mysql_num_rows|mysql_pconnect|mysql_ping|mysql_query|mysql_real_escape_string|mysql_result|mysql_select_db|mysql_set_charset|mysql_stat|mysql_tablename|mysql_thread_id|mysql_unbuffered_query|mysqli|mysqli_affected_rows|mysqli_autocommit|mysqli_bind_param|mysqli_bind_result|mysqli_cache_stats|mysqli_change_user|mysqli_character_set_name|mysqli_client_encoding|mysqli_close|mysqli_commit|mysqli_connect|mysqli_connect_errno|mysqli_connect_error|mysqli_data_seek|mysqli_debug|mysqli_disable_reads_from_master|mysqli_disable_rpl_parse|mysqli_driver|mysqli_dump_debug_info|mysqli_embedded_server_end|mysqli_embedded_server_start|mysqli_enable_reads_from_master|mysqli_enable_rpl_parse|mysqli_errno|mysqli_error|mysqli_escape_string|mysqli_execute|mysqli_fetch|mysqli_fetch_all|mysqli_fetch_array|mysqli_fetch_assoc|mysqli_fetch_field|mysqli_fetch_field_direct|mysqli_fetch_fields|mysqli_fetch_lengths|mysqli_fetch_object|mysqli_fetch_row|mysqli_field_count|mysqli_field_seek|mysqli_field_tell|mysqli_free_result|mysqli_get_charset|mysqli_get_client_info|mysqli_get_client_stats|mysqli_get_client_version|mysqli_get_connection_stats|mysqli_get_host_info|mysqli_get_metadata|mysqli_get_proto_info|mysqli_get_server_info|mysqli_get_server_version|mysqli_get_warnings|mysqli_info|mysqli_init|mysqli_insert_id|mysqli_kill|mysqli_link_construct|mysqli_master_query|mysqli_more_results|mysqli_multi_query|mysqli_next_result|mysqli_num_fields|mysqli_num_rows|mysqli_options|mysqli_param_count|mysqli_ping|mysqli_poll|mysqli_prepare|mysqli_query|mysqli_real_connect|mysqli_real_escape_string|mysqli_real_query|mysqli_reap_async_query|mysqli_refresh|mysqli_report|mysqli_result|mysqli_rollback|mysqli_rpl_parse_enabled|mysqli_rpl_probe|mysqli_rpl_query_type|mysqli_select_db|mysqli_send_long_data|mysqli_send_query|mysqli_set_charset|mysqli_set_local_infile_default|mysqli_set_local_infile_handler|mysqli_set_opt|mysqli_slave_query|mysqli_sqlstate|mysqli_ssl_set|mysqli_stat|mysqli_stmt|mysqli_stmt_affected_rows|mysqli_stmt_attr_get|mysqli_stmt_attr_set|mysqli_stmt_bind_param|mysqli_stmt_bind_result|mysqli_stmt_close|mysqli_stmt_data_seek|mysqli_stmt_errno|mysqli_stmt_error|mysqli_stmt_execute|mysqli_stmt_fetch|mysqli_stmt_field_count|mysqli_stmt_free_result|mysqli_stmt_get_result|mysqli_stmt_get_warnings|mysqli_stmt_init|mysqli_stmt_insert_id|mysqli_stmt_next_result|mysqli_stmt_num_rows|mysqli_stmt_param_count|mysqli_stmt_prepare|mysqli_stmt_reset|mysqli_stmt_result_metadata|mysqli_stmt_send_long_data|mysqli_stmt_sqlstate|mysqli_stmt_store_result|mysqli_store_result|mysqli_thread_id|mysqli_thread_safe|mysqli_use_result|mysqli_warning|mysqli_warning_count|mysqlnd_ms_get_stats|mysqlnd_ms_query_is_select|mysqlnd_ms_set_user_pick_server|mysqlnd_qc_change_handler|mysqlnd_qc_clear_cache|mysqlnd_qc_get_cache_info|mysqlnd_qc_get_core_stats|mysqlnd_qc_get_handler|mysqlnd_qc_get_query_trace_log|mysqlnd_qc_set_user_handlers|natcasesort|natsort|ncurses_addch|ncurses_addchnstr|ncurses_addchstr|ncurses_addnstr|ncurses_addstr|ncurses_assume_default_colors|ncurses_attroff|ncurses_attron|ncurses_attrset|ncurses_baudrate|ncurses_beep|ncurses_bkgd|ncurses_bkgdset|ncurses_border|ncurses_bottom_panel|ncurses_can_change_color|ncurses_cbreak|ncurses_clear|ncurses_clrtobot|ncurses_clrtoeol|ncurses_color_content|ncurses_color_set|ncurses_curs_set|ncurses_def_prog_mode|ncurses_def_shell_mode|ncurses_define_key|ncurses_del_panel|ncurses_delay_output|ncurses_delch|ncurses_deleteln|ncurses_delwin|ncurses_doupdate|ncurses_echo|ncurses_echochar|ncurses_end|ncurses_erase|ncurses_erasechar|ncurses_filter|ncurses_flash|ncurses_flushinp|ncurses_getch|ncurses_getmaxyx|ncurses_getmouse|ncurses_getyx|ncurses_halfdelay|ncurses_has_colors|ncurses_has_ic|ncurses_has_il|ncurses_has_key|ncurses_hide_panel|ncurses_hline|ncurses_inch|ncurses_init|ncurses_init_color|ncurses_init_pair|ncurses_insch|ncurses_insdelln|ncurses_insertln|ncurses_insstr|ncurses_instr|ncurses_isendwin|ncurses_keyok|ncurses_keypad|ncurses_killchar|ncurses_longname|ncurses_meta|ncurses_mouse_trafo|ncurses_mouseinterval|ncurses_mousemask|ncurses_move|ncurses_move_panel|ncurses_mvaddch|ncurses_mvaddchnstr|ncurses_mvaddchstr|ncurses_mvaddnstr|ncurses_mvaddstr|ncurses_mvcur|ncurses_mvdelch|ncurses_mvgetch|ncurses_mvhline|ncurses_mvinch|ncurses_mvvline|ncurses_mvwaddstr|ncurses_napms|ncurses_new_panel|ncurses_newpad|ncurses_newwin|ncurses_nl|ncurses_nocbreak|ncurses_noecho|ncurses_nonl|ncurses_noqiflush|ncurses_noraw|ncurses_pair_content|ncurses_panel_above|ncurses_panel_below|ncurses_panel_window|ncurses_pnoutrefresh|ncurses_prefresh|ncurses_putp|ncurses_qiflush|ncurses_raw|ncurses_refresh|ncurses_replace_panel|ncurses_reset_prog_mode|ncurses_reset_shell_mode|ncurses_resetty|ncurses_savetty|ncurses_scr_dump|ncurses_scr_init|ncurses_scr_restore|ncurses_scr_set|ncurses_scrl|ncurses_show_panel|ncurses_slk_attr|ncurses_slk_attroff|ncurses_slk_attron|ncurses_slk_attrset|ncurses_slk_clear|ncurses_slk_color|ncurses_slk_init|ncurses_slk_noutrefresh|ncurses_slk_refresh|ncurses_slk_restore|ncurses_slk_set|ncurses_slk_touch|ncurses_standend|ncurses_standout|ncurses_start_color|ncurses_termattrs|ncurses_termname|ncurses_timeout|ncurses_top_panel|ncurses_typeahead|ncurses_ungetch|ncurses_ungetmouse|ncurses_update_panels|ncurses_use_default_colors|ncurses_use_env|ncurses_use_extended_names|ncurses_vidattr|ncurses_vline|ncurses_waddch|ncurses_waddstr|ncurses_wattroff|ncurses_wattron|ncurses_wattrset|ncurses_wborder|ncurses_wclear|ncurses_wcolor_set|ncurses_werase|ncurses_wgetch|ncurses_whline|ncurses_wmouse_trafo|ncurses_wmove|ncurses_wnoutrefresh|ncurses_wrefresh|ncurses_wstandend|ncurses_wstandout|ncurses_wvline|newinstance|newinstanceargs|newt_bell|newt_button|newt_button_bar|newt_centered_window|newt_checkbox|newt_checkbox_get_value|newt_checkbox_set_flags|newt_checkbox_set_value|newt_checkbox_tree|newt_checkbox_tree_add_item|newt_checkbox_tree_find_item|newt_checkbox_tree_get_current|newt_checkbox_tree_get_entry_value|newt_checkbox_tree_get_multi_selection|newt_checkbox_tree_get_selection|newt_checkbox_tree_multi|newt_checkbox_tree_set_current|newt_checkbox_tree_set_entry|newt_checkbox_tree_set_entry_value|newt_checkbox_tree_set_width|newt_clear_key_buffer|newt_cls|newt_compact_button|newt_component_add_callback|newt_component_takes_focus|newt_create_grid|newt_cursor_off|newt_cursor_on|newt_delay|newt_draw_form|newt_draw_root_text|newt_entry|newt_entry_get_value|newt_entry_set|newt_entry_set_filter|newt_entry_set_flags|newt_finished|newt_form|newt_form_add_component|newt_form_add_components|newt_form_add_hot_key|newt_form_destroy|newt_form_get_current|newt_form_run|newt_form_set_background|newt_form_set_height|newt_form_set_size|newt_form_set_timer|newt_form_set_width|newt_form_watch_fd|newt_get_screen_size|newt_grid_add_components_to_form|newt_grid_basic_window|newt_grid_free|newt_grid_get_size|newt_grid_h_close_stacked|newt_grid_h_stacked|newt_grid_place|newt_grid_set_field|newt_grid_simple_window|newt_grid_v_close_stacked|newt_grid_v_stacked|newt_grid_wrapped_window|newt_grid_wrapped_window_at|newt_init|newt_label|newt_label_set_text|newt_listbox|newt_listbox_append_entry|newt_listbox_clear|newt_listbox_clear_selection|newt_listbox_delete_entry|newt_listbox_get_current|newt_listbox_get_selection|newt_listbox_insert_entry|newt_listbox_item_count|newt_listbox_select_item|newt_listbox_set_current|newt_listbox_set_current_by_key|newt_listbox_set_data|newt_listbox_set_entry|newt_listbox_set_width|newt_listitem|newt_listitem_get_data|newt_listitem_set|newt_open_window|newt_pop_help_line|newt_pop_window|newt_push_help_line|newt_radio_get_current|newt_radiobutton|newt_redraw_help_line|newt_reflow_text|newt_refresh|newt_resize_screen|newt_resume|newt_run_form|newt_scale|newt_scale_set|newt_scrollbar_set|newt_set_help_callback|newt_set_suspend_callback|newt_suspend|newt_textbox|newt_textbox_get_num_lines|newt_textbox_reflowed|newt_textbox_set_height|newt_textbox_set_text|newt_vertical_scrollbar|newt_wait_for_key|newt_win_choice|newt_win_entries|newt_win_menu|newt_win_message|newt_win_messagev|newt_win_ternary|next|ngettext|nl2br|nl_langinfo|norewinditerator|normalizer|notes_body|notes_copy_db|notes_create_db|notes_create_note|notes_drop_db|notes_find_note|notes_header_info|notes_list_msgs|notes_mark_read|notes_mark_unread|notes_nav_create|notes_search|notes_unread|notes_version|nsapi_request_headers|nsapi_response_headers|nsapi_virtual|nthmac|number_format|numberformatter|oauth|oauth_get_sbs|oauth_urlencode|oauthexception|oauthprovider|ob_clean|ob_deflatehandler|ob_end_clean|ob_end_flush|ob_etaghandler|ob_flush|ob_get_clean|ob_get_contents|ob_get_flush|ob_get_length|ob_get_level|ob_get_status|ob_gzhandler|ob_iconv_handler|ob_implicit_flush|ob_inflatehandler|ob_list_handlers|ob_start|ob_tidyhandler|oci_bind_array_by_name|oci_bind_by_name|oci_cancel|oci_client_version|oci_close|oci_collection_append|oci_collection_assign|oci_collection_element_assign|oci_collection_element_get|oci_collection_free|oci_collection_max|oci_collection_size|oci_collection_trim|oci_commit|oci_connect|oci_define_by_name|oci_error|oci_execute|oci_fetch|oci_fetch_all|oci_fetch_array|oci_fetch_assoc|oci_fetch_object|oci_fetch_row|oci_field_is_null|oci_field_name|oci_field_precision|oci_field_scale|oci_field_size|oci_field_type|oci_field_type_raw|oci_free_statement|oci_internal_debug|oci_lob_append|oci_lob_close|oci_lob_copy|oci_lob_eof|oci_lob_erase|oci_lob_export|oci_lob_flush|oci_lob_free|oci_lob_getbuffering|oci_lob_import|oci_lob_is_equal|oci_lob_load|oci_lob_read|oci_lob_rewind|oci_lob_save|oci_lob_savefile|oci_lob_seek|oci_lob_setbuffering|oci_lob_size|oci_lob_tell|oci_lob_truncate|oci_lob_write|oci_lob_writetemporary|oci_lob_writetofile|oci_new_collection|oci_new_connect|oci_new_cursor|oci_new_descriptor|oci_num_fields|oci_num_rows|oci_parse|oci_password_change|oci_pconnect|oci_result|oci_rollback|oci_server_version|oci_set_action|oci_set_client_identifier|oci_set_client_info|oci_set_edition|oci_set_module_name|oci_set_prefetch|oci_statement_type|ocibindbyname|ocicancel|ocicloselob|ocicollappend|ocicollassign|ocicollassignelem|ocicollgetelem|ocicollmax|ocicollsize|ocicolltrim|ocicolumnisnull|ocicolumnname|ocicolumnprecision|ocicolumnscale|ocicolumnsize|ocicolumntype|ocicolumntyperaw|ocicommit|ocidefinebyname|ocierror|ociexecute|ocifetch|ocifetchinto|ocifetchstatement|ocifreecollection|ocifreecursor|ocifreedesc|ocifreestatement|ociinternaldebug|ociloadlob|ocilogoff|ocilogon|ocinewcollection|ocinewcursor|ocinewdescriptor|ocinlogon|ocinumcols|ociparse|ociplogon|ociresult|ocirollback|ocirowcount|ocisavelob|ocisavelobfile|ociserverversion|ocisetprefetch|ocistatementtype|ociwritelobtofile|ociwritetemporarylob|octdec|odbc_autocommit|odbc_binmode|odbc_close|odbc_close_all|odbc_columnprivileges|odbc_columns|odbc_commit|odbc_connect|odbc_cursor|odbc_data_source|odbc_do|odbc_error|odbc_errormsg|odbc_exec|odbc_execute|odbc_fetch_array|odbc_fetch_into|odbc_fetch_object|odbc_fetch_row|odbc_field_len|odbc_field_name|odbc_field_num|odbc_field_precision|odbc_field_scale|odbc_field_type|odbc_foreignkeys|odbc_free_result|odbc_gettypeinfo|odbc_longreadlen|odbc_next_result|odbc_num_fields|odbc_num_rows|odbc_pconnect|odbc_prepare|odbc_primarykeys|odbc_procedurecolumns|odbc_procedures|odbc_result|odbc_result_all|odbc_rollback|odbc_setoption|odbc_specialcolumns|odbc_statistics|odbc_tableprivileges|odbc_tables|openal_buffer_create|openal_buffer_data|openal_buffer_destroy|openal_buffer_get|openal_buffer_loadwav|openal_context_create|openal_context_current|openal_context_destroy|openal_context_process|openal_context_suspend|openal_device_close|openal_device_open|openal_listener_get|openal_listener_set|openal_source_create|openal_source_destroy|openal_source_get|openal_source_pause|openal_source_play|openal_source_rewind|openal_source_set|openal_source_stop|openal_stream|opendir|openlog|openssl_cipher_iv_length|openssl_csr_export|openssl_csr_export_to_file|openssl_csr_get_public_key|openssl_csr_get_subject|openssl_csr_new|openssl_csr_sign|openssl_decrypt|openssl_dh_compute_key|openssl_digest|openssl_encrypt|openssl_error_string|openssl_free_key|openssl_get_cipher_methods|openssl_get_md_methods|openssl_get_privatekey|openssl_get_publickey|openssl_open|openssl_pkcs12_export|openssl_pkcs12_export_to_file|openssl_pkcs12_read|openssl_pkcs7_decrypt|openssl_pkcs7_encrypt|openssl_pkcs7_sign|openssl_pkcs7_verify|openssl_pkey_export|openssl_pkey_export_to_file|openssl_pkey_free|openssl_pkey_get_details|openssl_pkey_get_private|openssl_pkey_get_public|openssl_pkey_new|openssl_private_decrypt|openssl_private_encrypt|openssl_public_decrypt|openssl_public_encrypt|openssl_random_pseudo_bytes|openssl_seal|openssl_sign|openssl_verify|openssl_x509_check_private_key|openssl_x509_checkpurpose|openssl_x509_export|openssl_x509_export_to_file|openssl_x509_free|openssl_x509_parse|openssl_x509_read|ord|outeriterator|outofboundsexception|outofrangeexception|output_add_rewrite_var|output_reset_rewrite_vars|overflowexception|overload|override_function|ovrimos_close|ovrimos_commit|ovrimos_connect|ovrimos_cursor|ovrimos_exec|ovrimos_execute|ovrimos_fetch_into|ovrimos_fetch_row|ovrimos_field_len|ovrimos_field_name|ovrimos_field_num|ovrimos_field_type|ovrimos_free_result|ovrimos_longreadlen|ovrimos_num_fields|ovrimos_num_rows|ovrimos_prepare|ovrimos_result|ovrimos_result_all|ovrimos_rollback|pack|parentiterator|parse_ini_file|parse_ini_string|parse_str|parse_url|parsekit_compile_file|parsekit_compile_string|parsekit_func_arginfo|passthru|pathinfo|pclose|pcntl_alarm|pcntl_exec|pcntl_fork|pcntl_getpriority|pcntl_setpriority|pcntl_signal|pcntl_signal_dispatch|pcntl_sigprocmask|pcntl_sigtimedwait|pcntl_sigwaitinfo|pcntl_wait|pcntl_waitpid|pcntl_wexitstatus|pcntl_wifexited|pcntl_wifsignaled|pcntl_wifstopped|pcntl_wstopsig|pcntl_wtermsig|pdf_activate_item|pdf_add_annotation|pdf_add_bookmark|pdf_add_launchlink|pdf_add_locallink|pdf_add_nameddest|pdf_add_note|pdf_add_outline|pdf_add_pdflink|pdf_add_table_cell|pdf_add_textflow|pdf_add_thumbnail|pdf_add_weblink|pdf_arc|pdf_arcn|pdf_attach_file|pdf_begin_document|pdf_begin_font|pdf_begin_glyph|pdf_begin_item|pdf_begin_layer|pdf_begin_page|pdf_begin_page_ext|pdf_begin_pattern|pdf_begin_template|pdf_begin_template_ext|pdf_circle|pdf_clip|pdf_close|pdf_close_image|pdf_close_pdi|pdf_close_pdi_page|pdf_closepath|pdf_closepath_fill_stroke|pdf_closepath_stroke|pdf_concat|pdf_continue_text|pdf_create_3dview|pdf_create_action|pdf_create_annotation|pdf_create_bookmark|pdf_create_field|pdf_create_fieldgroup|pdf_create_gstate|pdf_create_pvf|pdf_create_textflow|pdf_curveto|pdf_define_layer|pdf_delete|pdf_delete_pvf|pdf_delete_table|pdf_delete_textflow|pdf_encoding_set_char|pdf_end_document|pdf_end_font|pdf_end_glyph|pdf_end_item|pdf_end_layer|pdf_end_page|pdf_end_page_ext|pdf_end_pattern|pdf_end_template|pdf_endpath|pdf_fill|pdf_fill_imageblock|pdf_fill_pdfblock|pdf_fill_stroke|pdf_fill_textblock|pdf_findfont|pdf_fit_image|pdf_fit_pdi_page|pdf_fit_table|pdf_fit_textflow|pdf_fit_textline|pdf_get_apiname|pdf_get_buffer|pdf_get_errmsg|pdf_get_errnum|pdf_get_font|pdf_get_fontname|pdf_get_fontsize|pdf_get_image_height|pdf_get_image_width|pdf_get_majorversion|pdf_get_minorversion|pdf_get_parameter|pdf_get_pdi_parameter|pdf_get_pdi_value|pdf_get_value|pdf_info_font|pdf_info_matchbox|pdf_info_table|pdf_info_textflow|pdf_info_textline|pdf_initgraphics|pdf_lineto|pdf_load_3ddata|pdf_load_font|pdf_load_iccprofile|pdf_load_image|pdf_makespotcolor|pdf_moveto|pdf_new|pdf_open_ccitt|pdf_open_file|pdf_open_gif|pdf_open_image|pdf_open_image_file|pdf_open_jpeg|pdf_open_memory_image|pdf_open_pdi|pdf_open_pdi_document|pdf_open_pdi_page|pdf_open_tiff|pdf_pcos_get_number|pdf_pcos_get_stream|pdf_pcos_get_string|pdf_place_image|pdf_place_pdi_page|pdf_process_pdi|pdf_rect|pdf_restore|pdf_resume_page|pdf_rotate|pdf_save|pdf_scale|pdf_set_border_color|pdf_set_border_dash|pdf_set_border_style|pdf_set_char_spacing|pdf_set_duration|pdf_set_gstate|pdf_set_horiz_scaling|pdf_set_info|pdf_set_info_author|pdf_set_info_creator|pdf_set_info_keywords|pdf_set_info_subject|pdf_set_info_title|pdf_set_layer_dependency|pdf_set_leading|pdf_set_parameter|pdf_set_text_matrix|pdf_set_text_pos|pdf_set_text_rendering|pdf_set_text_rise|pdf_set_value|pdf_set_word_spacing|pdf_setcolor|pdf_setdash|pdf_setdashpattern|pdf_setflat|pdf_setfont|pdf_setgray|pdf_setgray_fill|pdf_setgray_stroke|pdf_setlinecap|pdf_setlinejoin|pdf_setlinewidth|pdf_setmatrix|pdf_setmiterlimit|pdf_setpolydash|pdf_setrgbcolor|pdf_setrgbcolor_fill|pdf_setrgbcolor_stroke|pdf_shading|pdf_shading_pattern|pdf_shfill|pdf_show|pdf_show_boxed|pdf_show_xy|pdf_skew|pdf_stringwidth|pdf_stroke|pdf_suspend_page|pdf_translate|pdf_utf16_to_utf8|pdf_utf32_to_utf16|pdf_utf8_to_utf16|pdo|pdo_cubrid_schema|pdo_pgsqllobcreate|pdo_pgsqllobopen|pdo_pgsqllobunlink|pdo_sqlitecreateaggregate|pdo_sqlitecreatefunction|pdoexception|pdostatement|pfsockopen|pg_affected_rows|pg_cancel_query|pg_client_encoding|pg_close|pg_connect|pg_connection_busy|pg_connection_reset|pg_connection_status|pg_convert|pg_copy_from|pg_copy_to|pg_dbname|pg_delete|pg_end_copy|pg_escape_bytea|pg_escape_string|pg_execute|pg_fetch_all|pg_fetch_all_columns|pg_fetch_array|pg_fetch_assoc|pg_fetch_object|pg_fetch_result|pg_fetch_row|pg_field_is_null|pg_field_name|pg_field_num|pg_field_prtlen|pg_field_size|pg_field_table|pg_field_type|pg_field_type_oid|pg_free_result|pg_get_notify|pg_get_pid|pg_get_result|pg_host|pg_insert|pg_last_error|pg_last_notice|pg_last_oid|pg_lo_close|pg_lo_create|pg_lo_export|pg_lo_import|pg_lo_open|pg_lo_read|pg_lo_read_all|pg_lo_seek|pg_lo_tell|pg_lo_unlink|pg_lo_write|pg_meta_data|pg_num_fields|pg_num_rows|pg_options|pg_parameter_status|pg_pconnect|pg_ping|pg_port|pg_prepare|pg_put_line|pg_query|pg_query_params|pg_result_error|pg_result_error_field|pg_result_seek|pg_result_status|pg_select|pg_send_execute|pg_send_prepare|pg_send_query|pg_send_query_params|pg_set_client_encoding|pg_set_error_verbosity|pg_trace|pg_transaction_status|pg_tty|pg_unescape_bytea|pg_untrace|pg_update|pg_version|php_check_syntax|php_ini_loaded_file|php_ini_scanned_files|php_logo_guid|php_sapi_name|php_strip_whitespace|php_uname|phpcredits|phpinfo|phpversion|pi|png2wbmp|popen|pos|posix_access|posix_ctermid|posix_errno|posix_get_last_error|posix_getcwd|posix_getegid|posix_geteuid|posix_getgid|posix_getgrgid|posix_getgrnam|posix_getgroups|posix_getlogin|posix_getpgid|posix_getpgrp|posix_getpid|posix_getppid|posix_getpwnam|posix_getpwuid|posix_getrlimit|posix_getsid|posix_getuid|posix_initgroups|posix_isatty|posix_kill|posix_mkfifo|posix_mknod|posix_setegid|posix_seteuid|posix_setgid|posix_setpgid|posix_setsid|posix_setuid|posix_strerror|posix_times|posix_ttyname|posix_uname|pow|preg_filter|preg_grep|preg_last_error|preg_match|preg_match_all|preg_quote|preg_replace|preg_replace_callback|preg_split|prev|print|print_r|printer_abort|printer_close|printer_create_brush|printer_create_dc|printer_create_font|printer_create_pen|printer_delete_brush|printer_delete_dc|printer_delete_font|printer_delete_pen|printer_draw_bmp|printer_draw_chord|printer_draw_elipse|printer_draw_line|printer_draw_pie|printer_draw_rectangle|printer_draw_roundrect|printer_draw_text|printer_end_doc|printer_end_page|printer_get_option|printer_list|printer_logical_fontheight|printer_open|printer_select_brush|printer_select_font|printer_select_pen|printer_set_option|printer_start_doc|printer_start_page|printer_write|printf|proc_close|proc_get_status|proc_nice|proc_open|proc_terminate|property_exists|ps_add_bookmark|ps_add_launchlink|ps_add_locallink|ps_add_note|ps_add_pdflink|ps_add_weblink|ps_arc|ps_arcn|ps_begin_page|ps_begin_pattern|ps_begin_template|ps_circle|ps_clip|ps_close|ps_close_image|ps_closepath|ps_closepath_stroke|ps_continue_text|ps_curveto|ps_delete|ps_end_page|ps_end_pattern|ps_end_template|ps_fill|ps_fill_stroke|ps_findfont|ps_get_buffer|ps_get_parameter|ps_get_value|ps_hyphenate|ps_include_file|ps_lineto|ps_makespotcolor|ps_moveto|ps_new|ps_open_file|ps_open_image|ps_open_image_file|ps_open_memory_image|ps_place_image|ps_rect|ps_restore|ps_rotate|ps_save|ps_scale|ps_set_border_color|ps_set_border_dash|ps_set_border_style|ps_set_info|ps_set_parameter|ps_set_text_pos|ps_set_value|ps_setcolor|ps_setdash|ps_setflat|ps_setfont|ps_setgray|ps_setlinecap|ps_setlinejoin|ps_setlinewidth|ps_setmiterlimit|ps_setoverprintmode|ps_setpolydash|ps_shading|ps_shading_pattern|ps_shfill|ps_show|ps_show2|ps_show_boxed|ps_show_xy|ps_show_xy2|ps_string_geometry|ps_stringwidth|ps_stroke|ps_symbol|ps_symbol_name|ps_symbol_width|ps_translate|pspell_add_to_personal|pspell_add_to_session|pspell_check|pspell_clear_session|pspell_config_create|pspell_config_data_dir|pspell_config_dict_dir|pspell_config_ignore|pspell_config_mode|pspell_config_personal|pspell_config_repl|pspell_config_runtogether|pspell_config_save_repl|pspell_new|pspell_new_config|pspell_new_personal|pspell_save_wordlist|pspell_store_replacement|pspell_suggest|putenv|px_close|px_create_fp|px_date2string|px_delete|px_delete_record|px_get_field|px_get_info|px_get_parameter|px_get_record|px_get_schema|px_get_value|px_insert_record|px_new|px_numfields|px_numrecords|px_open_fp|px_put_record|px_retrieve_record|px_set_blob_file|px_set_parameter|px_set_tablename|px_set_targetencoding|px_set_value|px_timestamp2string|px_update_record|qdom_error|qdom_tree|quoted_printable_decode|quoted_printable_encode|quotemeta|rad2deg|radius_acct_open|radius_add_server|radius_auth_open|radius_close|radius_config|radius_create_request|radius_cvt_addr|radius_cvt_int|radius_cvt_string|radius_demangle|radius_demangle_mppe_key|radius_get_attr|radius_get_vendor_attr|radius_put_addr|radius_put_attr|radius_put_int|radius_put_string|radius_put_vendor_addr|radius_put_vendor_attr|radius_put_vendor_int|radius_put_vendor_string|radius_request_authenticator|radius_send_request|radius_server_secret|radius_strerror|rand|range|rangeexception|rar_wrapper_cache_stats|rararchive|rarentry|rarexception|rawurldecode|rawurlencode|read_exif_data|readdir|readfile|readgzfile|readline|readline_add_history|readline_callback_handler_install|readline_callback_handler_remove|readline_callback_read_char|readline_clear_history|readline_completion_function|readline_info|readline_list_history|readline_on_new_line|readline_read_history|readline_redisplay|readline_write_history|readlink|realpath|realpath_cache_get|realpath_cache_size|recode|recode_file|recode_string|recursivearrayiterator|recursivecachingiterator|recursivecallbackfilteriterator|recursivedirectoryiterator|recursivefilteriterator|recursiveiterator|recursiveiteratoriterator|recursiveregexiterator|recursivetreeiterator|reflection|reflectionclass|reflectionexception|reflectionextension|reflectionfunction|reflectionfunctionabstract|reflectionmethod|reflectionobject|reflectionparameter|reflectionproperty|reflector|regexiterator|register_shutdown_function|register_tick_function|rename|rename_function|require|require_once|reset|resetValue|resourcebundle|restore_error_handler|restore_exception_handler|restore_include_path|return|rewind|rewinddir|rmdir|round|rpm_close|rpm_get_tag|rpm_is_valid|rpm_open|rpm_version|rrd_create|rrd_error|rrd_fetch|rrd_first|rrd_graph|rrd_info|rrd_last|rrd_lastupdate|rrd_restore|rrd_tune|rrd_update|rrd_xport|rrdcreator|rrdgraph|rrdupdater|rsort|rtrim|runkit_class_adopt|runkit_class_emancipate|runkit_constant_add|runkit_constant_redefine|runkit_constant_remove|runkit_function_add|runkit_function_copy|runkit_function_redefine|runkit_function_remove|runkit_function_rename|runkit_import|runkit_lint|runkit_lint_file|runkit_method_add|runkit_method_copy|runkit_method_redefine|runkit_method_remove|runkit_method_rename|runkit_return_value_used|runkit_sandbox_output_handler|runkit_superglobals|runtimeexception|samconnection_commit|samconnection_connect|samconnection_constructor|samconnection_disconnect|samconnection_errno|samconnection_error|samconnection_isconnected|samconnection_peek|samconnection_peekall|samconnection_receive|samconnection_remove|samconnection_rollback|samconnection_send|samconnection_setDebug|samconnection_subscribe|samconnection_unsubscribe|sammessage_body|sammessage_constructor|sammessage_header|sca_createdataobject|sca_getservice|sca_localproxy_createdataobject|sca_soapproxy_createdataobject|scandir|sdo_das_changesummary_beginlogging|sdo_das_changesummary_endlogging|sdo_das_changesummary_getchangeddataobjects|sdo_das_changesummary_getchangetype|sdo_das_changesummary_getoldcontainer|sdo_das_changesummary_getoldvalues|sdo_das_changesummary_islogging|sdo_das_datafactory_addpropertytotype|sdo_das_datafactory_addtype|sdo_das_datafactory_getdatafactory|sdo_das_dataobject_getchangesummary|sdo_das_relational_applychanges|sdo_das_relational_construct|sdo_das_relational_createrootdataobject|sdo_das_relational_executepreparedquery|sdo_das_relational_executequery|sdo_das_setting_getlistindex|sdo_das_setting_getpropertyindex|sdo_das_setting_getpropertyname|sdo_das_setting_getvalue|sdo_das_setting_isset|sdo_das_xml_addtypes|sdo_das_xml_create|sdo_das_xml_createdataobject|sdo_das_xml_createdocument|sdo_das_xml_document_getrootdataobject|sdo_das_xml_document_getrootelementname|sdo_das_xml_document_getrootelementuri|sdo_das_xml_document_setencoding|sdo_das_xml_document_setxmldeclaration|sdo_das_xml_document_setxmlversion|sdo_das_xml_loadfile|sdo_das_xml_loadstring|sdo_das_xml_savefile|sdo_das_xml_savestring|sdo_datafactory_create|sdo_dataobject_clear|sdo_dataobject_createdataobject|sdo_dataobject_getcontainer|sdo_dataobject_getsequence|sdo_dataobject_gettypename|sdo_dataobject_gettypenamespaceuri|sdo_exception_getcause|sdo_list_insert|sdo_model_property_getcontainingtype|sdo_model_property_getdefault|sdo_model_property_getname|sdo_model_property_gettype|sdo_model_property_iscontainment|sdo_model_property_ismany|sdo_model_reflectiondataobject_construct|sdo_model_reflectiondataobject_export|sdo_model_reflectiondataobject_getcontainmentproperty|sdo_model_reflectiondataobject_getinstanceproperties|sdo_model_reflectiondataobject_gettype|sdo_model_type_getbasetype|sdo_model_type_getname|sdo_model_type_getnamespaceuri|sdo_model_type_getproperties|sdo_model_type_getproperty|sdo_model_type_isabstracttype|sdo_model_type_isdatatype|sdo_model_type_isinstance|sdo_model_type_isopentype|sdo_model_type_issequencedtype|sdo_sequence_getproperty|sdo_sequence_insert|sdo_sequence_move|seekableiterator|sem_acquire|sem_get|sem_release|sem_remove|serializable|serialize|session_cache_expire|session_cache_limiter|session_commit|session_decode|session_destroy|session_encode|session_get_cookie_params|session_id|session_is_registered|session_module_name|session_name|session_pgsql_add_error|session_pgsql_get_error|session_pgsql_get_field|session_pgsql_reset|session_pgsql_set_field|session_pgsql_status|session_regenerate_id|session_register|session_save_path|session_set_cookie_params|session_set_save_handler|session_start|session_unregister|session_unset|session_write_close|setCounterClass|set_error_handler|set_exception_handler|set_file_buffer|set_include_path|set_magic_quotes_runtime|set_socket_blocking|set_time_limit|setcookie|setlocale|setproctitle|setrawcookie|setstaticpropertyvalue|setthreadtitle|settype|sha1|sha1_file|shell_exec|shm_attach|shm_detach|shm_get_var|shm_has_var|shm_put_var|shm_remove|shm_remove_var|shmop_close|shmop_delete|shmop_open|shmop_read|shmop_size|shmop_write|show_source|shuffle|signeurlpaiement|similar_text|simplexml_import_dom|simplexml_load_file|simplexml_load_string|simplexmlelement|simplexmliterator|sin|sinh|sizeof|sleep|snmp|snmp2_get|snmp2_getnext|snmp2_real_walk|snmp2_set|snmp2_walk|snmp3_get|snmp3_getnext|snmp3_real_walk|snmp3_set|snmp3_walk|snmp_get_quick_print|snmp_get_valueretrieval|snmp_read_mib|snmp_set_enum_print|snmp_set_oid_numeric_print|snmp_set_oid_output_format|snmp_set_quick_print|snmp_set_valueretrieval|snmpget|snmpgetnext|snmprealwalk|snmpset|snmpwalk|snmpwalkoid|soapclient|soapfault|soapheader|soapparam|soapserver|soapvar|socket_accept|socket_bind|socket_clear_error|socket_close|socket_connect|socket_create|socket_create_listen|socket_create_pair|socket_get_option|socket_get_status|socket_getpeername|socket_getsockname|socket_last_error|socket_listen|socket_read|socket_recv|socket_recvfrom|socket_select|socket_send|socket_sendto|socket_set_block|socket_set_blocking|socket_set_nonblock|socket_set_option|socket_set_timeout|socket_shutdown|socket_strerror|socket_write|solr_get_version|solrclient|solrclientexception|solrdocument|solrdocumentfield|solrexception|solrgenericresponse|solrillegalargumentexception|solrillegaloperationexception|solrinputdocument|solrmodifiableparams|solrobject|solrparams|solrpingresponse|solrquery|solrqueryresponse|solrresponse|solrupdateresponse|solrutils|sort|soundex|sphinxclient|spl_autoload|spl_autoload_call|spl_autoload_extensions|spl_autoload_functions|spl_autoload_register|spl_autoload_unregister|spl_classes|spl_object_hash|splbool|spldoublylinkedlist|splenum|splfileinfo|splfileobject|splfixedarray|splfloat|splheap|splint|split|spliti|splmaxheap|splminheap|splobjectstorage|splobserver|splpriorityqueue|splqueue|splstack|splstring|splsubject|spltempfileobject|spoofchecker|sprintf|sql_regcase|sqlite3|sqlite3result|sqlite3stmt|sqlite_array_query|sqlite_busy_timeout|sqlite_changes|sqlite_close|sqlite_column|sqlite_create_aggregate|sqlite_create_function|sqlite_current|sqlite_error_string|sqlite_escape_string|sqlite_exec|sqlite_factory|sqlite_fetch_all|sqlite_fetch_array|sqlite_fetch_column_types|sqlite_fetch_object|sqlite_fetch_single|sqlite_fetch_string|sqlite_field_name|sqlite_has_more|sqlite_has_prev|sqlite_key|sqlite_last_error|sqlite_last_insert_rowid|sqlite_libencoding|sqlite_libversion|sqlite_next|sqlite_num_fields|sqlite_num_rows|sqlite_open|sqlite_popen|sqlite_prev|sqlite_query|sqlite_rewind|sqlite_seek|sqlite_single_query|sqlite_udf_decode_binary|sqlite_udf_encode_binary|sqlite_unbuffered_query|sqlite_valid|sqrt|srand|sscanf|ssdeep_fuzzy_compare|ssdeep_fuzzy_hash|ssdeep_fuzzy_hash_filename|ssh2_auth_hostbased_file|ssh2_auth_none|ssh2_auth_password|ssh2_auth_pubkey_file|ssh2_connect|ssh2_exec|ssh2_fetch_stream|ssh2_fingerprint|ssh2_methods_negotiated|ssh2_publickey_add|ssh2_publickey_init|ssh2_publickey_list|ssh2_publickey_remove|ssh2_scp_recv|ssh2_scp_send|ssh2_sftp|ssh2_sftp_lstat|ssh2_sftp_mkdir|ssh2_sftp_readlink|ssh2_sftp_realpath|ssh2_sftp_rename|ssh2_sftp_rmdir|ssh2_sftp_stat|ssh2_sftp_symlink|ssh2_sftp_unlink|ssh2_shell|ssh2_tunnel|stat|stats_absolute_deviation|stats_cdf_beta|stats_cdf_binomial|stats_cdf_cauchy|stats_cdf_chisquare|stats_cdf_exponential|stats_cdf_f|stats_cdf_gamma|stats_cdf_laplace|stats_cdf_logistic|stats_cdf_negative_binomial|stats_cdf_noncentral_chisquare|stats_cdf_noncentral_f|stats_cdf_poisson|stats_cdf_t|stats_cdf_uniform|stats_cdf_weibull|stats_covariance|stats_den_uniform|stats_dens_beta|stats_dens_cauchy|stats_dens_chisquare|stats_dens_exponential|stats_dens_f|stats_dens_gamma|stats_dens_laplace|stats_dens_logistic|stats_dens_negative_binomial|stats_dens_normal|stats_dens_pmf_binomial|stats_dens_pmf_hypergeometric|stats_dens_pmf_poisson|stats_dens_t|stats_dens_weibull|stats_harmonic_mean|stats_kurtosis|stats_rand_gen_beta|stats_rand_gen_chisquare|stats_rand_gen_exponential|stats_rand_gen_f|stats_rand_gen_funiform|stats_rand_gen_gamma|stats_rand_gen_ibinomial|stats_rand_gen_ibinomial_negative|stats_rand_gen_int|stats_rand_gen_ipoisson|stats_rand_gen_iuniform|stats_rand_gen_noncenral_chisquare|stats_rand_gen_noncentral_f|stats_rand_gen_noncentral_t|stats_rand_gen_normal|stats_rand_gen_t|stats_rand_get_seeds|stats_rand_phrase_to_seeds|stats_rand_ranf|stats_rand_setall|stats_skew|stats_standard_deviation|stats_stat_binomial_coef|stats_stat_correlation|stats_stat_gennch|stats_stat_independent_t|stats_stat_innerproduct|stats_stat_noncentral_t|stats_stat_paired_t|stats_stat_percentile|stats_stat_powersum|stats_variance|stomp|stomp_connect_error|stomp_version|stompexception|stompframe|str_getcsv|str_ireplace|str_pad|str_repeat|str_replace|str_rot13|str_shuffle|str_split|str_word_count|strcasecmp|strchr|strcmp|strcoll|strcspn|stream_bucket_append|stream_bucket_make_writeable|stream_bucket_new|stream_bucket_prepend|stream_context_create|stream_context_get_default|stream_context_get_options|stream_context_get_params|stream_context_set_default|stream_context_set_option|stream_context_set_params|stream_copy_to_stream|stream_encoding|stream_filter_append|stream_filter_prepend|stream_filter_register|stream_filter_remove|stream_get_contents|stream_get_filters|stream_get_line|stream_get_meta_data|stream_get_transports|stream_get_wrappers|stream_is_local|stream_notification_callback|stream_register_wrapper|stream_resolve_include_path|stream_select|stream_set_blocking|stream_set_read_buffer|stream_set_timeout|stream_set_write_buffer|stream_socket_accept|stream_socket_client|stream_socket_enable_crypto|stream_socket_get_name|stream_socket_pair|stream_socket_recvfrom|stream_socket_sendto|stream_socket_server|stream_socket_shutdown|stream_supports_lock|stream_wrapper_register|stream_wrapper_restore|stream_wrapper_unregister|streamwrapper|strftime|strip_tags|stripcslashes|stripos|stripslashes|stristr|strlen|strnatcasecmp|strnatcmp|strncasecmp|strncmp|strpbrk|strpos|strptime|strrchr|strrev|strripos|strrpos|strspn|strstr|strtok|strtolower|strtotime|strtoupper|strtr|strval|substr|substr_compare|substr_count|substr_replace|svm|svmmodel|svn_add|svn_auth_get_parameter|svn_auth_set_parameter|svn_blame|svn_cat|svn_checkout|svn_cleanup|svn_client_version|svn_commit|svn_delete|svn_diff|svn_export|svn_fs_abort_txn|svn_fs_apply_text|svn_fs_begin_txn2|svn_fs_change_node_prop|svn_fs_check_path|svn_fs_contents_changed|svn_fs_copy|svn_fs_delete|svn_fs_dir_entries|svn_fs_file_contents|svn_fs_file_length|svn_fs_is_dir|svn_fs_is_file|svn_fs_make_dir|svn_fs_make_file|svn_fs_node_created_rev|svn_fs_node_prop|svn_fs_props_changed|svn_fs_revision_prop|svn_fs_revision_root|svn_fs_txn_root|svn_fs_youngest_rev|svn_import|svn_log|svn_ls|svn_mkdir|svn_repos_create|svn_repos_fs|svn_repos_fs_begin_txn_for_commit|svn_repos_fs_commit_txn|svn_repos_hotcopy|svn_repos_open|svn_repos_recover|svn_revert|svn_status|svn_update|swf_actiongeturl|swf_actiongotoframe|swf_actiongotolabel|swf_actionnextframe|swf_actionplay|swf_actionprevframe|swf_actionsettarget|swf_actionstop|swf_actiontogglequality|swf_actionwaitforframe|swf_addbuttonrecord|swf_addcolor|swf_closefile|swf_definebitmap|swf_definefont|swf_defineline|swf_definepoly|swf_definerect|swf_definetext|swf_endbutton|swf_enddoaction|swf_endshape|swf_endsymbol|swf_fontsize|swf_fontslant|swf_fonttracking|swf_getbitmapinfo|swf_getfontinfo|swf_getframe|swf_labelframe|swf_lookat|swf_modifyobject|swf_mulcolor|swf_nextid|swf_oncondition|swf_openfile|swf_ortho|swf_ortho2|swf_perspective|swf_placeobject|swf_polarview|swf_popmatrix|swf_posround|swf_pushmatrix|swf_removeobject|swf_rotate|swf_scale|swf_setfont|swf_setframe|swf_shapearc|swf_shapecurveto|swf_shapecurveto3|swf_shapefillbitmapclip|swf_shapefillbitmaptile|swf_shapefilloff|swf_shapefillsolid|swf_shapelinesolid|swf_shapelineto|swf_shapemoveto|swf_showframe|swf_startbutton|swf_startdoaction|swf_startshape|swf_startsymbol|swf_textwidth|swf_translate|swf_viewport|swfaction|swfbitmap|swfbutton|swfdisplayitem|swffill|swffont|swffontchar|swfgradient|swfmorph|swfmovie|swfprebuiltclip|swfshape|swfsound|swfsoundinstance|swfsprite|swftext|swftextfield|swfvideostream|swish_construct|swish_getmetalist|swish_getpropertylist|swish_prepare|swish_query|swishresult_getmetalist|swishresult_stem|swishresults_getparsedwords|swishresults_getremovedstopwords|swishresults_nextresult|swishresults_seekresult|swishsearch_execute|swishsearch_resetlimit|swishsearch_setlimit|swishsearch_setphrasedelimiter|swishsearch_setsort|swishsearch_setstructure|sybase_affected_rows|sybase_close|sybase_connect|sybase_data_seek|sybase_deadlock_retry_count|sybase_fetch_array|sybase_fetch_assoc|sybase_fetch_field|sybase_fetch_object|sybase_fetch_row|sybase_field_seek|sybase_free_result|sybase_get_last_message|sybase_min_client_severity|sybase_min_error_severity|sybase_min_message_severity|sybase_min_server_severity|sybase_num_fields|sybase_num_rows|sybase_pconnect|sybase_query|sybase_result|sybase_select_db|sybase_set_message_handler|sybase_unbuffered_query|symlink|sys_get_temp_dir|sys_getloadavg|syslog|system|tag|tan|tanh|tcpwrap_check|tempnam|textdomain|tidy|tidy_access_count|tidy_config_count|tidy_diagnose|tidy_error_count|tidy_get_error_buffer|tidy_get_output|tidy_load_config|tidy_reset_config|tidy_save_config|tidy_set_encoding|tidy_setopt|tidy_warning_count|tidynode|time|time_nanosleep|time_sleep_until|timezone_abbreviations_list|timezone_identifiers_list|timezone_location_get|timezone_name_from_abbr|timezone_name_get|timezone_offset_get|timezone_open|timezone_transitions_get|timezone_version_get|tmpfile|token_get_all|token_name|tokyotyrant|tokyotyrantquery|tokyotyranttable|tostring|tostring|touch|trait_exists|transliterator|traversable|trigger_error|trim|uasort|ucfirst|ucwords|udm_add_search_limit|udm_alloc_agent|udm_alloc_agent_array|udm_api_version|udm_cat_list|udm_cat_path|udm_check_charset|udm_check_stored|udm_clear_search_limits|udm_close_stored|udm_crc32|udm_errno|udm_error|udm_find|udm_free_agent|udm_free_ispell_data|udm_free_res|udm_get_doc_count|udm_get_res_field|udm_get_res_param|udm_hash32|udm_load_ispell_data|udm_open_stored|udm_set_agent_param|uksort|umask|underflowexception|unexpectedvalueexception|uniqid|unixtojd|unlink|unpack|unregister_tick_function|unserialize|unset|urldecode|urlencode|use_soap_error_handler|user_error|usleep|usort|utf8_decode|utf8_encode|v8js|v8jsexception|var_dump|var_export|variant|variant_abs|variant_add|variant_and|variant_cast|variant_cat|variant_cmp|variant_date_from_timestamp|variant_date_to_timestamp|variant_div|variant_eqv|variant_fix|variant_get_type|variant_idiv|variant_imp|variant_int|variant_mod|variant_mul|variant_neg|variant_not|variant_or|variant_pow|variant_round|variant_set|variant_set_type|variant_sub|variant_xor|version_compare|vfprintf|virtual|vpopmail_add_alias_domain|vpopmail_add_alias_domain_ex|vpopmail_add_domain|vpopmail_add_domain_ex|vpopmail_add_user|vpopmail_alias_add|vpopmail_alias_del|vpopmail_alias_del_domain|vpopmail_alias_get|vpopmail_alias_get_all|vpopmail_auth_user|vpopmail_del_domain|vpopmail_del_domain_ex|vpopmail_del_user|vpopmail_error|vpopmail_passwd|vpopmail_set_user_quota|vprintf|vsprintf|w32api_deftype|w32api_init_dtype|w32api_invoke_function|w32api_register_function|w32api_set_call_method|wddx_add_vars|wddx_deserialize|wddx_packet_end|wddx_packet_start|wddx_serialize_value|wddx_serialize_vars|win32_continue_service|win32_create_service|win32_delete_service|win32_get_last_control_message|win32_pause_service|win32_ps_list_procs|win32_ps_stat_mem|win32_ps_stat_proc|win32_query_service_status|win32_set_service_status|win32_start_service|win32_start_service_ctrl_dispatcher|win32_stop_service|wincache_fcache_fileinfo|wincache_fcache_meminfo|wincache_lock|wincache_ocache_fileinfo|wincache_ocache_meminfo|wincache_refresh_if_changed|wincache_rplist_fileinfo|wincache_rplist_meminfo|wincache_scache_info|wincache_scache_meminfo|wincache_ucache_add|wincache_ucache_cas|wincache_ucache_clear|wincache_ucache_dec|wincache_ucache_delete|wincache_ucache_exists|wincache_ucache_get|wincache_ucache_inc|wincache_ucache_info|wincache_ucache_meminfo|wincache_ucache_set|wincache_unlock|wordwrap|xattr_get|xattr_list|xattr_remove|xattr_set|xattr_supported|xdiff_file_bdiff|xdiff_file_bdiff_size|xdiff_file_bpatch|xdiff_file_diff|xdiff_file_diff_binary|xdiff_file_merge3|xdiff_file_patch|xdiff_file_patch_binary|xdiff_file_rabdiff|xdiff_string_bdiff|xdiff_string_bdiff_size|xdiff_string_bpatch|xdiff_string_diff|xdiff_string_diff_binary|xdiff_string_merge3|xdiff_string_patch|xdiff_string_patch_binary|xdiff_string_rabdiff|xhprof_disable|xhprof_enable|xhprof_sample_disable|xhprof_sample_enable|xml_error_string|xml_get_current_byte_index|xml_get_current_column_number|xml_get_current_line_number|xml_get_error_code|xml_parse|xml_parse_into_struct|xml_parser_create|xml_parser_create_ns|xml_parser_free|xml_parser_get_option|xml_parser_set_option|xml_set_character_data_handler|xml_set_default_handler|xml_set_element_handler|xml_set_end_namespace_decl_handler|xml_set_external_entity_ref_handler|xml_set_notation_decl_handler|xml_set_object|xml_set_processing_instruction_handler|xml_set_start_namespace_decl_handler|xml_set_unparsed_entity_decl_handler|xmlreader|xmlrpc_decode|xmlrpc_decode_request|xmlrpc_encode|xmlrpc_encode_request|xmlrpc_get_type|xmlrpc_is_fault|xmlrpc_parse_method_descriptions|xmlrpc_server_add_introspection_data|xmlrpc_server_call_method|xmlrpc_server_create|xmlrpc_server_destroy|xmlrpc_server_register_introspection_callback|xmlrpc_server_register_method|xmlrpc_set_type|xmlwriter_end_attribute|xmlwriter_end_cdata|xmlwriter_end_comment|xmlwriter_end_document|xmlwriter_end_dtd|xmlwriter_end_dtd_attlist|xmlwriter_end_dtd_element|xmlwriter_end_dtd_entity|xmlwriter_end_element|xmlwriter_end_pi|xmlwriter_flush|xmlwriter_full_end_element|xmlwriter_open_memory|xmlwriter_open_uri|xmlwriter_output_memory|xmlwriter_set_indent|xmlwriter_set_indent_string|xmlwriter_start_attribute|xmlwriter_start_attribute_ns|xmlwriter_start_cdata|xmlwriter_start_comment|xmlwriter_start_document|xmlwriter_start_dtd|xmlwriter_start_dtd_attlist|xmlwriter_start_dtd_element|xmlwriter_start_dtd_entity|xmlwriter_start_element|xmlwriter_start_element_ns|xmlwriter_start_pi|xmlwriter_text|xmlwriter_write_attribute|xmlwriter_write_attribute_ns|xmlwriter_write_cdata|xmlwriter_write_comment|xmlwriter_write_dtd|xmlwriter_write_dtd_attlist|xmlwriter_write_dtd_element|xmlwriter_write_dtd_entity|xmlwriter_write_element|xmlwriter_write_element_ns|xmlwriter_write_pi|xmlwriter_write_raw|xpath_eval|xpath_eval_expression|xpath_new_context|xpath_register_ns|xpath_register_ns_auto|xptr_eval|xptr_new_context|xslt_backend_info|xslt_backend_name|xslt_backend_version|xslt_create|xslt_errno|xslt_error|xslt_free|xslt_getopt|xslt_process|xslt_set_base|xslt_set_encoding|xslt_set_error_handler|xslt_set_log|xslt_set_object|xslt_set_sax_handler|xslt_set_sax_handlers|xslt_set_scheme_handler|xslt_set_scheme_handlers|xslt_setopt|xsltprocessor|yaml_emit|yaml_emit_file|yaml_parse|yaml_parse_file|yaml_parse_url|yaz_addinfo|yaz_ccl_conf|yaz_ccl_parse|yaz_close|yaz_connect|yaz_database|yaz_element|yaz_errno|yaz_error|yaz_es|yaz_es_result|yaz_get_option|yaz_hits|yaz_itemorder|yaz_present|yaz_range|yaz_record|yaz_scan|yaz_scan_result|yaz_schema|yaz_search|yaz_set_option|yaz_sort|yaz_syntax|yaz_wait|yp_all|yp_cat|yp_err_string|yp_errno|yp_first|yp_get_default_domain|yp_master|yp_match|yp_next|yp_order|zend_logo_guid|zend_thread_id|zend_version|zip_close|zip_entry_close|zip_entry_compressedsize|zip_entry_compressionmethod|zip_entry_filesize|zip_entry_name|zip_entry_open|zip_entry_read|zip_open|zip_read|ziparchive|ziparchive_addemptydir|ziparchive_addfile|ziparchive_addfromstring|ziparchive_close|ziparchive_deleteindex|ziparchive_deletename|ziparchive_extractto|ziparchive_getarchivecomment|ziparchive_getcommentindex|ziparchive_getcommentname|ziparchive_getfromindex|ziparchive_getfromname|ziparchive_getnameindex|ziparchive_getstatusstring|ziparchive_getstream|ziparchive_locatename|ziparchive_open|ziparchive_renameindex|ziparchive_renamename|ziparchive_setCommentName|ziparchive_setarchivecomment|ziparchive_setcommentindex|ziparchive_statindex|ziparchive_statname|ziparchive_unchangeall|ziparchive_unchangearchive|ziparchive_unchangeindex|ziparchive_unchangename|zlib_get_coding_type\".split(\"|\")),n=i.arrayToMap(\"abstract|and|array|as|break|case|catch|class|clone|const|continue|declare|default|do|else|elseif|enddeclare|endfor|endforeach|endif|endswitch|endwhile|extends|final|for|foreach|function|global|goto|if|implements|interface|instanceof|namespace|new|or|private|protected|public|static|switch|throw|trait|try|use|var|while|xor\".split(\"|\")),r=i.arrayToMap(\"die|echo|empty|exit|eval|include|include_once|isset|list|require|require_once|return|print|unset\".split(\"|\")),o=i.arrayToMap(\"true|TRUE|false|FALSE|null|NULL|__CLASS__|__DIR__|__FILE__|__LINE__|__METHOD__|__FUNCTION__|__NAMESPACE__\".split(\"|\")),u=i.arrayToMap(\"$GLOBALS|$_SERVER|$_GET|$_POST|$_FILES|$_REQUEST|$_SESSION|$_ENV|$_COOKIE|$php_errormsg|$HTTP_RAW_POST_DATA|$http_response_header|$argc|$argv\".split(\"|\")),a=i.arrayToMap(\"key_exists|cairo_matrix_create_scale|cairo_matrix_create_translate|call_user_method|call_user_method_array|com_addref|com_get|com_invoke|com_isenum|com_load|com_release|com_set|connection_timeout|cubrid_load_from_glo|cubrid_new_glo|cubrid_save_to_glo|cubrid_send_glo|define_syslog_variables|dl|ereg|ereg_replace|eregi|eregi_replace|hw_documentattributes|hw_documentbodytag|hw_documentsize|hw_outputdocument|imagedashedline|maxdb_bind_param|maxdb_bind_result|maxdb_client_encoding|maxdb_close_long_data|maxdb_execute|maxdb_fetch|maxdb_get_metadata|maxdb_param_count|maxdb_send_long_data|mcrypt_ecb|mcrypt_generic_end|mime_content_type|mysql_createdb|mysql_dbname|mysql_db_query|mysql_drop_db|mysql_dropdb|mysql_escape_string|mysql_fieldflags|mysql_fieldflags|mysql_fieldname|mysql_fieldtable|mysql_fieldtype|mysql_freeresult|mysql_listdbs|mysql_list_fields|mysql_listfields|mysql_list_tables|mysql_listtables|mysql_numfields|mysql_numrows|mysql_selectdb|mysql_tablename|mysqli_bind_param|mysqli_bind_result|mysqli_disable_reads_from_master|mysqli_disable_rpl_parse|mysqli_enable_reads_from_master|mysqli_enable_rpl_parse|mysqli_execute|mysqli_fetch|mysqli_get_metadata|mysqli_master_query|mysqli_param_count|mysqli_rpl_parse_enabled|mysqli_rpl_probe|mysqli_rpl_query_type|mysqli_send_long_data|mysqli_send_query|mysqli_slave_query|ocibindbyname|ocicancel|ocicloselob|ocicollappend|ocicollassign|ocicollassignelem|ocicollgetelem|ocicollmax|ocicollsize|ocicolltrim|ocicolumnisnull|ocicolumnname|ocicolumnprecision|ocicolumnscale|ocicolumnsize|ocicolumntype|ocicolumntyperaw|ocicommit|ocidefinebyname|ocierror|ociexecute|ocifetch|ocifetchinto|ocifetchstatement|ocifreecollection|ocifreecursor|ocifreedesc|ocifreestatement|ociinternaldebug|ociloadlob|ocilogoff|ocilogon|ocinewcollection|ocinewcursor|ocinewdescriptor|ocinlogon|ocinumcols|ociparse|ociplogon|ociresult|ocirollback|ocirowcount|ocisavelob|ocisavelobfile|ociserverversion|ocisetprefetch|ocistatementtype|ociwritelobtofile|ociwritetemporarylob|PDF_add_annotation|PDF_add_bookmark|PDF_add_launchlink|PDF_add_locallink|PDF_add_note|PDF_add_outline|PDF_add_pdflink|PDF_add_weblink|PDF_attach_file|PDF_begin_page|PDF_begin_template|PDF_close_pdi|PDF_close|PDF_findfont|PDF_get_font|PDF_get_fontname|PDF_get_fontsize|PDF_get_image_height|PDF_get_image_width|PDF_get_majorversion|PDF_get_minorversion|PDF_get_pdi_parameter|PDF_get_pdi_value|PDF_open_ccitt|PDF_open_file|PDF_open_gif|PDF_open_image_file|PDF_open_image|PDF_open_jpeg|PDF_open_pdi|PDF_open_tiff|PDF_place_image|PDF_place_pdi_page|PDF_set_border_color|PDF_set_border_dash|PDF_set_border_style|PDF_set_char_spacing|PDF_set_duration|PDF_set_horiz_scaling|PDF_set_info_author|PDF_set_info_creator|PDF_set_info_keywords|PDF_set_info_subject|PDF_set_info_title|PDF_set_leading|PDF_set_text_matrix|PDF_set_text_rendering|PDF_set_text_rise|PDF_set_word_spacing|PDF_setgray_fill|PDF_setgray_stroke|PDF_setgray|PDF_setpolydash|PDF_setrgbcolor_fill|PDF_setrgbcolor_stroke|PDF_setrgbcolor|PDF_show_boxed|php_check_syntax|px_set_tablename|px_set_targetencoding|runkit_sandbox_output_handler|session_is_registered|session_register|session_unregisterset_magic_quotes_runtime|magic_quotes_runtime|set_socket_blocking|socket_set_blocking|set_socket_timeout|socket_set_timeout|split|spliti|sql_regcase\".split(\"|\")),f=i.arrayToMap(\"cfunction|old_function\".split(\"|\")),l=i.arrayToMap([]);this.$rules={start:[{token:\"comment\",regex:/(?:#|\\/\\/)(?:[^?]|\\?[^>])*/},e.getStartRule(\"doc-start\"),{token:\"comment\",regex:\"\\\\/\\\\*\",next:\"comment\"},{token:\"string.regexp\",regex:\"[/](?:(?:\\\\[(?:\\\\\\\\]|[^\\\\]])+\\\\])|(?:\\\\\\\\/|[^\\\\]/]))*[/][gimy]*\\\\s*(?=[).,;]|$)\"},{token:\"string\",regex:'\"',next:\"qqstring\"},{token:\"string\",regex:\"'\",next:\"qstring\"},{token:\"constant.numeric\",regex:\"0[xX][0-9a-fA-F]+\\\\b\"},{token:\"constant.numeric\",regex:\"[+-]?\\\\d+(?:(?:\\\\.\\\\d*)?(?:[eE][+-]?\\\\d+)?)?\\\\b\"},{token:\"constant.language\",regex:\"\\\\b(?:DEFAULT_INCLUDE_PATH|E_(?:ALL|CO(?:MPILE_(?:ERROR|WARNING)|RE_(?:ERROR|WARNING))|ERROR|NOTICE|PARSE|STRICT|USER_(?:ERROR|NOTICE|WARNING)|WARNING)|P(?:EAR_(?:EXTENSION_DIR|INSTALL_DIR)|HP_(?:BINDIR|CONFIG_FILE_(?:PATH|SCAN_DIR)|DATADIR|E(?:OL|XTENSION_DIR)|INT_(?:MAX|SIZE)|L(?:IBDIR|OCALSTATEDIR)|O(?:S|UTPUT_HANDLER_(?:CONT|END|START))|PREFIX|S(?:API|HLIB_SUFFIX|YSCONFDIR)|VERSION))|__COMPILER_HALT_OFFSET__)\\\\b\"},{token:[\"keyword\",\"text\",\"support.class\"],regex:\"\\\\b(new)(\\\\s+)(\\\\w+)\"},{token:[\"support.class\",\"keyword.operator\"],regex:\"\\\\b(\\\\w+)(::)\"},{token:\"constant.language\",regex:\"\\\\b(?:A(?:B(?:DAY_(?:1|2|3|4|5|6|7)|MON_(?:1(?:0|1|2|)|2|3|4|5|6|7|8|9))|LT_DIGITS|M_STR|SSERT_(?:ACTIVE|BAIL|CALLBACK|QUIET_EVAL|WARNING))|C(?:ASE_(?:LOWER|UPPER)|HAR_MAX|O(?:DESET|NNECTION_(?:ABORTED|NORMAL|TIMEOUT)|UNT_(?:NORMAL|RECURSIVE))|R(?:EDITS_(?:ALL|DOCS|FULLPAGE|G(?:ENERAL|ROUP)|MODULES|QA|SAPI)|NCYSTR|YPT_(?:BLOWFISH|EXT_DES|MD5|S(?:ALT_LENGTH|TD_DES)))|URRENCY_SYMBOL)|D(?:AY_(?:1|2|3|4|5|6|7)|ECIMAL_POINT|IRECTORY_SEPARATOR|_(?:FMT|T_FMT))|E(?:NT_(?:COMPAT|NOQUOTES|QUOTES)|RA(?:_(?:D_(?:FMT|T_FMT)|T_FMT|YEAR)|)|XTR_(?:IF_EXISTS|OVERWRITE|PREFIX_(?:ALL|I(?:F_EXISTS|NVALID)|SAME)|SKIP))|FRAC_DIGITS|GROUPING|HTML_(?:ENTITIES|SPECIALCHARS)|IN(?:FO_(?:ALL|C(?:ONFIGURATION|REDITS)|ENVIRONMENT|GENERAL|LICENSE|MODULES|VARIABLES)|I_(?:ALL|PERDIR|SYSTEM|USER)|T_(?:CURR_SYMBOL|FRAC_DIGITS))|L(?:C_(?:ALL|C(?:OLLATE|TYPE)|M(?:ESSAGES|ONETARY)|NUMERIC|TIME)|O(?:CK_(?:EX|NB|SH|UN)|G_(?:A(?:LERT|UTH(?:PRIV|))|C(?:ONS|R(?:IT|ON))|D(?:AEMON|EBUG)|E(?:MERG|RR)|INFO|KERN|L(?:OCAL(?:0|1|2|3|4|5|6|7)|PR)|MAIL|N(?:DELAY|EWS|O(?:TICE|WAIT))|ODELAY|P(?:ERROR|ID)|SYSLOG|U(?:SER|UCP)|WARNING)))|M(?:ON_(?:1(?:0|1|2|)|2|3|4|5|6|7|8|9|DECIMAL_POINT|GROUPING|THOUSANDS_SEP)|_(?:1_PI|2_(?:PI|SQRTPI)|E|L(?:N(?:10|2)|OG(?:10E|2E))|PI(?:_(?:2|4)|)|SQRT(?:1_2|2)))|N(?:EGATIVE_SIGN|O(?:EXPR|STR)|_(?:CS_PRECEDES|S(?:EP_BY_SPACE|IGN_POSN)))|P(?:ATH(?:INFO_(?:BASENAME|DIRNAME|EXTENSION)|_SEPARATOR)|M_STR|OSITIVE_SIGN|_(?:CS_PRECEDES|S(?:EP_BY_SPACE|IGN_POSN)))|RADIXCHAR|S(?:EEK_(?:CUR|END|SET)|ORT_(?:ASC|DESC|NUMERIC|REGULAR|STRING)|TR_PAD_(?:BOTH|LEFT|RIGHT))|T(?:HOUS(?:ANDS_SEP|EP)|_FMT(?:_AMPM|))|YES(?:EXPR|STR)|STD(?:IN|OUT|ERR))\\\\b\"},{token:function(e){return n.hasOwnProperty(e)?\"keyword\":o.hasOwnProperty(e)?\"constant.language\":u.hasOwnProperty(e)?\"variable.language\":l.hasOwnProperty(e)?\"invalid.illegal\":t.hasOwnProperty(e)?\"support.function\":e==\"debugger\"?\"invalid.deprecated\":e.match(/^(\\$[a-zA-Z_\\x7f-\\uffff][a-zA-Z0-9_\\x7f-\\uffff]*|self|parent)$/)?\"variable\":\"identifier\"},regex:/[a-zA-Z_$\\x7f-\\uffff][a-zA-Z0-9_\\x7f-\\uffff]*/},{onMatch:function(e,t,n){e=e.substr(3);if(e[0]==\"'\"||e[0]=='\"')e=e.slice(1,-1);return n.unshift(this.next,e),\"markup.list\"},regex:/<<<(?:\\w+|'\\w+'|\"\\w+\")$/,next:\"heredoc\"},{token:\"keyword.operator\",regex:\"::|!|\\\\$|%|&|\\\\*|\\\\-\\\\-|\\\\-|\\\\+\\\\+|\\\\+|~|===|==|!=|!==|<=|>=|=>|<<=|>>=|>>>=|<>|<|>|=|!|&&|\\\\|\\\\||\\\\?\\\\:|\\\\*=|%=|\\\\+=|\\\\-=|&=|\\\\^=|\\\\b(?:in|instanceof|new|delete|typeof|void)\"},{token:\"paren.lparen\",regex:\"[[({]\"},{token:\"paren.rparen\",regex:\"[\\\\])}]\"},{token:\"text\",regex:\"\\\\s+\"}],heredoc:[{onMatch:function(e,t,n){return n[1]!=e?\"string\":(n.shift(),n.shift(),\"markup.list\")},regex:\"^\\\\w+(?=;?$)\",next:\"start\"},{token:\"string\",regex:\".*\"}],comment:[{token:\"comment\",regex:\"\\\\*\\\\/\",next:\"start\"},{defaultToken:\"comment\"}],qqstring:[{token:\"constant.language.escape\",regex:'\\\\\\\\(?:[nrtvef\\\\\\\\\"$]|[0-7]{1,3}|x[0-9A-Fa-f]{1,2})'},{token:\"variable\",regex:/\\$[\\w]+(?:\\[[\\w\\]+]|[=\\-]>\\w+)?/},{token:\"variable\",regex:/\\$\\{[^\"\\}]+\\}?/},{token:\"string\",regex:'\"',next:\"start\"},{defaultToken:\"string\"}],qstring:[{token:\"constant.language.escape\",regex:/\\\\['\\\\]/},{token:\"string\",regex:\"'\",next:\"start\"},{defaultToken:\"string\"}]},this.embedRules(s,\"doc-\",[s.getEndRule(\"start\")])};r.inherits(a,o);var f=function(){u.call(this);var e=[{token:\"support.php_tag\",regex:\"<\\\\?(?:php|=)?\",push:\"php-start\"}],t=[{token:\"support.php_tag\",regex:\"\\\\?>\",next:\"pop\"}];for(var n in this.$rules)this.$rules[n].unshift.apply(this.$rules[n],e);this.embedRules(a,\"php-\",t,[\"start\"]),this.normalizeRules()};r.inherits(f,u),t.PhpHighlightRules=f,t.PhpLangHighlightRules=a}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/php_completions\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function s(e,t){return e.type.lastIndexOf(t)>-1}var r={abs:[\"int abs(int number)\",\"Return the absolute value of the number\"],acos:[\"float acos(float number)\",\"Return the arc cosine of the number in radians\"],acosh:[\"float acosh(float number)\",\"Returns the inverse hyperbolic cosine of the number, i.e. the value whose hyperbolic cosine is number\"],addGlob:[\"bool addGlob(string pattern[,int flags [, array options]])\",\"Add files matching the glob pattern. See php's glob for the pattern syntax.\"],addPattern:[\"bool addPattern(string pattern[, string path [, array options]])\",\"Add files matching the pcre pattern. See php's pcre for the pattern syntax.\"],addcslashes:[\"string addcslashes(string str, string charlist)\",\"Escapes all chars mentioned in charlist with backslash. It creates octal representations if asked to backslash characters with 8th bit set or with ASCII<32 (except '\\\\n', '\\\\r', '\\\\t' etc...)\"],addslashes:[\"string addslashes(string str)\",\"Escapes single quote, double quotes and backslash characters in a string with backslashes\"],apache_child_terminate:[\"bool apache_child_terminate(void)\",\"Terminate apache process after this request\"],apache_get_modules:[\"array apache_get_modules(void)\",\"Get a list of loaded Apache modules\"],apache_get_version:[\"string apache_get_version(void)\",\"Fetch Apache version\"],apache_getenv:[\"bool apache_getenv(string variable [, bool walk_to_top])\",\"Get an Apache subprocess_env variable\"],apache_lookup_uri:[\"object apache_lookup_uri(string URI)\",\"Perform a partial request of the given URI to obtain information about it\"],apache_note:[\"string apache_note(string note_name [, string note_value])\",\"Get and set Apache request notes\"],apache_request_auth_name:[\"string apache_request_auth_name()\",\"\"],apache_request_auth_type:[\"string apache_request_auth_type()\",\"\"],apache_request_discard_request_body:[\"long apache_request_discard_request_body()\",\"\"],apache_request_err_headers_out:[\"array apache_request_err_headers_out([{string name|array list} [, string value [, bool replace = false]]])\",\"* fetch all headers that go out in case of an error or a subrequest\"],apache_request_headers:[\"array apache_request_headers(void)\",\"Fetch all HTTP request headers\"],apache_request_headers_in:[\"array apache_request_headers_in()\",\"* fetch all incoming request headers\"],apache_request_headers_out:[\"array apache_request_headers_out([{string name|array list} [, string value [, bool replace = false]]])\",\"* fetch all outgoing request headers\"],apache_request_is_initial_req:[\"bool apache_request_is_initial_req()\",\"\"],apache_request_log_error:[\"boolean apache_request_log_error(string message, [long facility])\",\"\"],apache_request_meets_conditions:[\"long apache_request_meets_conditions()\",\"\"],apache_request_remote_host:[\"int apache_request_remote_host([int type])\",\"\"],apache_request_run:[\"long apache_request_run()\",\"This is a wrapper for ap_sub_run_req and ap_destory_sub_req.  It takes      sub_request, runs it, destroys it, and returns it's status.\"],apache_request_satisfies:[\"long apache_request_satisfies()\",\"\"],apache_request_server_port:[\"int apache_request_server_port()\",\"\"],apache_request_set_etag:[\"void apache_request_set_etag()\",\"\"],apache_request_set_last_modified:[\"void apache_request_set_last_modified()\",\"\"],apache_request_some_auth_required:[\"bool apache_request_some_auth_required()\",\"\"],apache_request_sub_req_lookup_file:[\"object apache_request_sub_req_lookup_file(string file)\",\"Returns sub-request for the specified file.  You would     need to run it yourself with run().\"],apache_request_sub_req_lookup_uri:[\"object apache_request_sub_req_lookup_uri(string uri)\",\"Returns sub-request for the specified uri.  You would     need to run it yourself with run()\"],apache_request_sub_req_method_uri:[\"object apache_request_sub_req_method_uri(string method, string uri)\",\"Returns sub-request for the specified file.  You would     need to run it yourself with run().\"],apache_request_update_mtime:[\"long apache_request_update_mtime([int dependency_mtime])\",\"\"],apache_reset_timeout:[\"bool apache_reset_timeout(void)\",\"Reset the Apache write timer\"],apache_response_headers:[\"array apache_response_headers(void)\",\"Fetch all HTTP response headers\"],apache_setenv:[\"bool apache_setenv(string variable, string value [, bool walk_to_top])\",\"Set an Apache subprocess_env variable\"],array_change_key_case:[\"array array_change_key_case(array input [, int case=CASE_LOWER])\",\"Retuns an array with all string keys lowercased [or uppercased]\"],array_chunk:[\"array array_chunk(array input, int size [, bool preserve_keys])\",\"Split array into chunks\"],array_combine:[\"array array_combine(array keys, array values)\",\"Creates an array by using the elements of the first parameter as keys and the elements of the second as the corresponding values\"],array_count_values:[\"array array_count_values(array input)\",\"Return the value as key and the frequency of that value in input as value\"],array_diff:[\"array array_diff(array arr1, array arr2 [, array ...])\",\"Returns the entries of arr1 that have values which are not present in any of the others arguments.\"],array_diff_assoc:[\"array array_diff_assoc(array arr1, array arr2 [, array ...])\",\"Returns the entries of arr1 that have values which are not present in any of the others arguments but do additional checks whether the keys are equal\"],array_diff_key:[\"array array_diff_key(array arr1, array arr2 [, array ...])\",\"Returns the entries of arr1 that have keys which are not present in any of the others arguments. This function is like array_diff() but works on the keys instead of the values. The associativity is preserved.\"],array_diff_uassoc:[\"array array_diff_uassoc(array arr1, array arr2 [, array ...], callback data_comp_func)\",\"Returns the entries of arr1 that have values which are not present in any of the others arguments but do additional checks whether the keys are equal. Elements are compared by user supplied function.\"],array_diff_ukey:[\"array array_diff_ukey(array arr1, array arr2 [, array ...], callback key_comp_func)\",\"Returns the entries of arr1 that have keys which are not present in any of the others arguments. User supplied function is used for comparing the keys. This function is like array_udiff() but works on the keys instead of the values. The associativity is preserved.\"],array_fill:[\"array array_fill(int start_key, int num, mixed val)\",\"Create an array containing num elements starting with index start_key each initialized to val\"],array_fill_keys:[\"array array_fill_keys(array keys, mixed val)\",\"Create an array using the elements of the first parameter as keys each initialized to val\"],array_filter:[\"array array_filter(array input [, mixed callback])\",\"Filters elements from the array via the callback.\"],array_flip:[\"array array_flip(array input)\",\"Return array with key <-> value flipped\"],array_intersect:[\"array array_intersect(array arr1, array arr2 [, array ...])\",\"Returns the entries of arr1 that have values which are present in all the other arguments\"],array_intersect_assoc:[\"array array_intersect_assoc(array arr1, array arr2 [, array ...])\",\"Returns the entries of arr1 that have values which are present in all the other arguments. Keys are used to do more restrictive check\"],array_intersect_key:[\"array array_intersect_key(array arr1, array arr2 [, array ...])\",\"Returns the entries of arr1 that have keys which are present in all the other arguments. Kind of equivalent to array_diff(array_keys($arr1), array_keys($arr2)[,array_keys(...)]). Equivalent of array_intersect_assoc() but does not do compare of the data.\"],array_intersect_uassoc:[\"array array_intersect_uassoc(array arr1, array arr2 [, array ...], callback key_compare_func)\",\"Returns the entries of arr1 that have values which are present in all the other arguments. Keys are used to do more restrictive check and they are compared by using an user-supplied callback.\"],array_intersect_ukey:[\"array array_intersect_ukey(array arr1, array arr2 [, array ...], callback key_compare_func)\",\"Returns the entries of arr1 that have keys which are present in all the other arguments. Kind of equivalent to array_diff(array_keys($arr1), array_keys($arr2)[,array_keys(...)]). The comparison of the keys is performed by a user supplied function. Equivalent of array_intersect_uassoc() but does not do compare of the data.\"],array_key_exists:[\"bool array_key_exists(mixed key, array search)\",\"Checks if the given key or index exists in the array\"],array_keys:[\"array array_keys(array input [, mixed search_value[, bool strict]])\",\"Return just the keys from the input array, optionally only for the specified search_value\"],array_map:[\"array array_map(mixed callback, array input1 [, array input2 ,...])\",\"Applies the callback to the elements in given arrays.\"],array_merge:[\"array array_merge(array arr1, array arr2 [, array ...])\",\"Merges elements from passed arrays into one array\"],array_merge_recursive:[\"array array_merge_recursive(array arr1, array arr2 [, array ...])\",\"Recursively merges elements from passed arrays into one array\"],array_multisort:[\"bool array_multisort(array ar1 [, SORT_ASC|SORT_DESC [, SORT_REGULAR|SORT_NUMERIC|SORT_STRING]] [, array ar2 [, SORT_ASC|SORT_DESC [, SORT_REGULAR|SORT_NUMERIC|SORT_STRING]], ...])\",\"Sort multiple arrays at once similar to how ORDER BY clause works in SQL\"],array_pad:[\"array array_pad(array input, int pad_size, mixed pad_value)\",\"Returns a copy of input array padded with pad_value to size pad_size\"],array_pop:[\"mixed array_pop(array stack)\",\"Pops an element off the end of the array\"],array_product:[\"mixed array_product(array input)\",\"Returns the product of the array entries\"],array_push:[\"int array_push(array stack, mixed var [, mixed ...])\",\"Pushes elements onto the end of the array\"],array_rand:[\"mixed array_rand(array input [, int num_req])\",\"Return key/keys for random entry/entries in the array\"],array_reduce:[\"mixed array_reduce(array input, mixed callback [, mixed initial])\",\"Iteratively reduce the array to a single value via the callback.\"],array_replace:[\"array array_replace(array arr1, array arr2 [, array ...])\",\"Replaces elements from passed arrays into one array\"],array_replace_recursive:[\"array array_replace_recursive(array arr1, array arr2 [, array ...])\",\"Recursively replaces elements from passed arrays into one array\"],array_reverse:[\"array array_reverse(array input [, bool preserve keys])\",\"Return input as a new array with the order of the entries reversed\"],array_search:[\"mixed array_search(mixed needle, array haystack [, bool strict])\",\"Searches the array for a given value and returns the corresponding key if successful\"],array_shift:[\"mixed array_shift(array stack)\",\"Pops an element off the beginning of the array\"],array_slice:[\"array array_slice(array input, int offset [, int length [, bool preserve_keys]])\",\"Returns elements specified by offset and length\"],array_splice:[\"array array_splice(array input, int offset [, int length [, array replacement]])\",\"Removes the elements designated by offset and length and replace them with supplied array\"],array_sum:[\"mixed array_sum(array input)\",\"Returns the sum of the array entries\"],array_udiff:[\"array array_udiff(array arr1, array arr2 [, array ...], callback data_comp_func)\",\"Returns the entries of arr1 that have values which are not present in any of the others arguments. Elements are compared by user supplied function.\"],array_udiff_assoc:[\"array array_udiff_assoc(array arr1, array arr2 [, array ...], callback key_comp_func)\",\"Returns the entries of arr1 that have values which are not present in any of the others arguments but do additional checks whether the keys are equal. Keys are compared by user supplied function.\"],array_udiff_uassoc:[\"array array_udiff_uassoc(array arr1, array arr2 [, array ...], callback data_comp_func, callback key_comp_func)\",\"Returns the entries of arr1 that have values which are not present in any of the others arguments but do additional checks whether the keys are equal. Keys and elements are compared by user supplied functions.\"],array_uintersect:[\"array array_uintersect(array arr1, array arr2 [, array ...], callback data_compare_func)\",\"Returns the entries of arr1 that have values which are present in all the other arguments. Data is compared by using an user-supplied callback.\"],array_uintersect_assoc:[\"array array_uintersect_assoc(array arr1, array arr2 [, array ...], callback data_compare_func)\",\"Returns the entries of arr1 that have values which are present in all the other arguments. Keys are used to do more restrictive check. Data is compared by using an user-supplied callback.\"],array_uintersect_uassoc:[\"array array_uintersect_uassoc(array arr1, array arr2 [, array ...], callback data_compare_func, callback key_compare_func)\",\"Returns the entries of arr1 that have values which are present in all the other arguments. Keys are used to do more restrictive check. Both data and keys are compared by using user-supplied callbacks.\"],array_unique:[\"array array_unique(array input [, int sort_flags])\",\"Removes duplicate values from array\"],array_unshift:[\"int array_unshift(array stack, mixed var [, mixed ...])\",\"Pushes elements onto the beginning of the array\"],array_values:[\"array array_values(array input)\",\"Return just the values from the input array\"],array_walk:[\"bool array_walk(array input, string funcname [, mixed userdata])\",\"Apply a user function to every member of an array\"],array_walk_recursive:[\"bool array_walk_recursive(array input, string funcname [, mixed userdata])\",\"Apply a user function recursively to every member of an array\"],arsort:[\"bool arsort(array &array_arg [, int sort_flags])\",\"Sort an array in reverse order and maintain index association\"],asin:[\"float asin(float number)\",\"Returns the arc sine of the number in radians\"],asinh:[\"float asinh(float number)\",\"Returns the inverse hyperbolic sine of the number, i.e. the value whose hyperbolic sine is number\"],asort:[\"bool asort(array &array_arg [, int sort_flags])\",\"Sort an array and maintain index association\"],assert:[\"int assert(string|bool assertion)\",\"Checks if assertion is false\"],assert_options:[\"mixed assert_options(int what [, mixed value])\",\"Set/get the various assert flags\"],atan:[\"float atan(float number)\",\"Returns the arc tangent of the number in radians\"],atan2:[\"float atan2(float y, float x)\",\"Returns the arc tangent of y/x, with the resulting quadrant determined by the signs of y and x\"],atanh:[\"float atanh(float number)\",\"Returns the inverse hyperbolic tangent of the number, i.e. the value whose hyperbolic tangent is number\"],attachIterator:[\"void attachIterator(Iterator iterator[, mixed info])\",\"Attach a new iterator\"],base64_decode:[\"string base64_decode(string str[, bool strict])\",\"Decodes string using MIME base64 algorithm\"],base64_encode:[\"string base64_encode(string str)\",\"Encodes string using MIME base64 algorithm\"],base_convert:[\"string base_convert(string number, int frombase, int tobase)\",\"Converts a number in a string from any base <= 36 to any base <= 36\"],basename:[\"string basename(string path [, string suffix])\",\"Returns the filename component of the path\"],bcadd:[\"string bcadd(string left_operand, string right_operand [, int scale])\",\"Returns the sum of two arbitrary precision numbers\"],bccomp:[\"int bccomp(string left_operand, string right_operand [, int scale])\",\"Compares two arbitrary precision numbers\"],bcdiv:[\"string bcdiv(string left_operand, string right_operand [, int scale])\",\"Returns the quotient of two arbitrary precision numbers (division)\"],bcmod:[\"string bcmod(string left_operand, string right_operand)\",\"Returns the modulus of the two arbitrary precision operands\"],bcmul:[\"string bcmul(string left_operand, string right_operand [, int scale])\",\"Returns the multiplication of two arbitrary precision numbers\"],bcpow:[\"string bcpow(string x, string y [, int scale])\",\"Returns the value of an arbitrary precision number raised to the power of another\"],bcpowmod:[\"string bcpowmod(string x, string y, string mod [, int scale])\",\"Returns the value of an arbitrary precision number raised to the power of another reduced by a modulous\"],bcscale:[\"bool bcscale(int scale)\",\"Sets default scale parameter for all bc math functions\"],bcsqrt:[\"string bcsqrt(string operand [, int scale])\",\"Returns the square root of an arbitray precision number\"],bcsub:[\"string bcsub(string left_operand, string right_operand [, int scale])\",\"Returns the difference between two arbitrary precision numbers\"],bin2hex:[\"string bin2hex(string data)\",\"Converts the binary representation of data to hex\"],bind_textdomain_codeset:[\"string bind_textdomain_codeset (string domain, string codeset)\",\"Specify the character encoding in which the messages from the DOMAIN message catalog will be returned.\"],bindec:[\"int bindec(string binary_number)\",\"Returns the decimal equivalent of the binary number\"],bindtextdomain:[\"string bindtextdomain(string domain_name, string dir)\",\"Bind to the text domain domain_name, looking for translations in dir. Returns the current domain\"],birdstep_autocommit:[\"bool birdstep_autocommit(int index)\",\"\"],birdstep_close:[\"bool birdstep_close(int id)\",\"\"],birdstep_commit:[\"bool birdstep_commit(int index)\",\"\"],birdstep_connect:[\"int birdstep_connect(string server, string user, string pass)\",\"\"],birdstep_exec:[\"int birdstep_exec(int index, string exec_str)\",\"\"],birdstep_fetch:[\"bool birdstep_fetch(int index)\",\"\"],birdstep_fieldname:[\"string birdstep_fieldname(int index, int col)\",\"\"],birdstep_fieldnum:[\"int birdstep_fieldnum(int index)\",\"\"],birdstep_freeresult:[\"bool birdstep_freeresult(int index)\",\"\"],birdstep_off_autocommit:[\"bool birdstep_off_autocommit(int index)\",\"\"],birdstep_result:[\"mixed birdstep_result(int index, mixed col)\",\"\"],birdstep_rollback:[\"bool birdstep_rollback(int index)\",\"\"],bzcompress:[\"string bzcompress(string source [, int blocksize100k [, int workfactor]])\",\"Compresses a string into BZip2 encoded data\"],bzdecompress:[\"string bzdecompress(string source [, int small])\",\"Decompresses BZip2 compressed data\"],bzerrno:[\"int bzerrno(resource bz)\",\"Returns the error number\"],bzerror:[\"array bzerror(resource bz)\",\"Returns the error number and error string in an associative array\"],bzerrstr:[\"string bzerrstr(resource bz)\",\"Returns the error string\"],bzopen:[\"resource bzopen(string|int file|fp, string mode)\",\"Opens a new BZip2 stream\"],bzread:[\"string bzread(resource bz[, int length])\",\"Reads up to length bytes from a BZip2 stream, or 1024 bytes if length is not specified\"],cal_days_in_month:[\"int cal_days_in_month(int calendar, int month, int year)\",\"Returns the number of days in a month for a given year and calendar\"],cal_from_jd:[\"array cal_from_jd(int jd, int calendar)\",\"Converts from Julian Day Count to a supported calendar and return extended information\"],cal_info:[\"array cal_info([int calendar])\",\"Returns information about a particular calendar\"],cal_to_jd:[\"int cal_to_jd(int calendar, int month, int day, int year)\",\"Converts from a supported calendar to Julian Day Count\"],call_user_func:[\"mixed call_user_func(mixed function_name [, mixed parmeter] [, mixed ...])\",\"Call a user function which is the first parameter\"],call_user_func_array:[\"mixed call_user_func_array(string function_name, array parameters)\",\"Call a user function which is the first parameter with the arguments contained in array\"],call_user_method:[\"mixed call_user_method(string method_name, mixed object [, mixed parameter] [, mixed ...])\",\"Call a user method on a specific object or class\"],call_user_method_array:[\"mixed call_user_method_array(string method_name, mixed object, array params)\",\"Call a user method on a specific object or class using a parameter array\"],ceil:[\"float ceil(float number)\",\"Returns the next highest integer value of the number\"],chdir:[\"bool chdir(string directory)\",\"Change the current directory\"],checkdate:[\"bool checkdate(int month, int day, int year)\",\"Returns true(1) if it is a valid date in gregorian calendar\"],chgrp:[\"bool chgrp(string filename, mixed group)\",\"Change file group\"],chmod:[\"bool chmod(string filename, int mode)\",\"Change file mode\"],chown:[\"bool chown (string filename, mixed user)\",\"Change file owner\"],chr:[\"string chr(int ascii)\",\"Converts ASCII code to a character\"],chroot:[\"bool chroot(string directory)\",\"Change root directory\"],chunk_split:[\"string chunk_split(string str [, int chunklen [, string ending]])\",\"Returns split line\"],class_alias:[\"bool class_alias(string user_class_name , string alias_name [, bool autoload])\",\"Creates an alias for user defined class\"],class_exists:[\"bool class_exists(string classname [, bool autoload])\",\"Checks if the class exists\"],class_implements:[\"array class_implements(mixed what [, bool autoload ])\",\"Return all classes and interfaces implemented by SPL\"],class_parents:[\"array class_parents(object instance [, boolean autoload = true])\",\"Return an array containing the names of all parent classes\"],clearstatcache:[\"void clearstatcache([bool clear_realpath_cache[, string filename]])\",\"Clear file stat cache\"],closedir:[\"void closedir([resource dir_handle])\",\"Close directory connection identified by the dir_handle\"],closelog:[\"bool closelog(void)\",\"Close connection to system logger\"],collator_asort:[\"bool collator_asort( Collator $coll, array(string) $arr )\",\"* Sort array using specified collator, maintaining index association.\"],collator_compare:[\"int collator_compare( Collator $coll, string $str1, string $str2 )\",\"* Compare two strings.\"],collator_create:[\"Collator collator_create( string $locale )\",\"* Create collator.\"],collator_get_attribute:[\"int collator_get_attribute( Collator $coll, int $attr )\",\"* Get collation attribute value.\"],collator_get_error_code:[\"int collator_get_error_code( Collator $coll )\",\"* Get collator's last error code.\"],collator_get_error_message:[\"string collator_get_error_message( Collator $coll )\",\"* Get text description for collator's last error code.\"],collator_get_locale:[\"string collator_get_locale( Collator $coll, int $type )\",\"* Gets the locale name of the collator.\"],collator_get_sort_key:[\"bool collator_get_sort_key( Collator $coll, string $str )\",\"* Get a sort key for a string from a Collator. }}}\"],collator_get_strength:[\"int collator_get_strength(Collator coll)\",\"* Returns the current collation strength.\"],collator_set_attribute:[\"bool collator_set_attribute( Collator $coll, int $attr, int $val )\",\"* Set collation attribute.\"],collator_set_strength:[\"bool collator_set_strength(Collator coll, int strength)\",\"* Set the collation strength.\"],collator_sort:[\"bool collator_sort(  Collator $coll, array(string) $arr [, int $sort_flags] )\",\"* Sort array using specified collator.\"],collator_sort_with_sort_keys:[\"bool collator_sort_with_sort_keys( Collator $coll, array(string) $arr )\",\"* Equivalent to standard PHP sort using Collator.  * Uses ICU ucol_getSortKey for performance.\"],com_create_guid:[\"string com_create_guid()\",\"Generate a globally unique identifier (GUID)\"],com_event_sink:[\"bool com_event_sink(object comobject, object sinkobject [, mixed sinkinterface])\",\"Connect events from a COM object to a PHP object\"],com_get_active_object:[\"object com_get_active_object(string progid [, int code_page ])\",\"Returns a handle to an already running instance of a COM object\"],com_load_typelib:[\"bool com_load_typelib(string typelib_name [, int case_insensitive])\",\"Loads a Typelibrary and registers its constants\"],com_message_pump:[\"bool com_message_pump([int timeoutms])\",\"Process COM messages, sleeping for up to timeoutms milliseconds\"],com_print_typeinfo:[\"bool com_print_typeinfo(object comobject | string typelib, string dispinterface, bool wantsink)\",\"Print out a PHP class definition for a dispatchable interface\"],compact:[\"array compact(mixed var_names [, mixed ...])\",\"Creates a hash containing variables and their values\"],compose_locale:[\"static string compose_locale($array)\",\"* Creates a locale by combining the parts of locale-ID passed  * }}}\"],confirm_extname_compiled:[\"string confirm_extname_compiled(string arg)\",\"Return a string to confirm that the module is compiled in\"],connection_aborted:[\"int connection_aborted(void)\",\"Returns true if client disconnected\"],connection_status:[\"int connection_status(void)\",\"Returns the connection status bitfield\"],constant:[\"mixed constant(string const_name)\",\"Given the name of a constant this function will return the constant's associated value\"],convert_cyr_string:[\"string convert_cyr_string(string str, string from, string to)\",\"Convert from one Cyrillic character set to another\"],convert_uudecode:[\"string convert_uudecode(string data)\",\"decode a uuencoded string\"],convert_uuencode:[\"string convert_uuencode(string data)\",\"uuencode a string\"],copy:[\"bool copy(string source_file, string destination_file [, resource context])\",\"Copy a file\"],cos:[\"float cos(float number)\",\"Returns the cosine of the number in radians\"],cosh:[\"float cosh(float number)\",\"Returns the hyperbolic cosine of the number, defined as (exp(number) + exp(-number))/2\"],count:[\"int count(mixed var [, int mode])\",\"Count the number of elements in a variable (usually an array)\"],count_chars:[\"mixed count_chars(string input [, int mode])\",\"Returns info about what characters are used in input\"],crc32:[\"string crc32(string str)\",\"Calculate the crc32 polynomial of a string\"],create_function:[\"string create_function(string args, string code)\",\"Creates an anonymous function, and returns its name (funny, eh?)\"],crypt:[\"string crypt(string str [, string salt])\",\"Hash a string\"],ctype_alnum:[\"bool ctype_alnum(mixed c)\",\"Checks for alphanumeric character(s)\"],ctype_alpha:[\"bool ctype_alpha(mixed c)\",\"Checks for alphabetic character(s)\"],ctype_cntrl:[\"bool ctype_cntrl(mixed c)\",\"Checks for control character(s)\"],ctype_digit:[\"bool ctype_digit(mixed c)\",\"Checks for numeric character(s)\"],ctype_graph:[\"bool ctype_graph(mixed c)\",\"Checks for any printable character(s) except space\"],ctype_lower:[\"bool ctype_lower(mixed c)\",\"Checks for lowercase character(s)\"],ctype_print:[\"bool ctype_print(mixed c)\",\"Checks for printable character(s)\"],ctype_punct:[\"bool ctype_punct(mixed c)\",\"Checks for any printable character which is not whitespace or an alphanumeric character\"],ctype_space:[\"bool ctype_space(mixed c)\",\"Checks for whitespace character(s)\"],ctype_upper:[\"bool ctype_upper(mixed c)\",\"Checks for uppercase character(s)\"],ctype_xdigit:[\"bool ctype_xdigit(mixed c)\",\"Checks for character(s) representing a hexadecimal digit\"],curl_close:[\"void curl_close(resource ch)\",\"Close a cURL session\"],curl_copy_handle:[\"resource curl_copy_handle(resource ch)\",\"Copy a cURL handle along with all of it's preferences\"],curl_errno:[\"int curl_errno(resource ch)\",\"Return an integer containing the last error number\"],curl_error:[\"string curl_error(resource ch)\",\"Return a string contain the last error for the current session\"],curl_exec:[\"bool curl_exec(resource ch)\",\"Perform a cURL session\"],curl_getinfo:[\"mixed curl_getinfo(resource ch [, int option])\",\"Get information regarding a specific transfer\"],curl_init:[\"resource curl_init([string url])\",\"Initialize a cURL session\"],curl_multi_add_handle:[\"int curl_multi_add_handle(resource mh, resource ch)\",\"Add a normal cURL handle to a cURL multi handle\"],curl_multi_close:[\"void curl_multi_close(resource mh)\",\"Close a set of cURL handles\"],curl_multi_exec:[\"int curl_multi_exec(resource mh, int &still_running)\",\"Run the sub-connections of the current cURL handle\"],curl_multi_getcontent:[\"string curl_multi_getcontent(resource ch)\",\"Return the content of a cURL handle if CURLOPT_RETURNTRANSFER is set\"],curl_multi_info_read:[\"array curl_multi_info_read(resource mh [, long msgs_in_queue])\",\"Get information about the current transfers\"],curl_multi_init:[\"resource curl_multi_init(void)\",\"Returns a new cURL multi handle\"],curl_multi_remove_handle:[\"int curl_multi_remove_handle(resource mh, resource ch)\",\"Remove a multi handle from a set of cURL handles\"],curl_multi_select:[\"int curl_multi_select(resource mh[, double timeout])\",'Get all the sockets associated with the cURL extension, which can then be \"selected\"'],curl_setopt:[\"bool curl_setopt(resource ch, int option, mixed value)\",\"Set an option for a cURL transfer\"],curl_setopt_array:[\"bool curl_setopt_array(resource ch, array options)\",\"Set an array of option for a cURL transfer\"],curl_version:[\"array curl_version([int version])\",\"Return cURL version information.\"],current:[\"mixed current(array array_arg)\",\"Return the element currently pointed to by the internal array pointer\"],date:[\"string date(string format [, long timestamp])\",\"Format a local date/time\"],date_add:[\"DateTime date_add(DateTime object, DateInterval interval)\",\"Adds an interval to the current date in object.\"],date_create:[\"DateTime date_create([string time[, DateTimeZone object]])\",\"Returns new DateTime object\"],date_create_from_format:[\"DateTime date_create_from_format(string format, string time[, DateTimeZone object])\",\"Returns new DateTime object formatted according to the specified format\"],date_date_set:[\"DateTime date_date_set(DateTime object, long year, long month, long day)\",\"Sets the date.\"],date_default_timezone_get:[\"string date_default_timezone_get()\",\"Gets the default timezone used by all date/time functions in a script\"],date_default_timezone_set:[\"bool date_default_timezone_set(string timezone_identifier)\",\"Sets the default timezone used by all date/time functions in a script\"],date_diff:[\"DateInterval date_diff(DateTime object [, bool absolute])\",\"Returns the difference between two DateTime objects.\"],date_format:[\"string date_format(DateTime object, string format)\",\"Returns date formatted according to given format\"],date_get_last_errors:[\"array date_get_last_errors()\",\"Returns the warnings and errors found while parsing a date/time string.\"],date_interval_create_from_date_string:[\"DateInterval date_interval_create_from_date_string(string time)\",\"Uses the normal date parsers and sets up a DateInterval from the relative parts of the parsed string\"],date_interval_format:[\"string date_interval_format(DateInterval object, string format)\",\"Formats the interval.\"],date_isodate_set:[\"DateTime date_isodate_set(DateTime object, long year, long week[, long day])\",\"Sets the ISO date.\"],date_modify:[\"DateTime date_modify(DateTime object, string modify)\",\"Alters the timestamp.\"],date_offset_get:[\"long date_offset_get(DateTime object)\",\"Returns the DST offset.\"],date_parse:[\"array date_parse(string date)\",\"Returns associative array with detailed info about given date\"],date_parse_from_format:[\"array date_parse_from_format(string format, string date)\",\"Returns associative array with detailed info about given date\"],date_sub:[\"DateTime date_sub(DateTime object, DateInterval interval)\",\"Subtracts an interval to the current date in object.\"],date_sun_info:[\"array date_sun_info(long time, float latitude, float longitude)\",\"Returns an array with information about sun set/rise and twilight begin/end\"],date_sunrise:[\"mixed date_sunrise(mixed time [, int format [, float latitude [, float longitude [, float zenith [, float gmt_offset]]]]])\",\"Returns time of sunrise for a given day and location\"],date_sunset:[\"mixed date_sunset(mixed time [, int format [, float latitude [, float longitude [, float zenith [, float gmt_offset]]]]])\",\"Returns time of sunset for a given day and location\"],date_time_set:[\"DateTime date_time_set(DateTime object, long hour, long minute[, long second])\",\"Sets the time.\"],date_timestamp_get:[\"long date_timestamp_get(DateTime object)\",\"Gets the Unix timestamp.\"],date_timestamp_set:[\"DateTime date_timestamp_set(DateTime object, long unixTimestamp)\",\"Sets the date and time based on an Unix timestamp.\"],date_timezone_get:[\"DateTimeZone date_timezone_get(DateTime object)\",\"Return new DateTimeZone object relative to give DateTime\"],date_timezone_set:[\"DateTime date_timezone_set(DateTime object, DateTimeZone object)\",\"Sets the timezone for the DateTime object.\"],datefmt_create:[\"IntlDateFormatter datefmt_create(string $locale, long date_type, long time_type[, string $timezone_str, long $calendar, string $pattern] )\",\"* Create formatter.\"],datefmt_format:[\"string datefmt_format( [mixed]int $args or array $args )\",\"* Format the time value as a string. }}}\"],datefmt_get_calendar:[\"string datefmt_get_calendar( IntlDateFormatter $mf )\",\"* Get formatter calendar.\"],datefmt_get_datetype:[\"string datefmt_get_datetype( IntlDateFormatter $mf )\",\"* Get formatter datetype.\"],datefmt_get_error_code:[\"int datefmt_get_error_code( IntlDateFormatter $nf )\",\"* Get formatter's last error code.\"],datefmt_get_error_message:[\"string datefmt_get_error_message( IntlDateFormatter $coll )\",\"* Get text description for formatter's last error code.\"],datefmt_get_locale:[\"string datefmt_get_locale(IntlDateFormatter $mf)\",\"* Get formatter locale.\"],datefmt_get_pattern:[\"string datefmt_get_pattern( IntlDateFormatter $mf )\",\"* Get formatter pattern.\"],datefmt_get_timetype:[\"string datefmt_get_timetype( IntlDateFormatter $mf )\",\"* Get formatter timetype.\"],datefmt_get_timezone_id:[\"string datefmt_get_timezone_id( IntlDateFormatter $mf )\",\"* Get formatter timezone_id.\"],datefmt_isLenient:[\"string datefmt_isLenient(IntlDateFormatter $mf)\",\"* Get formatter locale.\"],datefmt_localtime:[\"integer datefmt_localtime( IntlDateFormatter $fmt, string $text_to_parse[, int $parse_pos ])\",\"* Parse the string $value to a localtime array  }}}\"],datefmt_parse:[\"integer datefmt_parse( IntlDateFormatter $fmt, string $text_to_parse [, int $parse_pos] )\",\"* Parse the string $value starting at parse_pos to a Unix timestamp -int }}}\"],datefmt_setLenient:[\"string datefmt_setLenient(IntlDateFormatter $mf)\",\"* Set formatter lenient.\"],datefmt_set_calendar:[\"bool datefmt_set_calendar( IntlDateFormatter $mf, int $calendar )\",\"* Set formatter calendar.\"],datefmt_set_pattern:[\"bool datefmt_set_pattern( IntlDateFormatter $mf, string $pattern )\",\"* Set formatter pattern.\"],datefmt_set_timezone_id:[\"boolean datefmt_set_timezone_id( IntlDateFormatter $mf,$timezone_id)\",\"* Set formatter timezone_id.\"],dba_close:[\"void dba_close(resource handle)\",\"Closes database\"],dba_delete:[\"bool dba_delete(string key, resource handle)\",\"Deletes the entry associated with key    If inifile: remove all other key lines\"],dba_exists:[\"bool dba_exists(string key, resource handle)\",\"Checks, if the specified key exists\"],dba_fetch:[\"string dba_fetch(string key, [int skip ,] resource handle)\",\"Fetches the data associated with key\"],dba_firstkey:[\"string dba_firstkey(resource handle)\",\"Resets the internal key pointer and returns the first key\"],dba_handlers:[\"array dba_handlers([bool full_info])\",\"List configured database handlers\"],dba_insert:[\"bool dba_insert(string key, string value, resource handle)\",\"If not inifile: Insert value as key, return false, if key exists already     If inifile: Add vakue as key (next instance of key)\"],dba_key_split:[\"array|false dba_key_split(string key)\",\"Splits an inifile key into an array of the form array(0=>group,1=>value_name) but returns false if input is false or null\"],dba_list:[\"array dba_list()\",\"List opened databases\"],dba_nextkey:[\"string dba_nextkey(resource handle)\",\"Returns the next key\"],dba_open:[\"resource dba_open(string path, string mode [, string handlername, string ...])\",\"Opens path using the specified handler in mode\"],dba_optimize:[\"bool dba_optimize(resource handle)\",\"Optimizes (e.g. clean up, vacuum) database\"],dba_popen:[\"resource dba_popen(string path, string mode [, string handlername, string ...])\",\"Opens path using the specified handler in mode persistently\"],dba_replace:[\"bool dba_replace(string key, string value, resource handle)\",\"Inserts value as key, replaces key, if key exists already    If inifile: remove all other key lines\"],dba_sync:[\"bool dba_sync(resource handle)\",\"Synchronizes database\"],dcgettext:[\"string dcgettext(string domain_name, string msgid, long category)\",\"Return the translation of msgid for domain_name and category, or msgid unaltered if a translation does not exist\"],dcngettext:[\"string dcngettext (string domain, string msgid1, string msgid2, int n, int category)\",\"Plural version of dcgettext()\"],debug_backtrace:[\"array debug_backtrace([bool provide_object])\",\"Return backtrace as array\"],debug_print_backtrace:[\"void debug_print_backtrace(void) */\",\"ZEND_FUNCTION(debug_print_backtrace) {  zend_execute_data *ptr, *skip;  int lineno;  char *function_name;  char *filename;  char *class_name = NULL;  char *call_type;  char *include_filename = NULL;  zval *arg_array = NULL;  int indent = 0;   if (zend_parse_parameters_none() == FAILURE) {   return;  }   ptr = EG(current_execute_data);\",\"PHP_FUNCTION(dom_document_relaxNG_validate_file) {  _dom_document_relaxNG_validate(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_FILE); } /* }}} end dom_document_relaxNG_validate_file\"],dom_document_relaxNG_validate_xml:[\"boolean dom_document_relaxNG_validate_xml(string source); */\",\"PHP_FUNCTION(dom_document_relaxNG_validate_xml) {  _dom_document_relaxNG_validate(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_STRING); } /* }}} end dom_document_relaxNG_validate_xml\"],dom_document_rename_node:[\"DOMNode dom_document_rename_node(node n, string namespaceURI, string qualifiedName);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Document3-renameNode Since: DOM Level 3\"],dom_document_save:[\"int dom_document_save(string file);\",\"Convenience method to save to file\"],dom_document_save_html:[\"string dom_document_save_html();\",\"Convenience method to output as html\"],dom_document_save_html_file:[\"int dom_document_save_html_file(string file);\",\"Convenience method to save to file as html\"],dom_document_savexml:[\"string dom_document_savexml([node n]);\",\"URL: http://www.w3.org/TR/DOM-Level-3-LS/load-save.html#LS-DocumentLS-saveXML Since: DOM Level 3\"],dom_document_schema_validate:[\"boolean dom_document_schema_validate(string source); */\",\"PHP_FUNCTION(dom_document_schema_validate_xml) {  _dom_document_schema_validate(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_STRING); } /* }}} end dom_document_schema_validate\"],dom_document_schema_validate_file:[\"boolean dom_document_schema_validate_file(string filename); */\",\"PHP_FUNCTION(dom_document_schema_validate_file) {  _dom_document_schema_validate(INTERNAL_FUNCTION_PARAM_PASSTHRU, DOM_LOAD_FILE); } /* }}} end dom_document_schema_validate_file\"],dom_document_validate:[\"boolean dom_document_validate();\",\"Since: DOM extended\"],dom_document_xinclude:[\"int dom_document_xinclude([int options])\",\"Substitutues xincludes in a DomDocument\"],dom_domconfiguration_can_set_parameter:[\"boolean dom_domconfiguration_can_set_parameter(string name, domuserdata value);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#DOMConfiguration-canSetParameter Since:\"],dom_domconfiguration_get_parameter:[\"domdomuserdata dom_domconfiguration_get_parameter(string name);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#DOMConfiguration-getParameter Since:\"],dom_domconfiguration_set_parameter:[\"dom_void dom_domconfiguration_set_parameter(string name, domuserdata value);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#DOMConfiguration-property Since:\"],dom_domerrorhandler_handle_error:[\"dom_boolean dom_domerrorhandler_handle_error(domerror error);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#ID-ERRORS-DOMErrorHandler-handleError Since:\"],dom_domimplementation_create_document:[\"DOMDocument dom_domimplementation_create_document(string namespaceURI, string qualifiedName, DOMDocumentType doctype);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Level-2-Core-DOM-createDocument Since: DOM Level 2\"],dom_domimplementation_create_document_type:[\"DOMDocumentType dom_domimplementation_create_document_type(string qualifiedName, string publicId, string systemId);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Level-2-Core-DOM-createDocType Since: DOM Level 2\"],dom_domimplementation_get_feature:[\"DOMNode dom_domimplementation_get_feature(string feature, string version);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#DOMImplementation3-getFeature Since: DOM Level 3\"],dom_domimplementation_has_feature:[\"boolean dom_domimplementation_has_feature(string feature, string version);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#ID-5CED94D7 Since:\"],dom_domimplementationlist_item:[\"domdomimplementation dom_domimplementationlist_item(int index);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#DOMImplementationList-item Since:\"],dom_domimplementationsource_get_domimplementation:[\"domdomimplementation dom_domimplementationsource_get_domimplementation(string features);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#ID-getDOMImpl Since:\"],dom_domimplementationsource_get_domimplementations:[\"domimplementationlist dom_domimplementationsource_get_domimplementations(string features);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#ID-getDOMImpls Since:\"],dom_domstringlist_item:[\"domstring dom_domstringlist_item(int index);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#DOMStringList-item Since:\"],dom_element_get_attribute:[\"string dom_element_get_attribute(string name);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-666EE0F9 Since:\"],dom_element_get_attribute_node:[\"DOMAttr dom_element_get_attribute_node(string name);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-217A91B8 Since:\"],dom_element_get_attribute_node_ns:[\"DOMAttr dom_element_get_attribute_node_ns(string namespaceURI, string localName);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-ElGetAtNodeNS Since: DOM Level 2\"],dom_element_get_attribute_ns:[\"string dom_element_get_attribute_ns(string namespaceURI, string localName);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-ElGetAttrNS Since: DOM Level 2\"],dom_element_get_elements_by_tag_name:[\"DOMNodeList dom_element_get_elements_by_tag_name(string name);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-1938918D Since:\"],dom_element_get_elements_by_tag_name_ns:[\"DOMNodeList dom_element_get_elements_by_tag_name_ns(string namespaceURI, string localName);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-A6C90942 Since: DOM Level 2\"],dom_element_has_attribute:[\"boolean dom_element_has_attribute(string name);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-ElHasAttr Since: DOM Level 2\"],dom_element_has_attribute_ns:[\"boolean dom_element_has_attribute_ns(string namespaceURI, string localName);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-ElHasAttrNS Since: DOM Level 2\"],dom_element_remove_attribute:[\"void dom_element_remove_attribute(string name);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-6D6AC0F9 Since:\"],dom_element_remove_attribute_node:[\"DOMAttr dom_element_remove_attribute_node(DOMAttr oldAttr);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-D589198 Since:\"],dom_element_remove_attribute_ns:[\"void dom_element_remove_attribute_ns(string namespaceURI, string localName);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-ElRemAtNS Since: DOM Level 2\"],dom_element_set_attribute:[\"void dom_element_set_attribute(string name, string value);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-F68F082 Since:\"],dom_element_set_attribute_node:[\"DOMAttr dom_element_set_attribute_node(DOMAttr newAttr);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-887236154 Since:\"],dom_element_set_attribute_node_ns:[\"DOMAttr dom_element_set_attribute_node_ns(DOMAttr newAttr);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-ElSetAtNodeNS Since: DOM Level 2\"],dom_element_set_attribute_ns:[\"void dom_element_set_attribute_ns(string namespaceURI, string qualifiedName, string value);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-ElSetAttrNS Since: DOM Level 2\"],dom_element_set_id_attribute:[\"void dom_element_set_id_attribute(string name, boolean isId);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-ElSetIdAttr Since: DOM Level 3\"],dom_element_set_id_attribute_node:[\"void dom_element_set_id_attribute_node(attr idAttr, boolean isId);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-ElSetIdAttrNode Since: DOM Level 3\"],dom_element_set_id_attribute_ns:[\"void dom_element_set_id_attribute_ns(string namespaceURI, string localName, boolean isId);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-ElSetIdAttrNS Since: DOM Level 3\"],dom_import_simplexml:[\"somNode dom_import_simplexml(sxeobject node)\",\"Get a simplexml_element object from dom to allow for processing\"],dom_namednodemap_get_named_item:[\"DOMNode dom_namednodemap_get_named_item(string name);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-1074577549 Since:\"],dom_namednodemap_get_named_item_ns:[\"DOMNode dom_namednodemap_get_named_item_ns(string namespaceURI, string localName);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-getNamedItemNS Since: DOM Level 2\"],dom_namednodemap_item:[\"DOMNode dom_namednodemap_item(int index);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-349467F9 Since:\"],dom_namednodemap_remove_named_item:[\"DOMNode dom_namednodemap_remove_named_item(string name);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-D58B193 Since:\"],dom_namednodemap_remove_named_item_ns:[\"DOMNode dom_namednodemap_remove_named_item_ns(string namespaceURI, string localName);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-removeNamedItemNS Since: DOM Level 2\"],dom_namednodemap_set_named_item:[\"DOMNode dom_namednodemap_set_named_item(DOMNode arg);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-1025163788 Since:\"],dom_namednodemap_set_named_item_ns:[\"DOMNode dom_namednodemap_set_named_item_ns(DOMNode arg);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-setNamedItemNS Since: DOM Level 2\"],dom_namelist_get_name:[\"string dom_namelist_get_name(int index);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#NameList-getName Since:\"],dom_namelist_get_namespace_uri:[\"string dom_namelist_get_namespace_uri(int index);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#NameList-getNamespaceURI Since:\"],dom_node_append_child:[\"DomNode dom_node_append_child(DomNode newChild);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-184E7107 Since:\"],dom_node_clone_node:[\"DomNode dom_node_clone_node(boolean deep);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-3A0ED0A4 Since:\"],dom_node_compare_document_position:[\"short dom_node_compare_document_position(DomNode other);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Node3-compareDocumentPosition Since: DOM Level 3\"],dom_node_get_feature:[\"DomNode dom_node_get_feature(string feature, string version);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Node3-getFeature Since: DOM Level 3\"],dom_node_get_user_data:[\"mixed dom_node_get_user_data(string key);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Node3-getUserData Since: DOM Level 3\"],dom_node_has_attributes:[\"boolean dom_node_has_attributes();\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-NodeHasAttrs Since: DOM Level 2\"],dom_node_has_child_nodes:[\"boolean dom_node_has_child_nodes();\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-810594187 Since:\"],dom_node_insert_before:[\"domnode dom_node_insert_before(DomNode newChild, DomNode refChild);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-952280727 Since:\"],dom_node_is_default_namespace:[\"boolean dom_node_is_default_namespace(string namespaceURI);\",\"URL: http://www.w3.org/TR/DOM-Level-3-Core/core.html#Node3-isDefaultNamespace Since: DOM Level 3\"],dom_node_is_equal_node:[\"boolean dom_node_is_equal_node(DomNode arg);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Node3-isEqualNode Since: DOM Level 3\"],dom_node_is_same_node:[\"boolean dom_node_is_same_node(DomNode other);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Node3-isSameNode Since: DOM Level 3\"],dom_node_is_supported:[\"boolean dom_node_is_supported(string feature, string version);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Level-2-Core-Node-supports Since: DOM Level 2\"],dom_node_lookup_namespace_uri:[\"string dom_node_lookup_namespace_uri(string prefix);\",\"URL: http://www.w3.org/TR/DOM-Level-3-Core/core.html#Node3-lookupNamespaceURI Since: DOM Level 3\"],dom_node_lookup_prefix:[\"string dom_node_lookup_prefix(string namespaceURI);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Node3-lookupNamespacePrefix Since: DOM Level 3\"],dom_node_normalize:[\"void dom_node_normalize();\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-normalize Since:\"],dom_node_remove_child:[\"DomNode dom_node_remove_child(DomNode oldChild);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-1734834066 Since:\"],dom_node_replace_child:[\"DomNode dom_node_replace_child(DomNode newChild, DomNode oldChild);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-785887307 Since:\"],dom_node_set_user_data:[\"mixed dom_node_set_user_data(string key, mixed data, userdatahandler handler);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#Node3-setUserData Since: DOM Level 3\"],dom_nodelist_item:[\"DOMNode dom_nodelist_item(int index);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#ID-844377136 Since:\"],dom_string_extend_find_offset16:[\"int dom_string_extend_find_offset16(int offset32);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#i18n-methods-StringExtend-findOffset16 Since:\"],dom_string_extend_find_offset32:[\"int dom_string_extend_find_offset32(int offset16);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#i18n-methods-StringExtend-findOffset32 Since:\"],dom_text_is_whitespace_in_element_content:[\"boolean dom_text_is_whitespace_in_element_content();\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Text3-isWhitespaceInElementContent Since: DOM Level 3\"],dom_text_replace_whole_text:[\"DOMText dom_text_replace_whole_text(string content);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-Text3-replaceWholeText Since: DOM Level 3\"],dom_text_split_text:[\"DOMText dom_text_split_text(int offset);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#core-ID-38853C1D Since:\"],dom_userdatahandler_handle:[\"dom_void dom_userdatahandler_handle(short operation, string key, domobject data, node src, node dst);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html#ID-handleUserDataEvent Since:\"],dom_xpath_evaluate:[\"mixed dom_xpath_evaluate(string expr [,DOMNode context]); */\",\"PHP_FUNCTION(dom_xpath_evaluate) {  php_xpath_eval(INTERNAL_FUNCTION_PARAM_PASSTHRU, PHP_DOM_XPATH_EVALUATE); } /* }}} end dom_xpath_evaluate\"],dom_xpath_query:[\"DOMNodeList dom_xpath_query(string expr [,DOMNode context]); */\",\"PHP_FUNCTION(dom_xpath_query) {  php_xpath_eval(INTERNAL_FUNCTION_PARAM_PASSTHRU, PHP_DOM_XPATH_QUERY); } /* }}} end dom_xpath_query\"],dom_xpath_register_ns:[\"boolean dom_xpath_register_ns(string prefix, string uri); */\",'PHP_FUNCTION(dom_xpath_register_ns) {  zval *id;  xmlXPathContextPtr ctxp;  int prefix_len, ns_uri_len;  dom_xpath_object *intern;  unsigned char *prefix, *ns_uri;   if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), \"Oss\", &id, dom_xpath_class_entry, &prefix, &prefix_len, &ns_uri, &ns_uri_len) == FAILURE) {   return;  }   intern = (dom_xpath_object *)zend_object_store_get_object(id TSRMLS_CC);   ctxp = (xmlXPathContextPtr) intern->ptr;  if (ctxp == NULL) {   php_error_docref(NULL TSRMLS_CC, E_WARNING, \"Invalid XPath Context\");   RETURN_FALSE;  }   if (xmlXPathRegisterNs(ctxp, prefix, ns_uri) != 0) {   RETURN_FALSE  }  RETURN_TRUE; } /* }}}'],dom_xpath_register_php_functions:[\"void dom_xpath_register_php_functions() */\",'PHP_FUNCTION(dom_xpath_register_php_functions) {  zval *id;  dom_xpath_object *intern;  zval *array_value, **entry, *new_string;  int  name_len = 0;  char *name;   DOM_GET_THIS(id);    if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS() TSRMLS_CC, \"a\",  &array_value) == SUCCESS) {   intern = (dom_xpath_object *)zend_object_store_get_object(id TSRMLS_CC);   zend_hash_internal_pointer_reset(Z_ARRVAL_P(array_value));    while (zend_hash_get_current_data(Z_ARRVAL_P(array_value), (void **)&entry) == SUCCESS) {    SEPARATE_ZVAL(entry);    convert_to_string_ex(entry);     MAKE_STD_ZVAL(new_string);    ZVAL_LONG(new_string,1);       zend_hash_update(intern->registered_phpfunctions, Z_STRVAL_PP(entry), Z_STRLEN_PP(entry) + 1, &new_string, sizeof(zval*), NULL);    zend_hash_move_forward(Z_ARRVAL_P(array_value));   }   intern->registerPhpFunctions = 2;   RETURN_TRUE;   } else if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS() TSRMLS_CC, \"s\",  &name, &name_len) == SUCCESS) {   intern = (dom_xpath_object *)zend_object_store_get_object(id TSRMLS_CC);      MAKE_STD_ZVAL(new_string);   ZVAL_LONG(new_string,1);   zend_hash_update(intern->registered_phpfunctions, name, name_len + 1, &new_string, sizeof(zval*), NULL);   intern->registerPhpFunctions = 2;     } else {   intern = (dom_xpath_object *)zend_object_store_get_object(id TSRMLS_CC);   intern->registerPhpFunctions = 1;  }   } /* }}} end dom_xpath_register_php_functions'],each:[\"array each(array arr)\",\"Return the currently pointed key..value pair in the passed array, and advance the pointer to the next element\"],easter_date:[\"int easter_date([int year])\",\"Return the timestamp of midnight on Easter of a given year (defaults to current year)\"],easter_days:[\"int easter_days([int year, [int method]])\",\"Return the number of days after March 21 that Easter falls on for a given year (defaults to current year)\"],echo:[\"void echo(string arg1 [, string ...])\",\"Output one or more strings\"],empty:[\"bool empty( mixed var )\",\"Determine whether a variable is empty\"],enchant_broker_describe:[\"array enchant_broker_describe(resource broker)\",\"Enumerates the Enchant providers and tells you some rudimentary information about them. The same info is provided through phpinfo()\"],enchant_broker_dict_exists:[\"bool enchant_broker_dict_exists(resource broker, string tag)\",\"Wether a dictionary exists or not. Using non-empty tag\"],enchant_broker_free:[\"boolean enchant_broker_free(resource broker)\",\"Destroys the broker object and its dictionnaries\"],enchant_broker_free_dict:[\"resource enchant_broker_free_dict(resource dict)\",\"Free the dictionary resource\"],enchant_broker_get_dict_path:[\"string enchant_broker_get_dict_path(resource broker, int dict_type)\",\"Get the directory path for a given backend, works with ispell and myspell\"],enchant_broker_get_error:[\"string enchant_broker_get_error(resource broker)\",\"Returns the last error of the broker\"],enchant_broker_init:[\"resource enchant_broker_init()\",\"create a new broker object capable of requesting\"],enchant_broker_list_dicts:[\"string enchant_broker_list_dicts(resource broker)\",\"Lists the dictionaries available for the given broker\"],enchant_broker_request_dict:[\"resource enchant_broker_request_dict(resource broker, string tag)\",'create a new dictionary using tag, the non-empty language tag you wish to request  a dictionary for (\"en_US\", \"de_DE\", ...)'],enchant_broker_request_pwl_dict:[\"resource enchant_broker_request_pwl_dict(resource broker, string filename)\",\"creates a dictionary using a PWL file. A PWL file is personal word file one word per line. It must exist before the call.\"],enchant_broker_set_dict_path:[\"bool enchant_broker_set_dict_path(resource broker, int dict_type, string value)\",\"Set the directory path for a given backend, works with ispell and myspell\"],enchant_broker_set_ordering:[\"bool enchant_broker_set_ordering(resource broker, string tag, string ordering)\",\"Declares a preference of dictionaries to use for the language  described/referred to by 'tag'. The ordering is a comma delimited  list of provider names. As a special exception, the \\\"*\\\" tag can  be used as a language tag to declare a default ordering for any  language that does not explictly declare an ordering.\"],enchant_dict_add_to_personal:[\"void enchant_dict_add_to_personal(resource dict, string word)\",\"add 'word' to personal word list\"],enchant_dict_add_to_session:[\"void enchant_dict_add_to_session(resource dict, string word)\",\"add 'word' to this spell-checking session\"],enchant_dict_check:[\"bool enchant_dict_check(resource dict, string word)\",\"If the word is correctly spelled return true, otherwise return false\"],enchant_dict_describe:[\"array enchant_dict_describe(resource dict)\",\"Describes an individual dictionary 'dict'\"],enchant_dict_get_error:[\"string enchant_dict_get_error(resource dict)\",\"Returns the last error of the current spelling-session\"],enchant_dict_is_in_session:[\"bool enchant_dict_is_in_session(resource dict, string word)\",\"whether or not 'word' exists in this spelling-session\"],enchant_dict_quick_check:[\"bool enchant_dict_quick_check(resource dict, string word [, array &suggestions])\",\"If the word is correctly spelled return true, otherwise return false, if suggestions variable     is provided, fill it with spelling alternatives.\"],enchant_dict_store_replacement:[\"void enchant_dict_store_replacement(resource dict, string mis, string cor)\",\"add a correction for 'mis' using 'cor'.  Notes that you replaced @mis with @cor, so it's possibly more likely  that future occurrences of @mis will be replaced with @cor. So it might  bump @cor up in the suggestion list.\"],enchant_dict_suggest:[\"array enchant_dict_suggest(resource dict, string word)\",\"Will return a list of values if any of those pre-conditions are not met.\"],end:[\"mixed end(array array_arg)\",\"Advances array argument's internal pointer to the last element and return it\"],ereg:[\"int ereg(string pattern, string string [, array registers])\",\"Regular expression match\"],ereg_replace:[\"string ereg_replace(string pattern, string replacement, string string)\",\"Replace regular expression\"],eregi:[\"int eregi(string pattern, string string [, array registers])\",\"Case-insensitive regular expression match\"],eregi_replace:[\"string eregi_replace(string pattern, string replacement, string string)\",\"Case insensitive replace regular expression\"],error_get_last:[\"array error_get_last()\",\"Get the last occurred error as associative array. Returns NULL if there hasn't been an error yet.\"],error_log:[\"bool error_log(string message [, int message_type [, string destination [, string extra_headers]]])\",\"Send an error message somewhere\"],error_reporting:[\"int error_reporting([int new_error_level])\",\"Return the current error_reporting level, and if an argument was passed - change to the new level\"],escapeshellarg:[\"string escapeshellarg(string arg)\",\"Quote and escape an argument for use in a shell command\"],escapeshellcmd:[\"string escapeshellcmd(string command)\",\"Escape shell metacharacters\"],exec:[\"string exec(string command [, array &output [, int &return_value]])\",\"Execute an external program\"],exif_imagetype:[\"int exif_imagetype(string imagefile)\",\"Get the type of an image\"],exif_read_data:[\"array exif_read_data(string filename [, sections_needed [, sub_arrays[, read_thumbnail]]])\",\"Reads header data from the JPEG/TIFF image filename and optionally reads the internal thumbnails\"],exif_tagname:[\"string exif_tagname(index)\",\"Get headername for index or false if not defined\"],exif_thumbnail:[\"string exif_thumbnail(string filename [, &width, &height [, &imagetype]])\",\"Reads the embedded thumbnail\"],exit:[\"void exit([mixed status])\",\"Output a message and terminate the current script\"],exp:[\"float exp(float number)\",\"Returns e raised to the power of the number\"],explode:[\"array explode(string separator, string str [, int limit])\",\"Splits a string on string separator and return array of components. If limit is positive only limit number of components is returned. If limit is negative all components except the last abs(limit) are returned.\"],expm1:[\"float expm1(float number)\",\"Returns exp(number) - 1, computed in a way that accurate even when the value of number is close to zero\"],extension_loaded:[\"bool extension_loaded(string extension_name)\",\"Returns true if the named extension is loaded\"],extract:[\"int extract(array var_array [, int extract_type [, string prefix]])\",\"Imports variables into symbol table from an array\"],ezmlm_hash:[\"int ezmlm_hash(string addr)\",\"Calculate EZMLM list hash value.\"],fclose:[\"bool fclose(resource fp)\",\"Close an open file pointer\"],feof:[\"bool feof(resource fp)\",\"Test for end-of-file on a file pointer\"],fflush:[\"bool fflush(resource fp)\",\"Flushes output\"],fgetc:[\"string fgetc(resource fp)\",\"Get a character from file pointer\"],fgetcsv:[\"array fgetcsv(resource fp [,int length [, string delimiter [, string enclosure [, string escape]]]])\",\"Get line from file pointer and parse for CSV fields\"],fgets:[\"string fgets(resource fp[, int length])\",\"Get a line from file pointer\"],fgetss:[\"string fgetss(resource fp [, int length [, string allowable_tags]])\",\"Get a line from file pointer and strip HTML tags\"],file:[\"array file(string filename [, int flags[, resource context]])\",\"Read entire file into an array\"],file_exists:[\"bool file_exists(string filename)\",\"Returns true if filename exists\"],file_get_contents:[\"string file_get_contents(string filename [, bool use_include_path [, resource context [, long offset [, long maxlen]]]])\",\"Read the entire file into a string\"],file_put_contents:[\"int file_put_contents(string file, mixed data [, int flags [, resource context]])\",\"Write/Create a file with contents data and return the number of bytes written\"],fileatime:[\"int fileatime(string filename)\",\"Get last access time of file\"],filectime:[\"int filectime(string filename)\",\"Get inode modification time of file\"],filegroup:[\"int filegroup(string filename)\",\"Get file group\"],fileinode:[\"int fileinode(string filename)\",\"Get file inode\"],filemtime:[\"int filemtime(string filename)\",\"Get last modification time of file\"],fileowner:[\"int fileowner(string filename)\",\"Get file owner\"],fileperms:[\"int fileperms(string filename)\",\"Get file permissions\"],filesize:[\"int filesize(string filename)\",\"Get file size\"],filetype:[\"string filetype(string filename)\",\"Get file type\"],filter_has_var:[\"mixed filter_has_var(constant type, string variable_name)\",\"* Returns true if the variable with the name 'name' exists in source.\"],filter_input:[\"mixed filter_input(constant type, string variable_name [, long filter [, mixed options]])\",\"* Returns the filtered variable 'name'* from source `type`.\"],filter_input_array:[\"mixed filter_input_array(constant type, [, mixed options]])\",\"* Returns an array with all arguments defined in 'definition'.\"],filter_var:[\"mixed filter_var(mixed variable [, long filter [, mixed options]])\",\"* Returns the filtered version of the vriable.\"],filter_var_array:[\"mixed filter_var_array(array data, [, mixed options]])\",\"* Returns an array with all arguments defined in 'definition'.\"],finfo_buffer:[\"string finfo_buffer(resource finfo, char *string [, int options [, resource context]])\",\"Return infromation about a string buffer.\"],finfo_close:[\"resource finfo_close(resource finfo)\",\"Close fileinfo resource.\"],finfo_file:[\"string finfo_file(resource finfo, char *file_name [, int options [, resource context]])\",\"Return information about a file.\"],finfo_open:[\"resource finfo_open([int options [, string arg]])\",\"Create a new fileinfo resource.\"],finfo_set_flags:[\"bool finfo_set_flags(resource finfo, int options)\",\"Set libmagic configuration options.\"],floatval:[\"float floatval(mixed var)\",\"Get the float value of a variable\"],flock:[\"bool flock(resource fp, int operation [, int &wouldblock])\",\"Portable file locking\"],floor:[\"float floor(float number)\",\"Returns the next lowest integer value from the number\"],flush:[\"void flush(void)\",\"Flush the output buffer\"],fmod:[\"float fmod(float x, float y)\",\"Returns the remainder of dividing x by y as a float\"],fnmatch:[\"bool fnmatch(string pattern, string filename [, int flags])\",\"Match filename against pattern\"],fopen:[\"resource fopen(string filename, string mode [, bool use_include_path [, resource context]])\",\"Open a file or a URL and return a file pointer\"],forward_static_call:[\"mixed forward_static_call(mixed function_name [, mixed parmeter] [, mixed ...])\",\"Call a user function which is the first parameter\"],fpassthru:[\"int fpassthru(resource fp)\",\"Output all remaining data from a file pointer\"],fprintf:[\"int fprintf(resource stream, string format [, mixed arg1 [, mixed ...]])\",\"Output a formatted string into a stream\"],fputcsv:[\"int fputcsv(resource fp, array fields [, string delimiter [, string enclosure]])\",\"Format line as CSV and write to file pointer\"],fread:[\"string fread(resource fp, int length)\",\"Binary-safe file read\"],frenchtojd:[\"int frenchtojd(int month, int day, int year)\",\"Converts a french republic calendar date to julian day count\"],fscanf:[\"mixed fscanf(resource stream, string format [, string ...])\",\"Implements a mostly ANSI compatible fscanf()\"],fseek:[\"int fseek(resource fp, int offset [, int whence])\",\"Seek on a file pointer\"],fsockopen:[\"resource fsockopen(string hostname, int port [, int errno [, string errstr [, float timeout]]])\",\"Open Internet or Unix domain socket connection\"],fstat:[\"array fstat(resource fp)\",\"Stat() on a filehandle\"],ftell:[\"int ftell(resource fp)\",\"Get file pointer's read/write position\"],ftok:[\"int ftok(string pathname, string proj)\",\"Convert a pathname and a project identifier to a System V IPC key\"],ftp_alloc:[\"bool ftp_alloc(resource stream, int size[, &response])\",\"Attempt to allocate space on the remote FTP server\"],ftp_cdup:[\"bool ftp_cdup(resource stream)\",\"Changes to the parent directory\"],ftp_chdir:[\"bool ftp_chdir(resource stream, string directory)\",\"Changes directories\"],ftp_chmod:[\"int ftp_chmod(resource stream, int mode, string filename)\",\"Sets permissions on a file\"],ftp_close:[\"bool ftp_close(resource stream)\",\"Closes the FTP stream\"],ftp_connect:[\"resource ftp_connect(string host [, int port [, int timeout]])\",\"Opens a FTP stream\"],ftp_delete:[\"bool ftp_delete(resource stream, string file)\",\"Deletes a file\"],ftp_exec:[\"bool ftp_exec(resource stream, string command)\",\"Requests execution of a program on the FTP server\"],ftp_fget:[\"bool ftp_fget(resource stream, resource fp, string remote_file, int mode[, int resumepos])\",\"Retrieves a file from the FTP server and writes it to an open file\"],ftp_fput:[\"bool ftp_fput(resource stream, string remote_file, resource fp, int mode[, int startpos])\",\"Stores a file from an open file to the FTP server\"],ftp_get:[\"bool ftp_get(resource stream, string local_file, string remote_file, int mode[, int resume_pos])\",\"Retrieves a file from the FTP server and writes it to a local file\"],ftp_get_option:[\"mixed ftp_get_option(resource stream, int option)\",\"Gets an FTP option\"],ftp_login:[\"bool ftp_login(resource stream, string username, string password)\",\"Logs into the FTP server\"],ftp_mdtm:[\"int ftp_mdtm(resource stream, string filename)\",\"Returns the last modification time of the file, or -1 on error\"],ftp_mkdir:[\"string ftp_mkdir(resource stream, string directory)\",\"Creates a directory and returns the absolute path for the new directory or false on error\"],ftp_nb_continue:[\"int ftp_nb_continue(resource stream)\",\"Continues retrieving/sending a file nbronously\"],ftp_nb_fget:[\"int ftp_nb_fget(resource stream, resource fp, string remote_file, int mode[, int resumepos])\",\"Retrieves a file from the FTP server asynchronly and writes it to an open file\"],ftp_nb_fput:[\"int ftp_nb_fput(resource stream, string remote_file, resource fp, int mode[, int startpos])\",\"Stores a file from an open file to the FTP server nbronly\"],ftp_nb_get:[\"int ftp_nb_get(resource stream, string local_file, string remote_file, int mode[, int resume_pos])\",\"Retrieves a file from the FTP server nbhronly and writes it to a local file\"],ftp_nb_put:[\"int ftp_nb_put(resource stream, string remote_file, string local_file, int mode[, int startpos])\",\"Stores a file on the FTP server\"],ftp_nlist:[\"array ftp_nlist(resource stream, string directory)\",\"Returns an array of filenames in the given directory\"],ftp_pasv:[\"bool ftp_pasv(resource stream, bool pasv)\",\"Turns passive mode on or off\"],ftp_put:[\"bool ftp_put(resource stream, string remote_file, string local_file, int mode[, int startpos])\",\"Stores a file on the FTP server\"],ftp_pwd:[\"string ftp_pwd(resource stream)\",\"Returns the present working directory\"],ftp_raw:[\"array ftp_raw(resource stream, string command)\",\"Sends a literal command to the FTP server\"],ftp_rawlist:[\"array ftp_rawlist(resource stream, string directory [, bool recursive])\",\"Returns a detailed listing of a directory as an array of output lines\"],ftp_rename:[\"bool ftp_rename(resource stream, string src, string dest)\",\"Renames the given file to a new path\"],ftp_rmdir:[\"bool ftp_rmdir(resource stream, string directory)\",\"Removes a directory\"],ftp_set_option:[\"bool ftp_set_option(resource stream, int option, mixed value)\",\"Sets an FTP option\"],ftp_site:[\"bool ftp_site(resource stream, string cmd)\",\"Sends a SITE command to the server\"],ftp_size:[\"int ftp_size(resource stream, string filename)\",\"Returns the size of the file, or -1 on error\"],ftp_ssl_connect:[\"resource ftp_ssl_connect(string host [, int port [, int timeout]])\",\"Opens a FTP-SSL stream\"],ftp_systype:[\"string ftp_systype(resource stream)\",\"Returns the system type identifier\"],ftruncate:[\"bool ftruncate(resource fp, int size)\",\"Truncate file to 'size' length\"],func_get_arg:[\"mixed func_get_arg(int arg_num)\",\"Get the $arg_num'th argument that was passed to the function\"],func_get_args:[\"array func_get_args()\",\"Get an array of the arguments that were passed to the function\"],func_num_args:[\"int func_num_args(void)\",\"Get the number of arguments that were passed to the function\"],function_exists:[\"bool function_exists(string function_name)\",\"Checks if the function exists\"],fwrite:[\"int fwrite(resource fp, string str [, int length])\",\"Binary-safe file write\"],gc_collect_cycles:[\"int gc_collect_cycles(void)\",\"Forces collection of any existing garbage cycles.    Returns number of freed zvals\"],gc_disable:[\"void gc_disable(void)\",\"Deactivates the circular reference collector\"],gc_enable:[\"void gc_enable(void)\",\"Activates the circular reference collector\"],gc_enabled:[\"void gc_enabled(void)\",\"Returns status of the circular reference collector\"],gd_info:[\"array gd_info()\",\"\"],getKeywords:[\"static array getKeywords(string $locale) {\",\"* return an associative array containing keyword-value  * pairs for this locale. The keys are keys to the array (doh!)  * }}}\"],get_browser:[\"mixed get_browser([string browser_name [, bool return_array]])\",\"Get information about the capabilities of a browser. If browser_name is omitted or null, HTTP_USER_AGENT is used. Returns an object by default; if return_array is true, returns an array.\"],get_called_class:[\"string get_called_class()\",'Retrieves the \"Late Static Binding\" class name'],get_cfg_var:[\"mixed get_cfg_var(string option_name)\",\"Get the value of a PHP configuration option\"],get_class:[\"string get_class([object object])\",\"Retrieves the class name\"],get_class_methods:[\"array get_class_methods(mixed class)\",\"Returns an array of method names for class or class instance.\"],get_class_vars:[\"array get_class_vars(string class_name)\",\"Returns an array of default properties of the class.\"],get_current_user:[\"string get_current_user(void)\",\"Get the name of the owner of the current PHP script\"],get_declared_classes:[\"array get_declared_classes()\",\"Returns an array of all declared classes.\"],get_declared_interfaces:[\"array get_declared_interfaces()\",\"Returns an array of all declared interfaces.\"],get_defined_constants:[\"array get_defined_constants([bool categorize])\",\"Return an array containing the names and values of all defined constants\"],get_defined_functions:[\"array get_defined_functions(void)\",\"Returns an array of all defined functions\"],get_defined_vars:[\"array get_defined_vars(void)\",\"Returns an associative array of names and values of all currently defined variable names (variables in the current scope)\"],get_display_language:[\"static string get_display_language($locale[, $in_locale = null])\",\"* gets the language for the $locale in $in_locale or default_locale\"],get_display_name:[\"static string get_display_name($locale[, $in_locale = null])\",\"* gets the name for the $locale in $in_locale or default_locale\"],get_display_region:[\"static string get_display_region($locale, $in_locale = null)\",\"* gets the region for the $locale in $in_locale or default_locale\"],get_display_script:[\"static string get_display_script($locale, $in_locale = null)\",\"* gets the script for the $locale in $in_locale or default_locale\"],get_extension_funcs:[\"array get_extension_funcs(string extension_name)\",\"Returns an array with the names of functions belonging to the named extension\"],get_headers:[\"array get_headers(string url[, int format])\",\"fetches all the headers sent by the server in response to a HTTP request\"],get_html_translation_table:[\"array get_html_translation_table([int table [, int quote_style]])\",\"Returns the internal translation table used by htmlspecialchars and htmlentities\"],get_include_path:[\"string get_include_path()\",\"Get the current include_path configuration option\"],get_included_files:[\"array get_included_files(void)\",\"Returns an array with the file names that were include_once()'d\"],get_loaded_extensions:[\"array get_loaded_extensions([bool zend_extensions])\",\"Return an array containing names of loaded extensions\"],get_magic_quotes_gpc:[\"int get_magic_quotes_gpc(void)\",\"Get the current active configuration setting of magic_quotes_gpc\"],get_magic_quotes_runtime:[\"int get_magic_quotes_runtime(void)\",\"Get the current active configuration setting of magic_quotes_runtime\"],get_meta_tags:[\"array get_meta_tags(string filename [, bool use_include_path])\",\"Extracts all meta tag content attributes from a file and returns an array\"],get_object_vars:[\"array get_object_vars(object obj)\",\"Returns an array of object properties\"],get_parent_class:[\"string get_parent_class([mixed object])\",\"Retrieves the parent class name for object or class or current scope.\"],get_resource_type:[\"string get_resource_type(resource res)\",\"Get the resource type name for a given resource\"],getallheaders:[\"array getallheaders(void)\",\"\"],getcwd:[\"mixed getcwd(void)\",\"Gets the current directory\"],getdate:[\"array getdate([int timestamp])\",\"Get date/time information\"],getenv:[\"string getenv(string varname)\",\"Get the value of an environment variable\"],gethostbyaddr:[\"string gethostbyaddr(string ip_address)\",\"Get the Internet host name corresponding to a given IP address\"],gethostbyname:[\"string gethostbyname(string hostname)\",\"Get the IP address corresponding to a given Internet host name\"],gethostbynamel:[\"array gethostbynamel(string hostname)\",\"Return a list of IP addresses that a given hostname resolves to.\"],gethostname:[\"string gethostname()\",\"Get the host name of the current machine\"],getimagesize:[\"array getimagesize(string imagefile [, array info])\",\"Get the size of an image as 4-element array\"],getlastmod:[\"int getlastmod(void)\",\"Get time of last page modification\"],getmygid:[\"int getmygid(void)\",\"Get PHP script owner's GID\"],getmyinode:[\"int getmyinode(void)\",\"Get the inode of the current script being parsed\"],getmypid:[\"int getmypid(void)\",\"Get current process ID\"],getmyuid:[\"int getmyuid(void)\",\"Get PHP script owner's UID\"],getopt:[\"array getopt(string options [, array longopts])\",\"Get options from the command line argument list\"],getprotobyname:[\"int getprotobyname(string name)\",\"Returns protocol number associated with name as per /etc/protocols\"],getprotobynumber:[\"string getprotobynumber(int proto)\",\"Returns protocol name associated with protocol number proto\"],getrandmax:[\"int getrandmax(void)\",\"Returns the maximum value a random number can have\"],getrusage:[\"array getrusage([int who])\",\"Returns an array of usage statistics\"],getservbyname:[\"int getservbyname(string service, string protocol)\",'Returns port associated with service. Protocol must be \"tcp\" or \"udp\"'],getservbyport:[\"string getservbyport(int port, string protocol)\",'Returns service name associated with port. Protocol must be \"tcp\" or \"udp\"'],gettext:[\"string gettext(string msgid)\",\"Return the translation of msgid for the current domain, or msgid unaltered if a translation does not exist\"],gettimeofday:[\"array gettimeofday([bool get_as_float])\",\"Returns the current time as array\"],gettype:[\"string gettype(mixed var)\",\"Returns the type of the variable\"],glob:[\"array glob(string pattern [, int flags])\",\"Find pathnames matching a pattern\"],gmdate:[\"string gmdate(string format [, long timestamp])\",\"Format a GMT date/time\"],gmmktime:[\"int gmmktime([int hour [, int min [, int sec [, int mon [, int day [, int year]]]]]])\",\"Get UNIX timestamp for a GMT date\"],gmp_abs:[\"resource gmp_abs(resource a)\",\"Calculates absolute value\"],gmp_add:[\"resource gmp_add(resource a, resource b)\",\"Add a and b\"],gmp_and:[\"resource gmp_and(resource a, resource b)\",\"Calculates logical AND of a and b\"],gmp_clrbit:[\"void gmp_clrbit(resource &a, int index)\",\"Clears bit in a\"],gmp_cmp:[\"int gmp_cmp(resource a, resource b)\",\"Compares two numbers\"],gmp_com:[\"resource gmp_com(resource a)\",\"Calculates one's complement of a\"],gmp_div_q:[\"resource gmp_div_q(resource a, resource b [, int round])\",\"Divide a by b, returns quotient only\"],gmp_div_qr:[\"array gmp_div_qr(resource a, resource b [, int round])\",\"Divide a by b, returns quotient and reminder\"],gmp_div_r:[\"resource gmp_div_r(resource a, resource b [, int round])\",\"Divide a by b, returns reminder only\"],gmp_divexact:[\"resource gmp_divexact(resource a, resource b)\",\"Divide a by b using exact division algorithm\"],gmp_fact:[\"resource gmp_fact(int a)\",\"Calculates factorial function\"],gmp_gcd:[\"resource gmp_gcd(resource a, resource b)\",\"Computes greatest common denominator (gcd) of a and b\"],gmp_gcdext:[\"array gmp_gcdext(resource a, resource b)\",\"Computes G, S, and T, such that AS + BT = G = `gcd' (A, B)\"],gmp_hamdist:[\"int gmp_hamdist(resource a, resource b)\",\"Calculates hamming distance between a and b\"],gmp_init:[\"resource gmp_init(mixed number [, int base])\",\"Initializes GMP number\"],gmp_intval:[\"int gmp_intval(resource gmpnumber)\",\"Gets signed long value of GMP number\"],gmp_invert:[\"resource gmp_invert(resource a, resource b)\",\"Computes the inverse of a modulo b\"],gmp_jacobi:[\"int gmp_jacobi(resource a, resource b)\",\"Computes Jacobi symbol\"],gmp_legendre:[\"int gmp_legendre(resource a, resource b)\",\"Computes Legendre symbol\"],gmp_mod:[\"resource gmp_mod(resource a, resource b)\",\"Computes a modulo b\"],gmp_mul:[\"resource gmp_mul(resource a, resource b)\",\"Multiply a and b\"],gmp_neg:[\"resource gmp_neg(resource a)\",\"Negates a number\"],gmp_nextprime:[\"resource gmp_nextprime(resource a)\",\"Finds next prime of a\"],gmp_or:[\"resource gmp_or(resource a, resource b)\",\"Calculates logical OR of a and b\"],gmp_perfect_square:[\"bool gmp_perfect_square(resource a)\",\"Checks if a is an exact square\"],gmp_popcount:[\"int gmp_popcount(resource a)\",\"Calculates the population count of a\"],gmp_pow:[\"resource gmp_pow(resource base, int exp)\",\"Raise base to power exp\"],gmp_powm:[\"resource gmp_powm(resource base, resource exp, resource mod)\",\"Raise base to power exp and take result modulo mod\"],gmp_prob_prime:[\"int gmp_prob_prime(resource a[, int reps])\",'Checks if a is \"probably prime\"'],gmp_random:[\"resource gmp_random([int limiter])\",\"Gets random number\"],gmp_scan0:[\"int gmp_scan0(resource a, int start)\",\"Finds first zero bit\"],gmp_scan1:[\"int gmp_scan1(resource a, int start)\",\"Finds first non-zero bit\"],gmp_setbit:[\"void gmp_setbit(resource &a, int index[, bool set_clear])\",\"Sets or clear bit in a\"],gmp_sign:[\"int gmp_sign(resource a)\",\"Gets the sign of the number\"],gmp_sqrt:[\"resource gmp_sqrt(resource a)\",\"Takes integer part of square root of a\"],gmp_sqrtrem:[\"array gmp_sqrtrem(resource a)\",\"Square root with remainder\"],gmp_strval:[\"string gmp_strval(resource gmpnumber [, int base])\",\"Gets string representation of GMP number\"],gmp_sub:[\"resource gmp_sub(resource a, resource b)\",\"Subtract b from a\"],gmp_testbit:[\"bool gmp_testbit(resource a, int index)\",\"Tests if bit is set in a\"],gmp_xor:[\"resource gmp_xor(resource a, resource b)\",\"Calculates logical exclusive OR of a and b\"],gmstrftime:[\"string gmstrftime(string format [, int timestamp])\",\"Format a GMT/UCT time/date according to locale settings\"],grapheme_extract:[\"string grapheme_extract(string str, int size[, int extract_type[, int start[, int next]]])\",\"Function to extract a sequence of default grapheme clusters\"],grapheme_stripos:[\"int grapheme_stripos(string haystack, string needle [, int offset ])\",\"Find position of first occurrence of a string within another, ignoring case differences\"],grapheme_stristr:[\"string grapheme_stristr(string haystack, string needle[, bool part])\",\"Finds first occurrence of a string within another\"],grapheme_strlen:[\"int grapheme_strlen(string str)\",\"Get number of graphemes in a string\"],grapheme_strpos:[\"int grapheme_strpos(string haystack, string needle [, int offset ])\",\"Find position of first occurrence of a string within another\"],grapheme_strripos:[\"int grapheme_strripos(string haystack, string needle [, int offset])\",\"Find position of last occurrence of a string within another, ignoring case\"],grapheme_strrpos:[\"int grapheme_strrpos(string haystack, string needle [, int offset])\",\"Find position of last occurrence of a string within another\"],grapheme_strstr:[\"string grapheme_strstr(string haystack, string needle[, bool part])\",\"Finds first occurrence of a string within another\"],grapheme_substr:[\"string grapheme_substr(string str, int start [, int length])\",\"Returns part of a string\"],gregoriantojd:[\"int gregoriantojd(int month, int day, int year)\",\"Converts a gregorian calendar date to julian day count\"],gzcompress:[\"string gzcompress(string data [, int level])\",\"Gzip-compress a string\"],gzdeflate:[\"string gzdeflate(string data [, int level])\",\"Gzip-compress a string\"],gzencode:[\"string gzencode(string data [, int level [, int encoding_mode]])\",\"GZ encode a string\"],gzfile:[\"array gzfile(string filename [, int use_include_path])\",\"Read und uncompress entire .gz-file into an array\"],gzinflate:[\"string gzinflate(string data [, int length])\",\"Unzip a gzip-compressed string\"],gzopen:[\"resource gzopen(string filename, string mode [, int use_include_path])\",\"Open a .gz-file and return a .gz-file pointer\"],gzuncompress:[\"string gzuncompress(string data [, int length])\",\"Unzip a gzip-compressed string\"],hash:[\"string hash(string algo, string data[, bool raw_output = false])\",\"Generate a hash of a given input string Returns lowercase hexits by default\"],hash_algos:[\"array hash_algos(void)\",\"Return a list of registered hashing algorithms\"],hash_copy:[\"resource hash_copy(resource context)\",\"Copy hash resource\"],hash_file:[\"string hash_file(string algo, string filename[, bool raw_output = false])\",\"Generate a hash of a given file Returns lowercase hexits by default\"],hash_final:[\"string hash_final(resource context[, bool raw_output=false])\",\"Output resulting digest\"],hash_hmac:[\"string hash_hmac(string algo, string data, string key[, bool raw_output = false])\",\"Generate a hash of a given input string with a key using HMAC Returns lowercase hexits by default\"],hash_hmac_file:[\"string hash_hmac_file(string algo, string filename, string key[, bool raw_output = false])\",\"Generate a hash of a given file with a key using HMAC Returns lowercase hexits by default\"],hash_init:[\"resource hash_init(string algo[, int options, string key])\",\"Initialize a hashing context\"],hash_update:[\"bool hash_update(resource context, string data)\",\"Pump data into the hashing algorithm\"],hash_update_file:[\"bool hash_update_file(resource context, string filename[, resource context])\",\"Pump data into the hashing algorithm from a file\"],hash_update_stream:[\"int hash_update_stream(resource context, resource handle[, integer length])\",\"Pump data into the hashing algorithm from an open stream\"],header:[\"void header(string header [, bool replace, [int http_response_code]])\",\"Sends a raw HTTP header\"],header_remove:[\"void header_remove([string name])\",\"Removes an HTTP header previously set using header()\"],headers_list:[\"array headers_list(void)\",\"Return list of headers to be sent / already sent\"],headers_sent:[\"bool headers_sent([string &$file [, int &$line]])\",\"Returns true if headers have already been sent, false otherwise\"],hebrev:[\"string hebrev(string str [, int max_chars_per_line])\",\"Converts logical Hebrew text to visual text\"],hebrevc:[\"string hebrevc(string str [, int max_chars_per_line])\",\"Converts logical Hebrew text to visual text with newline conversion\"],hexdec:[\"int hexdec(string hexadecimal_number)\",\"Returns the decimal equivalent of the hexadecimal number\"],highlight_file:[\"bool highlight_file(string file_name [, bool return] )\",\"Syntax highlight a source file\"],highlight_string:[\"bool highlight_string(string string [, bool return] )\",\"Syntax highlight a string or optionally return it\"],html_entity_decode:[\"string html_entity_decode(string string [, int quote_style][, string charset])\",\"Convert all HTML entities to their applicable characters\"],htmlentities:[\"string htmlentities(string string [, int quote_style[, string charset[, bool double_encode]]])\",\"Convert all applicable characters to HTML entities\"],htmlspecialchars:[\"string htmlspecialchars(string string [, int quote_style[, string charset[, bool double_encode]]])\",\"Convert special characters to HTML entities\"],htmlspecialchars_decode:[\"string htmlspecialchars_decode(string string [, int quote_style])\",\"Convert special HTML entities back to characters\"],http_build_query:[\"string http_build_query(mixed formdata [, string prefix [, string arg_separator]])\",\"Generates a form-encoded query string from an associative array or object.\"],hypot:[\"float hypot(float num1, float num2)\",\"Returns sqrt(num1*num1 + num2*num2)\"],ibase_add_user:[\"bool ibase_add_user(resource service_handle, string user_name, string password [, string first_name [, string middle_name [, string last_name]]])\",\"Add a user to security database\"],ibase_affected_rows:[\"int ibase_affected_rows( [ resource link_identifier ] )\",\"Returns the number of rows affected by the previous INSERT, UPDATE or DELETE statement\"],ibase_backup:[\"mixed ibase_backup(resource service_handle, string source_db, string dest_file [, int options [, bool verbose]])\",\"Initiates a backup task in the service manager and returns immediately\"],ibase_blob_add:[\"bool ibase_blob_add(resource blob_handle, string data)\",\"Add data into created blob\"],ibase_blob_cancel:[\"bool ibase_blob_cancel(resource blob_handle)\",\"Cancel creating blob\"],ibase_blob_close:[\"string ibase_blob_close(resource blob_handle)\",\"Close blob\"],ibase_blob_create:[\"resource ibase_blob_create([resource link_identifier])\",\"Create blob for adding data\"],ibase_blob_echo:[\"bool ibase_blob_echo([ resource link_identifier, ] string blob_id)\",\"Output blob contents to browser\"],ibase_blob_get:[\"string ibase_blob_get(resource blob_handle, int len)\",\"Get len bytes data from open blob\"],ibase_blob_import:[\"string ibase_blob_import([ resource link_identifier, ] resource file)\",\"Create blob, copy file in it, and close it\"],ibase_blob_info:[\"array ibase_blob_info([ resource link_identifier, ] string blob_id)\",\"Return blob length and other useful info\"],ibase_blob_open:[\"resource ibase_blob_open([ resource link_identifier, ] string blob_id)\",\"Open blob for retrieving data parts\"],ibase_close:[\"bool ibase_close([resource link_identifier])\",\"Close an InterBase connection\"],ibase_commit:[\"bool ibase_commit( resource link_identifier )\",\"Commit transaction\"],ibase_commit_ret:[\"bool ibase_commit_ret( resource link_identifier )\",\"Commit transaction and retain the transaction context\"],ibase_connect:[\"resource ibase_connect(string database [, string username [, string password [, string charset [, int buffers [, int dialect [, string role]]]]]])\",\"Open a connection to an InterBase database\"],ibase_db_info:[\"string ibase_db_info(resource service_handle, string db, int action [, int argument])\",\"Request statistics about a database\"],ibase_delete_user:[\"bool ibase_delete_user(resource service_handle, string user_name, string password [, string first_name [, string middle_name [, string last_name]]])\",\"Delete a user from security database\"],ibase_drop_db:[\"bool ibase_drop_db([resource link_identifier])\",\"Drop an InterBase database\"],ibase_errcode:[\"int ibase_errcode(void)\",\"Return error code\"],ibase_errmsg:[\"string ibase_errmsg(void)\",\"Return error message\"],ibase_execute:[\"mixed ibase_execute(resource query [, mixed bind_arg [, mixed bind_arg [, ...]]])\",\"Execute a previously prepared query\"],ibase_fetch_assoc:[\"array ibase_fetch_assoc(resource result [, int fetch_flags])\",\"Fetch a row  from the results of a query\"],ibase_fetch_object:[\"object ibase_fetch_object(resource result [, int fetch_flags])\",\"Fetch a object from the results of a query\"],ibase_fetch_row:[\"array ibase_fetch_row(resource result [, int fetch_flags])\",\"Fetch a row  from the results of a query\"],ibase_field_info:[\"array ibase_field_info(resource query_result, int field_number)\",\"Get information about a field\"],ibase_free_event_handler:[\"bool ibase_free_event_handler(resource event)\",\"Frees the event handler set by ibase_set_event_handler()\"],ibase_free_query:[\"bool ibase_free_query(resource query)\",\"Free memory used by a query\"],ibase_free_result:[\"bool ibase_free_result(resource result)\",\"Free the memory used by a result\"],ibase_gen_id:[\"int ibase_gen_id(string generator [, int increment [, resource link_identifier ]])\",\"Increments the named generator and returns its new value\"],ibase_maintain_db:[\"bool ibase_maintain_db(resource service_handle, string db, int action [, int argument])\",\"Execute a maintenance command on the database server\"],ibase_modify_user:[\"bool ibase_modify_user(resource service_handle, string user_name, string password [, string first_name [, string middle_name [, string last_name]]])\",\"Modify a user in security database\"],ibase_name_result:[\"bool ibase_name_result(resource result, string name)\",\"Assign a name to a result for use with ... WHERE CURRENT OF <name> statements\"],ibase_num_fields:[\"int ibase_num_fields(resource query_result)\",\"Get the number of fields in result\"],ibase_num_params:[\"int ibase_num_params(resource query)\",\"Get the number of params in a prepared query\"],ibase_num_rows:[\"int ibase_num_rows( resource result_identifier )\",\"Return the number of rows that are available in a result\"],ibase_param_info:[\"array ibase_param_info(resource query, int field_number)\",\"Get information about a parameter\"],ibase_pconnect:[\"resource ibase_pconnect(string database [, string username [, string password [, string charset [, int buffers [, int dialect [, string role]]]]]])\",\"Open a persistent connection to an InterBase database\"],ibase_prepare:[\"resource ibase_prepare(resource link_identifier[, string query [, resource trans_identifier ]])\",\"Prepare a query for later execution\"],ibase_query:[\"mixed ibase_query([resource link_identifier, [ resource link_identifier, ]] string query [, mixed bind_arg [, mixed bind_arg [, ...]]])\",\"Execute a query\"],ibase_restore:[\"mixed ibase_restore(resource service_handle, string source_file, string dest_db [, int options [, bool verbose]])\",\"Initiates a restore task in the service manager and returns immediately\"],ibase_rollback:[\"bool ibase_rollback( resource link_identifier )\",\"Rollback transaction\"],ibase_rollback_ret:[\"bool ibase_rollback_ret( resource link_identifier )\",\"Rollback transaction and retain the transaction context\"],ibase_server_info:[\"string ibase_server_info(resource service_handle, int action)\",\"Request information about a database server\"],ibase_service_attach:[\"resource ibase_service_attach(string host, string dba_username, string dba_password)\",\"Connect to the service manager\"],ibase_service_detach:[\"bool ibase_service_detach(resource service_handle)\",\"Disconnect from the service manager\"],ibase_set_event_handler:[\"resource ibase_set_event_handler([resource link_identifier,] callback handler, string event [, string event [, ...]])\",\"Register the callback for handling each of the named events\"],ibase_trans:[\"resource ibase_trans([int trans_args [, resource link_identifier [, ... ], int trans_args [, resource link_identifier [, ... ]] [, ...]]])\",\"Start a transaction over one or several databases\"],ibase_wait_event:[\"string ibase_wait_event([resource link_identifier,] string event [, string event [, ...]])\",\"Waits for any one of the passed Interbase events to be posted by the database, and returns its name\"],iconv:[\"string iconv(string in_charset, string out_charset, string str)\",\"Returns str converted to the out_charset character set\"],iconv_get_encoding:[\"mixed iconv_get_encoding([string type])\",\"Get internal encoding and output encoding for ob_iconv_handler()\"],iconv_mime_decode:[\"string iconv_mime_decode(string encoded_string [, int mode, string charset])\",\"Decodes a mime header field\"],iconv_mime_decode_headers:[\"array iconv_mime_decode_headers(string headers [, int mode, string charset])\",\"Decodes multiple mime header fields\"],iconv_mime_encode:[\"string iconv_mime_encode(string field_name, string field_value [, array preference])\",\"Composes a mime header field with field_name and field_value in a specified scheme\"],iconv_set_encoding:[\"bool iconv_set_encoding(string type, string charset)\",\"Sets internal encoding and output encoding for ob_iconv_handler()\"],iconv_strlen:[\"int iconv_strlen(string str [, string charset])\",\"Returns the character count of str\"],iconv_strpos:[\"int iconv_strpos(string haystack, string needle [, int offset [, string charset]])\",\"Finds position of first occurrence of needle within part of haystack beginning with offset\"],iconv_strrpos:[\"int iconv_strrpos(string haystack, string needle [, string charset])\",\"Finds position of last occurrence of needle within part of haystack beginning with offset\"],iconv_substr:[\"string iconv_substr(string str, int offset, [int length, string charset])\",\"Returns specified part of a string\"],idate:[\"int idate(string format [, int timestamp])\",\"Format a local time/date as integer\"],idn_to_ascii:[\"int idn_to_ascii(string domain[, int options])\",\"Converts an Unicode domain to ASCII representation, as defined in the IDNA RFC\"],idn_to_utf8:[\"int idn_to_utf8(string domain[, int options])\",\"Converts an ASCII representation of the domain to Unicode (UTF-8), as defined in the IDNA RFC\"],ignore_user_abort:[\"int ignore_user_abort([string value])\",\"Set whether we want to ignore a user abort event or not\"],image2wbmp:[\"bool image2wbmp(resource im [, string filename [, int threshold]])\",\"Output WBMP image to browser or file\"],image_type_to_extension:[\"string image_type_to_extension(int imagetype [, bool include_dot])\",\"Get file extension for image-type returned by getimagesize, exif_read_data, exif_thumbnail, exif_imagetype\"],image_type_to_mime_type:[\"string image_type_to_mime_type(int imagetype)\",\"Get Mime-Type for image-type returned by getimagesize, exif_read_data, exif_thumbnail, exif_imagetype\"],imagealphablending:[\"bool imagealphablending(resource im, bool on)\",\"Turn alpha blending mode on or off for the given image\"],imageantialias:[\"bool imageantialias(resource im, bool on)\",\"Should antialiased functions used or not\"],imagearc:[\"bool imagearc(resource im, int cx, int cy, int w, int h, int s, int e, int col)\",\"Draw a partial ellipse\"],imagechar:[\"bool imagechar(resource im, int font, int x, int y, string c, int col)\",\"Draw a character\"],imagecharup:[\"bool imagecharup(resource im, int font, int x, int y, string c, int col)\",\"Draw a character rotated 90 degrees counter-clockwise\"],imagecolorallocate:[\"int imagecolorallocate(resource im, int red, int green, int blue)\",\"Allocate a color for an image\"],imagecolorallocatealpha:[\"int imagecolorallocatealpha(resource im, int red, int green, int blue, int alpha)\",\"Allocate a color with an alpha level.  Works for true color and palette based images\"],imagecolorat:[\"int imagecolorat(resource im, int x, int y)\",\"Get the index of the color of a pixel\"],imagecolorclosest:[\"int imagecolorclosest(resource im, int red, int green, int blue)\",\"Get the index of the closest color to the specified color\"],imagecolorclosestalpha:[\"int imagecolorclosestalpha(resource im, int red, int green, int blue, int alpha)\",\"Find the closest matching colour with alpha transparency\"],imagecolorclosesthwb:[\"int imagecolorclosesthwb(resource im, int red, int green, int blue)\",\"Get the index of the color which has the hue, white and blackness nearest to the given color\"],imagecolordeallocate:[\"bool imagecolordeallocate(resource im, int index)\",\"De-allocate a color for an image\"],imagecolorexact:[\"int imagecolorexact(resource im, int red, int green, int blue)\",\"Get the index of the specified color\"],imagecolorexactalpha:[\"int imagecolorexactalpha(resource im, int red, int green, int blue, int alpha)\",\"Find exact match for colour with transparency\"],imagecolormatch:[\"bool imagecolormatch(resource im1, resource im2)\",\"Makes the colors of the palette version of an image more closely match the true color version\"],imagecolorresolve:[\"int imagecolorresolve(resource im, int red, int green, int blue)\",\"Get the index of the specified color or its closest possible alternative\"],imagecolorresolvealpha:[\"int imagecolorresolvealpha(resource im, int red, int green, int blue, int alpha)\",\"Resolve/Allocate a colour with an alpha level.  Works for true colour and palette based images\"],imagecolorset:[\"void imagecolorset(resource im, int col, int red, int green, int blue)\",\"Set the color for the specified palette index\"],imagecolorsforindex:[\"array imagecolorsforindex(resource im, int col)\",\"Get the colors for an index\"],imagecolorstotal:[\"int imagecolorstotal(resource im)\",\"Find out the number of colors in an image's palette\"],imagecolortransparent:[\"int imagecolortransparent(resource im [, int col])\",\"Define a color as transparent\"],imageconvolution:[\"resource imageconvolution(resource src_im, array matrix3x3, double div, double offset)\",\"Apply a 3x3 convolution matrix, using coefficient div and offset\"],imagecopy:[\"bool imagecopy(resource dst_im, resource src_im, int dst_x, int dst_y, int src_x, int src_y, int src_w, int src_h)\",\"Copy part of an image\"],imagecopymerge:[\"bool imagecopymerge(resource src_im, resource dst_im, int dst_x, int dst_y, int src_x, int src_y, int src_w, int src_h, int pct)\",\"Merge one part of an image with another\"],imagecopymergegray:[\"bool imagecopymergegray(resource src_im, resource dst_im, int dst_x, int dst_y, int src_x, int src_y, int src_w, int src_h, int pct)\",\"Merge one part of an image with another\"],imagecopyresampled:[\"bool imagecopyresampled(resource dst_im, resource src_im, int dst_x, int dst_y, int src_x, int src_y, int dst_w, int dst_h, int src_w, int src_h)\",\"Copy and resize part of an image using resampling to help ensure clarity\"],imagecopyresized:[\"bool imagecopyresized(resource dst_im, resource src_im, int dst_x, int dst_y, int src_x, int src_y, int dst_w, int dst_h, int src_w, int src_h)\",\"Copy and resize part of an image\"],imagecreate:[\"resource imagecreate(int x_size, int y_size)\",\"Create a new image\"],imagecreatefromgd:[\"resource imagecreatefromgd(string filename)\",\"Create a new image from GD file or URL\"],imagecreatefromgd2:[\"resource imagecreatefromgd2(string filename)\",\"Create a new image from GD2 file or URL\"],imagecreatefromgd2part:[\"resource imagecreatefromgd2part(string filename, int srcX, int srcY, int width, int height)\",\"Create a new image from a given part of GD2 file or URL\"],imagecreatefromgif:[\"resource imagecreatefromgif(string filename)\",\"Create a new image from GIF file or URL\"],imagecreatefromjpeg:[\"resource imagecreatefromjpeg(string filename)\",\"Create a new image from JPEG file or URL\"],imagecreatefrompng:[\"resource imagecreatefrompng(string filename)\",\"Create a new image from PNG file or URL\"],imagecreatefromstring:[\"resource imagecreatefromstring(string image)\",\"Create a new image from the image stream in the string\"],imagecreatefromwbmp:[\"resource imagecreatefromwbmp(string filename)\",\"Create a new image from WBMP file or URL\"],imagecreatefromxbm:[\"resource imagecreatefromxbm(string filename)\",\"Create a new image from XBM file or URL\"],imagecreatefromxpm:[\"resource imagecreatefromxpm(string filename)\",\"Create a new image from XPM file or URL\"],imagecreatetruecolor:[\"resource imagecreatetruecolor(int x_size, int y_size)\",\"Create a new true color image\"],imagedashedline:[\"bool imagedashedline(resource im, int x1, int y1, int x2, int y2, int col)\",\"Draw a dashed line\"],imagedestroy:[\"bool imagedestroy(resource im)\",\"Destroy an image\"],imageellipse:[\"bool imageellipse(resource im, int cx, int cy, int w, int h, int color)\",\"Draw an ellipse\"],imagefill:[\"bool imagefill(resource im, int x, int y, int col)\",\"Flood fill\"],imagefilledarc:[\"bool imagefilledarc(resource im, int cx, int cy, int w, int h, int s, int e, int col, int style)\",\"Draw a filled partial ellipse\"],imagefilledellipse:[\"bool imagefilledellipse(resource im, int cx, int cy, int w, int h, int color)\",\"Draw an ellipse\"],imagefilledpolygon:[\"bool imagefilledpolygon(resource im, array point, int num_points, int col)\",\"Draw a filled polygon\"],imagefilledrectangle:[\"bool imagefilledrectangle(resource im, int x1, int y1, int x2, int y2, int col)\",\"Draw a filled rectangle\"],imagefilltoborder:[\"bool imagefilltoborder(resource im, int x, int y, int border, int col)\",\"Flood fill to specific color\"],imagefilter:[\"bool imagefilter(resource src_im, int filtertype, [args] )\",\"Applies Filter an image using a custom angle\"],imagefontheight:[\"int imagefontheight(int font)\",\"Get font height\"],imagefontwidth:[\"int imagefontwidth(int font)\",\"Get font width\"],imageftbbox:[\"array imageftbbox(float size, float angle, string font_file, string text [, array extrainfo])\",\"Give the bounding box of a text using fonts via freetype2\"],imagefttext:[\"array imagefttext(resource im, float size, float angle, int x, int y, int col, string font_file, string text [, array extrainfo])\",\"Write text to the image using fonts via freetype2\"],imagegammacorrect:[\"bool imagegammacorrect(resource im, float inputgamma, float outputgamma)\",\"Apply a gamma correction to a GD image\"],imagegd:[\"bool imagegd(resource im [, string filename])\",\"Output GD image to browser or file\"],imagegd2:[\"bool imagegd2(resource im [, string filename, [, int chunk_size, [, int type]]])\",\"Output GD2 image to browser or file\"],imagegif:[\"bool imagegif(resource im [, string filename])\",\"Output GIF image to browser or file\"],imagegrabscreen:[\"resource imagegrabscreen()\",\"Grab a screenshot\"],imagegrabwindow:[\"resource imagegrabwindow(int window_handle [, int client_area])\",\"Grab a window or its client area using a windows handle (HWND property in COM instance)\"],imageinterlace:[\"int imageinterlace(resource im [, int interlace])\",\"Enable or disable interlace\"],imageistruecolor:[\"bool imageistruecolor(resource im)\",\"return true if the image uses truecolor\"],imagejpeg:[\"bool imagejpeg(resource im [, string filename [, int quality]])\",\"Output JPEG image to browser or file\"],imagelayereffect:[\"bool imagelayereffect(resource im, int effect)\",\"Set the alpha blending flag to use the bundled libgd layering effects\"],imageline:[\"bool imageline(resource im, int x1, int y1, int x2, int y2, int col)\",\"Draw a line\"],imageloadfont:[\"int imageloadfont(string filename)\",\"Load a new font\"],imagepalettecopy:[\"void imagepalettecopy(resource dst, resource src)\",\"Copy the palette from the src image onto the dst image\"],imagepng:[\"bool imagepng(resource im [, string filename])\",\"Output PNG image to browser or file\"],imagepolygon:[\"bool imagepolygon(resource im, array point, int num_points, int col)\",\"Draw a polygon\"],imagepsbbox:[\"array imagepsbbox(string text, resource font, int size [, int space, int tightness, float angle])\",\"Return the bounding box needed by a string if rasterized\"],imagepscopyfont:[\"int imagepscopyfont(int font_index)\",\"Make a copy of a font for purposes like extending or reenconding\"],imagepsencodefont:[\"bool imagepsencodefont(resource font_index, string filename)\",\"To change a fonts character encoding vector\"],imagepsextendfont:[\"bool imagepsextendfont(resource font_index, float extend)\",\"Extend or or condense (if extend < 1) a font\"],imagepsfreefont:[\"bool imagepsfreefont(resource font_index)\",\"Free memory used by a font\"],imagepsloadfont:[\"resource imagepsloadfont(string pathname)\",\"Load a new font from specified file\"],imagepsslantfont:[\"bool imagepsslantfont(resource font_index, float slant)\",\"Slant a font\"],imagepstext:[\"array imagepstext(resource image, string text, resource font, int size, int foreground, int background, int xcoord, int ycoord [, int space [, int tightness [, float angle [, int antialias])\",\"Rasterize a string over an image\"],imagerectangle:[\"bool imagerectangle(resource im, int x1, int y1, int x2, int y2, int col)\",\"Draw a rectangle\"],imagerotate:[\"resource imagerotate(resource src_im, float angle, int bgdcolor [, int ignoretransparent])\",\"Rotate an image using a custom angle\"],imagesavealpha:[\"bool imagesavealpha(resource im, bool on)\",\"Include alpha channel to a saved image\"],imagesetbrush:[\"bool imagesetbrush(resource image, resource brush)\",'Set the brush image to $brush when filling $image with the \"IMG_COLOR_BRUSHED\" color'],imagesetpixel:[\"bool imagesetpixel(resource im, int x, int y, int col)\",\"Set a single pixel\"],imagesetstyle:[\"bool imagesetstyle(resource im, array styles)\",\"Set the line drawing styles for use with imageline and IMG_COLOR_STYLED.\"],imagesetthickness:[\"bool imagesetthickness(resource im, int thickness)\",\"Set line thickness for drawing lines, ellipses, rectangles, polygons etc.\"],imagesettile:[\"bool imagesettile(resource image, resource tile)\",'Set the tile image to $tile when filling $image with the \"IMG_COLOR_TILED\" color'],imagestring:[\"bool imagestring(resource im, int font, int x, int y, string str, int col)\",\"Draw a string horizontally\"],imagestringup:[\"bool imagestringup(resource im, int font, int x, int y, string str, int col)\",\"Draw a string vertically - rotated 90 degrees counter-clockwise\"],imagesx:[\"int imagesx(resource im)\",\"Get image width\"],imagesy:[\"int imagesy(resource im)\",\"Get image height\"],imagetruecolortopalette:[\"void imagetruecolortopalette(resource im, bool ditherFlag, int colorsWanted)\",\"Convert a true colour image to a palette based image with a number of colours, optionally using dithering.\"],imagettfbbox:[\"array imagettfbbox(float size, float angle, string font_file, string text)\",\"Give the bounding box of a text using TrueType fonts\"],imagettftext:[\"array imagettftext(resource im, float size, float angle, int x, int y, int col, string font_file, string text)\",\"Write text to the image using a TrueType font\"],imagetypes:[\"int imagetypes(void)\",\"Return the types of images supported in a bitfield - 1=GIF, 2=JPEG, 4=PNG, 8=WBMP, 16=XPM\"],imagewbmp:[\"bool imagewbmp(resource im [, string filename, [, int foreground]])\",\"Output WBMP image to browser or file\"],imagexbm:[\"int imagexbm(int im, string filename [, int foreground])\",\"Output XBM image to browser or file\"],imap_8bit:[\"string imap_8bit(string text)\",\"Convert an 8-bit string to a quoted-printable string\"],imap_alerts:[\"array imap_alerts(void)\",\"Returns an array of all IMAP alerts that have been generated since the last page load or since the last imap_alerts() call, whichever came last. The alert stack is cleared after imap_alerts() is called.\"],imap_append:[\"bool imap_append(resource stream_id, string folder, string message [, string options [, string internal_date]])\",\"Append a new message to a specified mailbox\"],imap_base64:[\"string imap_base64(string text)\",\"Decode BASE64 encoded text\"],imap_binary:[\"string imap_binary(string text)\",\"Convert an 8bit string to a base64 string\"],imap_body:[\"string imap_body(resource stream_id, int msg_no [, int options])\",\"Read the message body\"],imap_bodystruct:[\"object imap_bodystruct(resource stream_id, int msg_no, string section)\",\"Read the structure of a specified body section of a specific message\"],imap_check:[\"object imap_check(resource stream_id)\",\"Get mailbox properties\"],imap_clearflag_full:[\"bool imap_clearflag_full(resource stream_id, string sequence, string flag [, int options])\",\"Clears flags on messages\"],imap_close:[\"bool imap_close(resource stream_id [, int options])\",\"Close an IMAP stream\"],imap_createmailbox:[\"bool imap_createmailbox(resource stream_id, string mailbox)\",\"Create a new mailbox\"],imap_delete:[\"bool imap_delete(resource stream_id, int msg_no [, int options])\",\"Mark a message for deletion\"],imap_deletemailbox:[\"bool imap_deletemailbox(resource stream_id, string mailbox)\",\"Delete a mailbox\"],imap_errors:[\"array imap_errors(void)\",\"Returns an array of all IMAP errors generated since the last page load, or since the last imap_errors() call, whichever came last. The error stack is cleared after imap_errors() is called.\"],imap_expunge:[\"bool imap_expunge(resource stream_id)\",\"Permanently delete all messages marked for deletion\"],imap_fetch_overview:[\"array imap_fetch_overview(resource stream_id, string sequence [, int options])\",\"Read an overview of the information in the headers of the given message sequence\"],imap_fetchbody:[\"string imap_fetchbody(resource stream_id, int msg_no, string section [, int options])\",\"Get a specific body section\"],imap_fetchheader:[\"string imap_fetchheader(resource stream_id, int msg_no [, int options])\",\"Get the full unfiltered header for a message\"],imap_fetchstructure:[\"object imap_fetchstructure(resource stream_id, int msg_no [, int options])\",\"Read the full structure of a message\"],imap_gc:[\"bool imap_gc(resource stream_id, int flags)\",\"This function garbage collects (purges) the cache of entries of a specific type.\"],imap_get_quota:[\"array imap_get_quota(resource stream_id, string qroot)\",\"Returns the quota set to the mailbox account qroot\"],imap_get_quotaroot:[\"array imap_get_quotaroot(resource stream_id, string mbox)\",\"Returns the quota set to the mailbox account mbox\"],imap_getacl:[\"array imap_getacl(resource stream_id, string mailbox)\",\"Gets the ACL for a given mailbox\"],imap_getmailboxes:[\"array imap_getmailboxes(resource stream_id, string ref, string pattern)\",\"Reads the list of mailboxes and returns a full array of objects containing name, attributes, and delimiter\"],imap_getsubscribed:[\"array imap_getsubscribed(resource stream_id, string ref, string pattern)\",\"Return a list of subscribed mailboxes, in the same format as imap_getmailboxes()\"],imap_headerinfo:[\"object imap_headerinfo(resource stream_id, int msg_no [, int from_length [, int subject_length [, string default_host]]])\",\"Read the headers of the message\"],imap_headers:[\"array imap_headers(resource stream_id)\",\"Returns headers for all messages in a mailbox\"],imap_last_error:[\"string imap_last_error(void)\",\"Returns the last error that was generated by an IMAP function. The error stack is NOT cleared after this call.\"],imap_list:[\"array imap_list(resource stream_id, string ref, string pattern)\",\"Read the list of mailboxes\"],imap_listscan:[\"array imap_listscan(resource stream_id, string ref, string pattern, string content)\",\"Read list of mailboxes containing a certain string\"],imap_lsub:[\"array imap_lsub(resource stream_id, string ref, string pattern)\",\"Return a list of subscribed mailboxes\"],imap_mail:[\"bool imap_mail(string to, string subject, string message [, string additional_headers [, string cc [, string bcc [, string rpath]]]])\",\"Send an email message\"],imap_mail_compose:[\"string imap_mail_compose(array envelope, array body)\",\"Create a MIME message based on given envelope and body sections\"],imap_mail_copy:[\"bool imap_mail_copy(resource stream_id, string msglist, string mailbox [, int options])\",\"Copy specified message to a mailbox\"],imap_mail_move:[\"bool imap_mail_move(resource stream_id, string sequence, string mailbox [, int options])\",\"Move specified message to a mailbox\"],imap_mailboxmsginfo:[\"object imap_mailboxmsginfo(resource stream_id)\",\"Returns info about the current mailbox\"],imap_mime_header_decode:[\"array imap_mime_header_decode(string str)\",\"Decode mime header element in accordance with RFC 2047 and return array of objects containing 'charset' encoding and decoded 'text'\"],imap_msgno:[\"int imap_msgno(resource stream_id, int unique_msg_id)\",\"Get the sequence number associated with a UID\"],imap_mutf7_to_utf8:[\"string imap_mutf7_to_utf8(string in)\",\"Decode a modified UTF-7 string to UTF-8\"],imap_num_msg:[\"int imap_num_msg(resource stream_id)\",\"Gives the number of messages in the current mailbox\"],imap_num_recent:[\"int imap_num_recent(resource stream_id)\",\"Gives the number of recent messages in current mailbox\"],imap_open:[\"resource imap_open(string mailbox, string user, string password [, int options [, int n_retries]])\",\"Open an IMAP stream to a mailbox\"],imap_ping:[\"bool imap_ping(resource stream_id)\",\"Check if the IMAP stream is still active\"],imap_qprint:[\"string imap_qprint(string text)\",\"Convert a quoted-printable string to an 8-bit string\"],imap_renamemailbox:[\"bool imap_renamemailbox(resource stream_id, string old_name, string new_name)\",\"Rename a mailbox\"],imap_reopen:[\"bool imap_reopen(resource stream_id, string mailbox [, int options [, int n_retries]])\",\"Reopen an IMAP stream to a new mailbox\"],imap_rfc822_parse_adrlist:[\"array imap_rfc822_parse_adrlist(string address_string, string default_host)\",\"Parses an address string\"],imap_rfc822_parse_headers:[\"object imap_rfc822_parse_headers(string headers [, string default_host])\",\"Parse a set of mail headers contained in a string, and return an object similar to imap_headerinfo()\"],imap_rfc822_write_address:[\"string imap_rfc822_write_address(string mailbox, string host, string personal)\",\"Returns a properly formatted email address given the mailbox, host, and personal info\"],imap_savebody:['bool imap_savebody(resource stream_id, string|resource file, int msg_no[, string section = \"\"[, int options = 0]])',\"Save a specific body section to a file\"],imap_search:[\"array imap_search(resource stream_id, string criteria [, int options [, string charset]])\",\"Return a list of messages matching the given criteria\"],imap_set_quota:[\"bool imap_set_quota(resource stream_id, string qroot, int mailbox_size)\",\"Will set the quota for qroot mailbox\"],imap_setacl:[\"bool imap_setacl(resource stream_id, string mailbox, string id, string rights)\",\"Sets the ACL for a given mailbox\"],imap_setflag_full:[\"bool imap_setflag_full(resource stream_id, string sequence, string flag [, int options])\",\"Sets flags on messages\"],imap_sort:[\"array imap_sort(resource stream_id, int criteria, int reverse [, int options [, string search_criteria [, string charset]]])\",\"Sort an array of message headers, optionally including only messages that meet specified criteria.\"],imap_status:[\"object imap_status(resource stream_id, string mailbox, int options)\",\"Get status info from a mailbox\"],imap_subscribe:[\"bool imap_subscribe(resource stream_id, string mailbox)\",\"Subscribe to a mailbox\"],imap_thread:[\"array imap_thread(resource stream_id [, int options])\",\"Return threaded by REFERENCES tree\"],imap_timeout:[\"mixed imap_timeout(int timeout_type [, int timeout])\",\"Set or fetch imap timeout\"],imap_uid:[\"int imap_uid(resource stream_id, int msg_no)\",\"Get the unique message id associated with a standard sequential message number\"],imap_undelete:[\"bool imap_undelete(resource stream_id, int msg_no [, int flags])\",\"Remove the delete flag from a message\"],imap_unsubscribe:[\"bool imap_unsubscribe(resource stream_id, string mailbox)\",\"Unsubscribe from a mailbox\"],imap_utf7_decode:[\"string imap_utf7_decode(string buf)\",\"Decode a modified UTF-7 string\"],imap_utf7_encode:[\"string imap_utf7_encode(string buf)\",\"Encode a string in modified UTF-7\"],imap_utf8:[\"string imap_utf8(string mime_encoded_text)\",\"Convert a mime-encoded text to UTF-8\"],imap_utf8_to_mutf7:[\"string imap_utf8_to_mutf7(string in)\",\"Encode a UTF-8 string to modified UTF-7\"],implode:[\"string implode([string glue,] array pieces)\",\"Joins array elements placing glue string between items and return one string\"],import_request_variables:[\"bool import_request_variables(string types [, string prefix])\",\"Import GET/POST/Cookie variables into the global scope\"],in_array:[\"bool in_array(mixed needle, array haystack [, bool strict])\",\"Checks if the given value exists in the array\"],include:[\"bool include(string path)\",\"Includes and evaluates the specified file\"],include_once:[\"bool include_once(string path)\",\"Includes and evaluates the specified file\"],inet_ntop:[\"string inet_ntop(string in_addr)\",\"Converts a packed inet address to a human readable IP address string\"],inet_pton:[\"string inet_pton(string ip_address)\",\"Converts a human readable IP address to a packed binary string\"],ini_get:[\"string ini_get(string varname)\",\"Get a configuration option\"],ini_get_all:[\"array ini_get_all([string extension[, bool details = true]])\",\"Get all configuration options\"],ini_restore:[\"void ini_restore(string varname)\",\"Restore the value of a configuration option specified by varname\"],ini_set:[\"string ini_set(string varname, string newvalue)\",\"Set a configuration option, returns false on error and the old value of the configuration option on success\"],interface_exists:[\"bool interface_exists(string classname [, bool autoload])\",\"Checks if the class exists\"],intl_error_name:[\"string intl_error_name()\",\"* Return a string for a given error code.  * The string will be the same as the name of the error code constant.\"],intl_get_error_code:[\"int intl_get_error_code()\",\"* Get code of the last occured error.\"],intl_get_error_message:[\"string intl_get_error_message()\",\"* Get text description of the last occured error.\"],intl_is_failure:[\"bool intl_is_failure()\",\"* Check whether the given error code indicates a failure.  * Returns true if it does, and false if the code  * indicates success or a warning.\"],intval:[\"int intval(mixed var [, int base])\",\"Get the integer value of a variable using the optional base for the conversion\"],ip2long:[\"int ip2long(string ip_address)\",\"Converts a string containing an (IPv4) Internet Protocol dotted address into a proper address\"],iptcembed:[\"array iptcembed(string iptcdata, string jpeg_file_name [, int spool])\",\"Embed binary IPTC data into a JPEG image.\"],iptcparse:[\"array iptcparse(string iptcdata)\",\"Parse binary IPTC-data into associative array\"],is_a:[\"bool is_a(object object, string class_name)\",\"Returns true if the object is of this class or has this class as one of its parents\"],is_array:[\"bool is_array(mixed var)\",\"Returns true if variable is an array\"],is_bool:[\"bool is_bool(mixed var)\",\"Returns true if variable is a boolean\"],is_callable:[\"bool is_callable(mixed var [, bool syntax_only [, string callable_name]])\",\"Returns true if var is callable.\"],is_dir:[\"bool is_dir(string filename)\",\"Returns true if file is directory\"],is_executable:[\"bool is_executable(string filename)\",\"Returns true if file is executable\"],is_file:[\"bool is_file(string filename)\",\"Returns true if file is a regular file\"],is_finite:[\"bool is_finite(float val)\",\"Returns whether argument is finite\"],is_float:[\"bool is_float(mixed var)\",\"Returns true if variable is float point\"],is_infinite:[\"bool is_infinite(float val)\",\"Returns whether argument is infinite\"],is_link:[\"bool is_link(string filename)\",\"Returns true if file is symbolic link\"],is_long:[\"bool is_long(mixed var)\",\"Returns true if variable is a long (integer)\"],is_nan:[\"bool is_nan(float val)\",\"Returns whether argument is not a number\"],is_null:[\"bool is_null(mixed var)\",\"Returns true if variable is null\"],is_numeric:[\"bool is_numeric(mixed value)\",\"Returns true if value is a number or a numeric string\"],is_object:[\"bool is_object(mixed var)\",\"Returns true if variable is an object\"],is_readable:[\"bool is_readable(string filename)\",\"Returns true if file can be read\"],is_resource:[\"bool is_resource(mixed var)\",\"Returns true if variable is a resource\"],is_scalar:[\"bool is_scalar(mixed value)\",\"Returns true if value is a scalar\"],is_string:[\"bool is_string(mixed var)\",\"Returns true if variable is a string\"],is_subclass_of:[\"bool is_subclass_of(object object, string class_name)\",\"Returns true if the object has this class as one of its parents\"],is_uploaded_file:[\"bool is_uploaded_file(string path)\",\"Check if file was created by rfc1867 upload\"],is_writable:[\"bool is_writable(string filename)\",\"Returns true if file can be written\"],isset:[\"bool isset(mixed var [, mixed var])\",\"Determine whether a variable is set\"],iterator_apply:[\"int iterator_apply(Traversable it, mixed function [, mixed params])\",\"Calls a function for every element in an iterator\"],iterator_count:[\"int iterator_count(Traversable it)\",\"Count the elements in an iterator\"],iterator_to_array:[\"array iterator_to_array(Traversable it [, bool use_keys = true])\",\"Copy the iterator into an array\"],jddayofweek:[\"mixed jddayofweek(int juliandaycount [, int mode])\",\"Returns name or number of day of week from julian day count\"],jdmonthname:[\"string jdmonthname(int juliandaycount, int mode)\",\"Returns name of month for julian day count\"],jdtofrench:[\"string jdtofrench(int juliandaycount)\",\"Converts a julian day count to a french republic calendar date\"],jdtogregorian:[\"string jdtogregorian(int juliandaycount)\",\"Converts a julian day count to a gregorian calendar date\"],jdtojewish:[\"string jdtojewish(int juliandaycount [, bool hebrew [, int fl]])\",\"Converts a julian day count to a jewish calendar date\"],jdtojulian:[\"string jdtojulian(int juliandaycount)\",\"Convert a julian day count to a julian calendar date\"],jdtounix:[\"int jdtounix(int jday)\",\"Convert Julian Day to UNIX timestamp\"],jewishtojd:[\"int jewishtojd(int month, int day, int year)\",\"Converts a jewish calendar date to a julian day count\"],join:[\"string join(array src, string glue)\",\"An alias for implode\"],jpeg2wbmp:[\"bool jpeg2wbmp (string f_org, string f_dest, int d_height, int d_width, int threshold)\",\"Convert JPEG image to WBMP image\"],json_decode:[\"mixed json_decode(string json [, bool assoc [, long depth]])\",\"Decodes the JSON representation into a PHP value\"],json_encode:[\"string json_encode(mixed data [, int options])\",\"Returns the JSON representation of a value\"],json_last_error:[\"int json_last_error()\",\"Returns the error code of the last json_decode().\"],juliantojd:[\"int juliantojd(int month, int day, int year)\",\"Converts a julian calendar date to julian day count\"],key:[\"mixed key(array array_arg)\",\"Return the key of the element currently pointed to by the internal array pointer\"],krsort:[\"bool krsort(array &array_arg [, int sort_flags])\",\"Sort an array by key value in reverse order\"],ksort:[\"bool ksort(array &array_arg [, int sort_flags])\",\"Sort an array by key\"],lcfirst:[\"string lcfirst(string str)\",\"Make a string's first character lowercase\"],lcg_value:[\"float lcg_value()\",\"Returns a value from the combined linear congruential generator\"],lchgrp:[\"bool lchgrp(string filename, mixed group)\",\"Change symlink group\"],ldap_8859_to_t61:[\"string ldap_8859_to_t61(string value)\",\"Translate 8859 characters to t61 characters\"],ldap_add:[\"bool ldap_add(resource link, string dn, array entry)\",\"Add entries to LDAP directory\"],ldap_bind:[\"bool ldap_bind(resource link [, string dn [, string password]])\",\"Bind to LDAP directory\"],ldap_compare:[\"bool ldap_compare(resource link, string dn, string attr, string value)\",\"Determine if an entry has a specific value for one of its attributes\"],ldap_connect:[\"resource ldap_connect([string host [, int port [, string wallet [, string wallet_passwd [, int authmode]]]]])\",\"Connect to an LDAP server\"],ldap_count_entries:[\"int ldap_count_entries(resource link, resource result)\",\"Count the number of entries in a search result\"],ldap_delete:[\"bool ldap_delete(resource link, string dn)\",\"Delete an entry from a directory\"],ldap_dn2ufn:[\"string ldap_dn2ufn(string dn)\",\"Convert DN to User Friendly Naming format\"],ldap_err2str:[\"string ldap_err2str(int errno)\",\"Convert error number to error string\"],ldap_errno:[\"int ldap_errno(resource link)\",\"Get the current ldap error number\"],ldap_error:[\"string ldap_error(resource link)\",\"Get the current ldap error string\"],ldap_explode_dn:[\"array ldap_explode_dn(string dn, int with_attrib)\",\"Splits DN into its component parts\"],ldap_first_attribute:[\"string ldap_first_attribute(resource link, resource result_entry)\",\"Return first attribute\"],ldap_first_entry:[\"resource ldap_first_entry(resource link, resource result)\",\"Return first result id\"],ldap_first_reference:[\"resource ldap_first_reference(resource link, resource result)\",\"Return first reference\"],ldap_free_result:[\"bool ldap_free_result(resource result)\",\"Free result memory\"],ldap_get_attributes:[\"array ldap_get_attributes(resource link, resource result_entry)\",\"Get attributes from a search result entry\"],ldap_get_dn:[\"string ldap_get_dn(resource link, resource result_entry)\",\"Get the DN of a result entry\"],ldap_get_entries:[\"array ldap_get_entries(resource link, resource result)\",\"Get all result entries\"],ldap_get_option:[\"bool ldap_get_option(resource link, int option, mixed retval)\",\"Get the current value of various session-wide parameters\"],ldap_get_values_len:[\"array ldap_get_values_len(resource link, resource result_entry, string attribute)\",\"Get all values with lengths from a result entry\"],ldap_list:[\"resource ldap_list(resource|array link, string base_dn, string filter [, array attrs [, int attrsonly [, int sizelimit [, int timelimit [, int deref]]]]])\",\"Single-level search\"],ldap_mod_add:[\"bool ldap_mod_add(resource link, string dn, array entry)\",\"Add attribute values to current\"],ldap_mod_del:[\"bool ldap_mod_del(resource link, string dn, array entry)\",\"Delete attribute values\"],ldap_mod_replace:[\"bool ldap_mod_replace(resource link, string dn, array entry)\",\"Replace attribute values with new ones\"],ldap_next_attribute:[\"string ldap_next_attribute(resource link, resource result_entry)\",\"Get the next attribute in result\"],ldap_next_entry:[\"resource ldap_next_entry(resource link, resource result_entry)\",\"Get next result entry\"],ldap_next_reference:[\"resource ldap_next_reference(resource link, resource reference_entry)\",\"Get next reference\"],ldap_parse_reference:[\"bool ldap_parse_reference(resource link, resource reference_entry, array referrals)\",\"Extract information from reference entry\"],ldap_parse_result:[\"bool ldap_parse_result(resource link, resource result, int errcode, string matcheddn, string errmsg, array referrals)\",\"Extract information from result\"],ldap_read:[\"resource ldap_read(resource|array link, string base_dn, string filter [, array attrs [, int attrsonly [, int sizelimit [, int timelimit [, int deref]]]]])\",\"Read an entry\"],ldap_rename:[\"bool ldap_rename(resource link, string dn, string newrdn, string newparent, bool deleteoldrdn);\",\"Modify the name of an entry\"],ldap_sasl_bind:[\"bool ldap_sasl_bind(resource link [, string binddn [, string password [, string sasl_mech [, string sasl_realm [, string sasl_authc_id [, string sasl_authz_id [, string props]]]]]]])\",\"Bind to LDAP directory using SASL\"],ldap_search:[\"resource ldap_search(resource|array link, string base_dn, string filter [, array attrs [, int attrsonly [, int sizelimit [, int timelimit [, int deref]]]]])\",\"Search LDAP tree under base_dn\"],ldap_set_option:[\"bool ldap_set_option(resource link, int option, mixed newval)\",\"Set the value of various session-wide parameters\"],ldap_set_rebind_proc:[\"bool ldap_set_rebind_proc(resource link, string callback)\",\"Set a callback function to do re-binds on referral chasing.\"],ldap_sort:[\"bool ldap_sort(resource link, resource result, string sortfilter)\",\"Sort LDAP result entries\"],ldap_start_tls:[\"bool ldap_start_tls(resource link)\",\"Start TLS\"],ldap_t61_to_8859:[\"string ldap_t61_to_8859(string value)\",\"Translate t61 characters to 8859 characters\"],ldap_unbind:[\"bool ldap_unbind(resource link)\",\"Unbind from LDAP directory\"],leak:[\"void leak(int num_bytes=3)\",\"Cause an intentional memory leak, for testing/debugging purposes\"],levenshtein:[\"int levenshtein(string str1, string str2[, int cost_ins, int cost_rep, int cost_del])\",\"Calculate Levenshtein distance between two strings\"],libxml_clear_errors:[\"void libxml_clear_errors()\",\"Clear last error from libxml\"],libxml_disable_entity_loader:[\"bool libxml_disable_entity_loader([boolean disable])\",\"Disable/Enable ability to load external entities\"],libxml_get_errors:[\"object libxml_get_errors()\",\"Retrieve array of errors\"],libxml_get_last_error:[\"object libxml_get_last_error()\",\"Retrieve last error from libxml\"],libxml_set_streams_context:[\"void libxml_set_streams_context(resource streams_context)\",\"Set the streams context for the next libxml document load or write\"],libxml_use_internal_errors:[\"bool libxml_use_internal_errors([boolean use_errors])\",\"Disable libxml errors and allow user to fetch error information as needed\"],link:[\"int link(string target, string link)\",\"Create a hard link\"],linkinfo:[\"int linkinfo(string filename)\",\"Returns the st_dev field of the UNIX C stat structure describing the link\"],litespeed_request_headers:[\"array litespeed_request_headers(void)\",\"Fetch all HTTP request headers\"],litespeed_response_headers:[\"array litespeed_response_headers(void)\",\"Fetch all HTTP response headers\"],locale_accept_from_http:[\"string locale_accept_from_http(string $http_accept)\",null],locale_canonicalize:[\"static string locale_canonicalize(Locale $loc, string $locale)\",\"* @param string $locale The locale string to canonicalize\"],locale_filter_matches:[\"boolean locale_filter_matches(string $langtag, string $locale[, bool $canonicalize])\",\"* Checks if a $langtag filter matches with $locale according to RFC 4647's basic filtering algorithm\"],locale_get_all_variants:[\"static array locale_get_all_variants($locale)\",\"* gets an array containing the list of variants, or null\"],locale_get_default:[\"static string locale_get_default( )\",\"Get default locale\"],locale_get_keywords:[\"static array locale_get_keywords(string $locale) {\",\"* return an associative array containing keyword-value  * pairs for this locale. The keys are keys to the array (doh!)\"],locale_get_primary_language:[\"static string locale_get_primary_language($locale)\",\"* gets the primary language for the $locale\"],locale_get_region:[\"static string locale_get_region($locale)\",\"* gets the region for the $locale\"],locale_get_script:[\"static string locale_get_script($locale)\",\"* gets the script for the $locale\"],locale_lookup:[\"string locale_lookup(array $langtag, string $locale[, bool $canonicalize[, string $default = null]])\",\"* Searchs the items in $langtag for the best match to the language * range\"],locale_set_default:[\"static string locale_set_default( string $locale )\",\"Set default locale\"],localeconv:[\"array localeconv(void)\",\"Returns numeric formatting information based on the current locale\"],localtime:[\"array localtime([int timestamp [, bool associative_array]])\",\"Returns the results of the C system call localtime as an associative array if the associative_array argument is set to 1 other wise it is a regular array\"],log:[\"float log(float number, [float base])\",\"Returns the natural logarithm of the number, or the base log if base is specified\"],log10:[\"float log10(float number)\",\"Returns the base-10 logarithm of the number\"],log1p:[\"float log1p(float number)\",\"Returns log(1 + number), computed in a way that accurate even when the value of number is close to zero\"],long2ip:[\"string long2ip(int proper_address)\",\"Converts an (IPv4) Internet network address into a string in Internet standard dotted format\"],lstat:[\"array lstat(string filename)\",\"Give information about a file or symbolic link\"],ltrim:[\"string ltrim(string str [, string character_mask])\",\"Strips whitespace from the beginning of a string\"],mail:[\"int mail(string to, string subject, string message [, string additional_headers [, string additional_parameters]])\",\"Send an email message\"],max:[\"mixed max(mixed arg1 [, mixed arg2 [, mixed ...]])\",\"Return the highest value in an array or a series of arguments\"],mb_check_encoding:[\"bool mb_check_encoding([string var[, string encoding]])\",\"Check if the string is valid for the specified encoding\"],mb_convert_case:[\"string mb_convert_case(string sourcestring, int mode [, string encoding])\",\"Returns a case-folded version of sourcestring\"],mb_convert_encoding:[\"string mb_convert_encoding(string str, string to-encoding [, mixed from-encoding])\",\"Returns converted string in desired encoding\"],mb_convert_kana:[\"string mb_convert_kana(string str [, string option] [, string encoding])\",\"Conversion between full-width character and half-width character (Japanese)\"],mb_convert_variables:[\"string mb_convert_variables(string to-encoding, mixed from-encoding, mixed vars [, ...])\",\"Converts the string resource in variables to desired encoding\"],mb_decode_mimeheader:[\"string mb_decode_mimeheader(string string)\",'Decodes the MIME \"encoded-word\" in the string'],mb_decode_numericentity:[\"string mb_decode_numericentity(string string, array convmap [, string encoding])\",\"Converts HTML numeric entities to character code\"],mb_detect_encoding:[\"string mb_detect_encoding(string str [, mixed encoding_list [, bool strict]])\",\"Encodings of the given string is returned (as a string)\"],mb_detect_order:[\"bool|array mb_detect_order([mixed encoding-list])\",\"Sets the current detect_order or Return the current detect_order as a array\"],mb_encode_mimeheader:[\"string mb_encode_mimeheader(string str [, string charset [, string transfer-encoding [, string linefeed [, int indent]]]])\",'Converts the string to MIME \"encoded-word\" in the format of =?charset?(B|Q)?encoded_string?='],mb_encode_numericentity:[\"string mb_encode_numericentity(string string, array convmap [, string encoding])\",\"Converts specified characters to HTML numeric entities\"],mb_encoding_aliases:[\"array mb_encoding_aliases(string encoding)\",\"Returns an array of the aliases of a given encoding name\"],mb_ereg:[\"int mb_ereg(string pattern, string string [, array registers])\",\"Regular expression match for multibyte string\"],mb_ereg_match:[\"bool mb_ereg_match(string pattern, string string [,string option])\",\"Regular expression match for multibyte string\"],mb_ereg_replace:[\"string mb_ereg_replace(string pattern, string replacement, string string [, string option])\",\"Replace regular expression for multibyte string\"],mb_ereg_search:[\"bool mb_ereg_search([string pattern[, string option]])\",\"Regular expression search for multibyte string\"],mb_ereg_search_getpos:[\"int mb_ereg_search_getpos(void)\",\"Get search start position\"],mb_ereg_search_getregs:[\"array mb_ereg_search_getregs(void)\",\"Get matched substring of the last time\"],mb_ereg_search_init:[\"bool mb_ereg_search_init(string string [, string pattern[, string option]])\",\"Initialize string and regular expression for search.\"],mb_ereg_search_pos:[\"array mb_ereg_search_pos([string pattern[, string option]])\",\"Regular expression search for multibyte string\"],mb_ereg_search_regs:[\"array mb_ereg_search_regs([string pattern[, string option]])\",\"Regular expression search for multibyte string\"],mb_ereg_search_setpos:[\"bool mb_ereg_search_setpos(int position)\",\"Set search start position\"],mb_eregi:[\"int mb_eregi(string pattern, string string [, array registers])\",\"Case-insensitive regular expression match for multibyte string\"],mb_eregi_replace:[\"string mb_eregi_replace(string pattern, string replacement, string string)\",\"Case insensitive replace regular expression for multibyte string\"],mb_get_info:[\"mixed mb_get_info([string type])\",\"Returns the current settings of mbstring\"],mb_http_input:[\"mixed mb_http_input([string type])\",\"Returns the input encoding\"],mb_http_output:[\"string mb_http_output([string encoding])\",\"Sets the current output_encoding or returns the current output_encoding as a string\"],mb_internal_encoding:[\"string mb_internal_encoding([string encoding])\",\"Sets the current internal encoding or Returns the current internal encoding as a string\"],mb_language:[\"string mb_language([string language])\",\"Sets the current language or Returns the current language as a string\"],mb_list_encodings:[\"mixed mb_list_encodings()\",\"Returns an array of all supported entity encodings\"],mb_output_handler:[\"string mb_output_handler(string contents, int status)\",\"Returns string in output buffer converted to the http_output encoding\"],mb_parse_str:[\"bool mb_parse_str(string encoded_string [, array result])\",\"Parses GET/POST/COOKIE data and sets global variables\"],mb_preferred_mime_name:[\"string mb_preferred_mime_name(string encoding)\",\"Return the preferred MIME name (charset) as a string\"],mb_regex_encoding:[\"string mb_regex_encoding([string encoding])\",\"Returns the current encoding for regex as a string.\"],mb_regex_set_options:[\"string mb_regex_set_options([string options])\",\"Set or get the default options for mbregex functions\"],mb_send_mail:[\"int mb_send_mail(string to, string subject, string message [, string additional_headers [, string additional_parameters]])\",\"*  Sends an email message with MIME scheme\"],mb_split:[\"array mb_split(string pattern, string string [, int limit])\",\"split multibyte string into array by regular expression\"],mb_strcut:[\"string mb_strcut(string str, int start [, int length [, string encoding]])\",\"Returns part of a string\"],mb_strimwidth:[\"string mb_strimwidth(string str, int start, int width [, string trimmarker [, string encoding]])\",\"Trim the string in terminal width\"],mb_stripos:[\"int mb_stripos(string haystack, string needle [, int offset [, string encoding]])\",\"Finds position of first occurrence of a string within another, case insensitive\"],mb_stristr:[\"string mb_stristr(string haystack, string needle[, bool part[, string encoding]])\",\"Finds first occurrence of a string within another, case insensitive\"],mb_strlen:[\"int mb_strlen(string str [, string encoding])\",\"Get character numbers of a string\"],mb_strpos:[\"int mb_strpos(string haystack, string needle [, int offset [, string encoding]])\",\"Find position of first occurrence of a string within another\"],mb_strrchr:[\"string mb_strrchr(string haystack, string needle[, bool part[, string encoding]])\",\"Finds the last occurrence of a character in a string within another\"],mb_strrichr:[\"string mb_strrichr(string haystack, string needle[, bool part[, string encoding]])\",\"Finds the last occurrence of a character in a string within another, case insensitive\"],mb_strripos:[\"int mb_strripos(string haystack, string needle [, int offset [, string encoding]])\",\"Finds position of last occurrence of a string within another, case insensitive\"],mb_strrpos:[\"int mb_strrpos(string haystack, string needle [, int offset [, string encoding]])\",\"Find position of last occurrence of a string within another\"],mb_strstr:[\"string mb_strstr(string haystack, string needle[, bool part[, string encoding]])\",\"Finds first occurrence of a string within another\"],mb_strtolower:[\"string mb_strtolower(string sourcestring [, string encoding])\",\"*  Returns a lowercased version of sourcestring\"],mb_strtoupper:[\"string mb_strtoupper(string sourcestring [, string encoding])\",\"*  Returns a uppercased version of sourcestring\"],mb_strwidth:[\"int mb_strwidth(string str [, string encoding])\",\"Gets terminal width of a string\"],mb_substitute_character:[\"mixed mb_substitute_character([mixed substchar])\",\"Sets the current substitute_character or returns the current substitute_character\"],mb_substr:[\"string mb_substr(string str, int start [, int length [, string encoding]])\",\"Returns part of a string\"],mb_substr_count:[\"int mb_substr_count(string haystack, string needle [, string encoding])\",\"Count the number of substring occurrences\"],mcrypt_cbc:[\"string mcrypt_cbc(int cipher, string key, string data, int mode, string iv)\",\"CBC crypt/decrypt data using key key with cipher cipher starting with iv\"],mcrypt_cfb:[\"string mcrypt_cfb(int cipher, string key, string data, int mode, string iv)\",\"CFB crypt/decrypt data using key key with cipher cipher starting with iv\"],mcrypt_create_iv:[\"string mcrypt_create_iv(int size, int source)\",\"Create an initialization vector (IV)\"],mcrypt_decrypt:[\"string mcrypt_decrypt(string cipher, string key, string data, string mode, string iv)\",\"OFB crypt/decrypt data using key key with cipher cipher starting with iv\"],mcrypt_ecb:[\"string mcrypt_ecb(int cipher, string key, string data, int mode, string iv)\",\"ECB crypt/decrypt data using key key with cipher cipher starting with iv\"],mcrypt_enc_get_algorithms_name:[\"string mcrypt_enc_get_algorithms_name(resource td)\",\"Returns the name of the algorithm specified by the descriptor td\"],mcrypt_enc_get_block_size:[\"int mcrypt_enc_get_block_size(resource td)\",\"Returns the block size of the cipher specified by the descriptor td\"],mcrypt_enc_get_iv_size:[\"int mcrypt_enc_get_iv_size(resource td)\",\"Returns the size of the IV in bytes of the algorithm specified by the descriptor td\"],mcrypt_enc_get_key_size:[\"int mcrypt_enc_get_key_size(resource td)\",\"Returns the maximum supported key size in bytes of the algorithm specified by the descriptor td\"],mcrypt_enc_get_modes_name:[\"string mcrypt_enc_get_modes_name(resource td)\",\"Returns the name of the mode specified by the descriptor td\"],mcrypt_enc_get_supported_key_sizes:[\"array mcrypt_enc_get_supported_key_sizes(resource td)\",\"This function decrypts the crypttext\"],mcrypt_enc_is_block_algorithm:[\"bool mcrypt_enc_is_block_algorithm(resource td)\",\"Returns TRUE if the alrogithm is a block algorithms\"],mcrypt_enc_is_block_algorithm_mode:[\"bool mcrypt_enc_is_block_algorithm_mode(resource td)\",\"Returns TRUE if the mode is for use with block algorithms\"],mcrypt_enc_is_block_mode:[\"bool mcrypt_enc_is_block_mode(resource td)\",\"Returns TRUE if the mode outputs blocks\"],mcrypt_enc_self_test:[\"int mcrypt_enc_self_test(resource td)\",\"This function runs the self test on the algorithm specified by the descriptor td\"],mcrypt_encrypt:[\"string mcrypt_encrypt(string cipher, string key, string data, string mode, string iv)\",\"OFB crypt/decrypt data using key key with cipher cipher starting with iv\"],mcrypt_generic:[\"string mcrypt_generic(resource td, string data)\",\"This function encrypts the plaintext\"],mcrypt_generic_deinit:[\"bool mcrypt_generic_deinit(resource td)\",\"This function terminates encrypt specified by the descriptor td\"],mcrypt_generic_init:[\"int mcrypt_generic_init(resource td, string key, string iv)\",\"This function initializes all buffers for the specific module\"],mcrypt_get_block_size:[\"int mcrypt_get_block_size(string cipher, string module)\",\"Get the key size of cipher\"],mcrypt_get_cipher_name:[\"string mcrypt_get_cipher_name(string cipher)\",\"Get the key size of cipher\"],mcrypt_get_iv_size:[\"int mcrypt_get_iv_size(string cipher, string module)\",\"Get the IV size of cipher (Usually the same as the blocksize)\"],mcrypt_get_key_size:[\"int mcrypt_get_key_size(string cipher, string module)\",\"Get the key size of cipher\"],mcrypt_list_algorithms:[\"array mcrypt_list_algorithms([string lib_dir])\",'List all algorithms in \"module_dir\"'],mcrypt_list_modes:[\"array mcrypt_list_modes([string lib_dir])\",'List all modes \"module_dir\"'],mcrypt_module_close:[\"bool mcrypt_module_close(resource td)\",\"Free the descriptor td\"],mcrypt_module_get_algo_block_size:[\"int mcrypt_module_get_algo_block_size(string algorithm [, string lib_dir])\",\"Returns the block size of the algorithm\"],mcrypt_module_get_algo_key_size:[\"int mcrypt_module_get_algo_key_size(string algorithm [, string lib_dir])\",\"Returns the maximum supported key size of the algorithm\"],mcrypt_module_get_supported_key_sizes:[\"array mcrypt_module_get_supported_key_sizes(string algorithm [, string lib_dir])\",\"This function decrypts the crypttext\"],mcrypt_module_is_block_algorithm:[\"bool mcrypt_module_is_block_algorithm(string algorithm [, string lib_dir])\",\"Returns TRUE if the algorithm is a block algorithm\"],mcrypt_module_is_block_algorithm_mode:[\"bool mcrypt_module_is_block_algorithm_mode(string mode [, string lib_dir])\",\"Returns TRUE if the mode is for use with block algorithms\"],mcrypt_module_is_block_mode:[\"bool mcrypt_module_is_block_mode(string mode [, string lib_dir])\",\"Returns TRUE if the mode outputs blocks of bytes\"],mcrypt_module_open:[\"resource mcrypt_module_open(string cipher, string cipher_directory, string mode, string mode_directory)\",\"Opens the module of the algorithm and the mode to be used\"],mcrypt_module_self_test:[\"bool mcrypt_module_self_test(string algorithm [, string lib_dir])\",'Does a self test of the module \"module\"'],mcrypt_ofb:[\"string mcrypt_ofb(int cipher, string key, string data, int mode, string iv)\",\"OFB crypt/decrypt data using key key with cipher cipher starting with iv\"],md5:[\"string md5(string str, [ bool raw_output])\",\"Calculate the md5 hash of a string\"],md5_file:[\"string md5_file(string filename [, bool raw_output])\",\"Calculate the md5 hash of given filename\"],mdecrypt_generic:[\"string mdecrypt_generic(resource td, string data)\",\"This function decrypts the plaintext\"],memory_get_peak_usage:[\"int memory_get_peak_usage([real_usage])\",\"Returns the peak allocated by PHP memory\"],memory_get_usage:[\"int memory_get_usage([real_usage])\",\"Returns the allocated by PHP memory\"],metaphone:[\"string metaphone(string text[, int phones])\",\"Break english phrases down into their phonemes\"],method_exists:[\"bool method_exists(object object, string method)\",\"Checks if the class method exists\"],mhash:[\"string mhash(int hash, string data [, string key])\",\"Hash data with hash\"],mhash_count:[\"int mhash_count(void)\",\"Gets the number of available hashes\"],mhash_get_block_size:[\"int mhash_get_block_size(int hash)\",\"Gets the block size of hash\"],mhash_get_hash_name:[\"string mhash_get_hash_name(int hash)\",\"Gets the name of hash\"],mhash_keygen_s2k:[\"string mhash_keygen_s2k(int hash, string input_password, string salt, int bytes)\",\"Generates a key using hash functions\"],microtime:[\"mixed microtime([bool get_as_float])\",\"Returns either a string or a float containing the current time in seconds and microseconds\"],mime_content_type:[\"string mime_content_type(string filename|resource stream)\",\"Return content-type for file\"],min:[\"mixed min(mixed arg1 [, mixed arg2 [, mixed ...]])\",\"Return the lowest value in an array or a series of arguments\"],mkdir:[\"bool mkdir(string pathname [, int mode [, bool recursive [, resource context]]])\",\"Create a directory\"],mktime:[\"int mktime([int hour [, int min [, int sec [, int mon [, int day [, int year]]]]]])\",\"Get UNIX timestamp for a date\"],money_format:[\"string money_format(string format , float value)\",\"Convert monetary value(s) to string\"],move_uploaded_file:[\"bool move_uploaded_file(string path, string new_path)\",\"Move a file if and only if it was created by an upload\"],msg_get_queue:[\"resource msg_get_queue(int key [, int perms])\",\"Attach to a message queue\"],msg_queue_exists:[\"bool msg_queue_exists(int key)\",\"Check wether a message queue exists\"],msg_receive:[\"mixed msg_receive(resource queue, int desiredmsgtype, int &msgtype, int maxsize, mixed message [, bool unserialize=true [, int flags=0 [, int errorcode]]])\",\"Send a message of type msgtype (must be > 0) to a message queue\"],msg_remove_queue:[\"bool msg_remove_queue(resource queue)\",\"Destroy the queue\"],msg_send:[\"bool msg_send(resource queue, int msgtype, mixed message [, bool serialize=true [, bool blocking=true [, int errorcode]]])\",\"Send a message of type msgtype (must be > 0) to a message queue\"],msg_set_queue:[\"bool msg_set_queue(resource queue, array data)\",\"Set information for a message queue\"],msg_stat_queue:[\"array msg_stat_queue(resource queue)\",\"Returns information about a message queue\"],msgfmt_create:[\"MessageFormatter msgfmt_create( string $locale, string $pattern )\",\"* Create formatter.\"],msgfmt_format:[\"mixed msgfmt_format( MessageFormatter $nf, array $args )\",\"* Format a message.\"],msgfmt_format_message:[\"mixed msgfmt_format_message( string $locale, string $pattern, array $args )\",\"* Format a message.\"],msgfmt_get_error_code:[\"int msgfmt_get_error_code( MessageFormatter $nf )\",\"* Get formatter's last error code.\"],msgfmt_get_error_message:[\"string msgfmt_get_error_message( MessageFormatter $coll )\",\"* Get text description for formatter's last error code.\"],msgfmt_get_locale:[\"string msgfmt_get_locale(MessageFormatter $mf)\",\"* Get formatter locale.\"],msgfmt_get_pattern:[\"string msgfmt_get_pattern( MessageFormatter $mf )\",\"* Get formatter pattern.\"],msgfmt_parse:[\"array msgfmt_parse( MessageFormatter $nf, string $source )\",\"* Parse a message.\"],msgfmt_set_pattern:[\"bool msgfmt_set_pattern( MessageFormatter $mf, string $pattern )\",\"* Set formatter pattern.\"],mssql_bind:[\"bool mssql_bind(resource stmt, string param_name, mixed var, int type [, bool is_output [, bool is_null [, int maxlen]]])\",\"Adds a parameter to a stored procedure or a remote stored procedure\"],mssql_close:[\"bool mssql_close([resource conn_id])\",\"Closes a connection to a MS-SQL server\"],mssql_connect:[\"int mssql_connect([string servername [, string username [, string password [, bool new_link]]]])\",\"Establishes a connection to a MS-SQL server\"],mssql_data_seek:[\"bool mssql_data_seek(resource result_id, int offset)\",\"Moves the internal row pointer of the MS-SQL result associated with the specified result identifier to pointer to the specified row number\"],mssql_execute:[\"mixed mssql_execute(resource stmt [, bool skip_results = false])\",\"Executes a stored procedure on a MS-SQL server database\"],mssql_fetch_array:[\"array mssql_fetch_array(resource result_id [, int result_type])\",\"Returns an associative array of the current row in the result set specified by result_id\"],mssql_fetch_assoc:[\"array mssql_fetch_assoc(resource result_id)\",\"Returns an associative array of the current row in the result set specified by result_id\"],mssql_fetch_batch:[\"int mssql_fetch_batch(resource result_index)\",\"Returns the next batch of records\"],mssql_fetch_field:[\"object mssql_fetch_field(resource result_id [, int offset])\",\"Gets information about certain fields in a query result\"],mssql_fetch_object:[\"object mssql_fetch_object(resource result_id)\",\"Returns a pseudo-object of the current row in the result set specified by result_id\"],mssql_fetch_row:[\"array mssql_fetch_row(resource result_id)\",\"Returns an array of the current row in the result set specified by result_id\"],mssql_field_length:[\"int mssql_field_length(resource result_id [, int offset])\",\"Get the length of a MS-SQL field\"],mssql_field_name:[\"string mssql_field_name(resource result_id [, int offset])\",\"Returns the name of the field given by offset in the result set given by result_id\"],mssql_field_seek:[\"bool mssql_field_seek(resource result_id, int offset)\",\"Seeks to the specified field offset\"],mssql_field_type:[\"string mssql_field_type(resource result_id [, int offset])\",\"Returns the type of a field\"],mssql_free_result:[\"bool mssql_free_result(resource result_index)\",\"Free a MS-SQL result index\"],mssql_free_statement:[\"bool mssql_free_statement(resource result_index)\",\"Free a MS-SQL statement index\"],mssql_get_last_message:[\"string mssql_get_last_message(void)\",\"Gets the last message from the MS-SQL server\"],mssql_guid_string:[\"string mssql_guid_string(string binary [,bool short_format])\",\"Converts a 16 byte binary GUID to a string\"],mssql_init:[\"int mssql_init(string sp_name [, resource conn_id])\",\"Initializes a stored procedure or a remote stored procedure\"],mssql_min_error_severity:[\"void mssql_min_error_severity(int severity)\",\"Sets the lower error severity\"],mssql_min_message_severity:[\"void mssql_min_message_severity(int severity)\",\"Sets the lower message severity\"],mssql_next_result:[\"bool mssql_next_result(resource result_id)\",\"Move the internal result pointer to the next result\"],mssql_num_fields:[\"int mssql_num_fields(resource mssql_result_index)\",\"Returns the number of fields fetched in from the result id specified\"],mssql_num_rows:[\"int mssql_num_rows(resource mssql_result_index)\",\"Returns the number of rows fetched in from the result id specified\"],mssql_pconnect:[\"int mssql_pconnect([string servername [, string username [, string password [, bool new_link]]]])\",\"Establishes a persistent connection to a MS-SQL server\"],mssql_query:[\"resource mssql_query(string query [, resource conn_id [, int batch_size]])\",\"Perform an SQL query on a MS-SQL server database\"],mssql_result:[\"string mssql_result(resource result_id, int row, mixed field)\",\"Returns the contents of one cell from a MS-SQL result set\"],mssql_rows_affected:[\"int mssql_rows_affected(resource conn_id)\",\"Returns the number of records affected by the query\"],mssql_select_db:[\"bool mssql_select_db(string database_name [, resource conn_id])\",\"Select a MS-SQL database\"],mt_getrandmax:[\"int mt_getrandmax(void)\",\"Returns the maximum value a random number from Mersenne Twister can have\"],mt_rand:[\"int mt_rand([int min, int max])\",\"Returns a random number from Mersenne Twister\"],mt_srand:[\"void mt_srand([int seed])\",\"Seeds Mersenne Twister random number generator\"],mysql_affected_rows:[\"int mysql_affected_rows([int link_identifier])\",\"Gets number of affected rows in previous MySQL operation\"],mysql_client_encoding:[\"string mysql_client_encoding([int link_identifier])\",\"Returns the default character set for the current connection\"],mysql_close:[\"bool mysql_close([int link_identifier])\",\"Close a MySQL connection\"],mysql_connect:[\"resource mysql_connect([string hostname[:port][:/path/to/socket] [, string username [, string password [, bool new [, int flags]]]]])\",\"Opens a connection to a MySQL Server\"],mysql_create_db:[\"bool mysql_create_db(string database_name [, int link_identifier])\",\"Create a MySQL database\"],mysql_data_seek:[\"bool mysql_data_seek(resource result, int row_number)\",\"Move internal result pointer\"],mysql_db_query:[\"resource mysql_db_query(string database_name, string query [, int link_identifier])\",\"Sends an SQL query to MySQL\"],mysql_drop_db:[\"bool mysql_drop_db(string database_name [, int link_identifier])\",\"Drops (delete) a MySQL database\"],mysql_errno:[\"int mysql_errno([int link_identifier])\",\"Returns the number of the error message from previous MySQL operation\"],mysql_error:[\"string mysql_error([int link_identifier])\",\"Returns the text of the error message from previous MySQL operation\"],mysql_escape_string:[\"string mysql_escape_string(string to_be_escaped)\",\"Escape string for mysql query\"],mysql_fetch_array:[\"array mysql_fetch_array(resource result [, int result_type])\",\"Fetch a result row as an array (associative, numeric or both)\"],mysql_fetch_assoc:[\"array mysql_fetch_assoc(resource result)\",\"Fetch a result row as an associative array\"],mysql_fetch_field:[\"object mysql_fetch_field(resource result [, int field_offset])\",\"Gets column information from a result and return as an object\"],mysql_fetch_lengths:[\"array mysql_fetch_lengths(resource result)\",\"Gets max data size of each column in a result\"],mysql_fetch_object:[\"object mysql_fetch_object(resource result [, string class_name [, NULL|array ctor_params]])\",\"Fetch a result row as an object\"],mysql_fetch_row:[\"array mysql_fetch_row(resource result)\",\"Gets a result row as an enumerated array\"],mysql_field_flags:[\"string mysql_field_flags(resource result, int field_offset)\",\"Gets the flags associated with the specified field in a result\"],mysql_field_len:[\"int mysql_field_len(resource result, int field_offset)\",\"Returns the length of the specified field\"],mysql_field_name:[\"string mysql_field_name(resource result, int field_index)\",\"Gets the name of the specified field in a result\"],mysql_field_seek:[\"bool mysql_field_seek(resource result, int field_offset)\",\"Sets result pointer to a specific field offset\"],mysql_field_table:[\"string mysql_field_table(resource result, int field_offset)\",\"Gets name of the table the specified field is in\"],mysql_field_type:[\"string mysql_field_type(resource result, int field_offset)\",\"Gets the type of the specified field in a result\"],mysql_free_result:[\"bool mysql_free_result(resource result)\",\"Free result memory\"],mysql_get_client_info:[\"string mysql_get_client_info(void)\",\"Returns a string that represents the client library version\"],mysql_get_host_info:[\"string mysql_get_host_info([int link_identifier])\",\"Returns a string describing the type of connection in use, including the server host name\"],mysql_get_proto_info:[\"int mysql_get_proto_info([int link_identifier])\",\"Returns the protocol version used by current connection\"],mysql_get_server_info:[\"string mysql_get_server_info([int link_identifier])\",\"Returns a string that represents the server version number\"],mysql_info:[\"string mysql_info([int link_identifier])\",\"Returns a string containing information about the most recent query\"],mysql_insert_id:[\"int mysql_insert_id([int link_identifier])\",\"Gets the ID generated from the previous INSERT operation\"],mysql_list_dbs:[\"resource mysql_list_dbs([int link_identifier])\",\"List databases available on a MySQL server\"],mysql_list_fields:[\"resource mysql_list_fields(string database_name, string table_name [, int link_identifier])\",\"List MySQL result fields\"],mysql_list_processes:[\"resource mysql_list_processes([int link_identifier])\",\"Returns a result set describing the current server threads\"],mysql_list_tables:[\"resource mysql_list_tables(string database_name [, int link_identifier])\",\"List tables in a MySQL database\"],mysql_num_fields:[\"int mysql_num_fields(resource result)\",\"Gets number of fields in a result\"],mysql_num_rows:[\"int mysql_num_rows(resource result)\",\"Gets number of rows in a result\"],mysql_pconnect:[\"resource mysql_pconnect([string hostname[:port][:/path/to/socket] [, string username [, string password [, int flags]]]])\",\"Opens a persistent connection to a MySQL Server\"],mysql_ping:[\"bool mysql_ping([int link_identifier])\",\"Ping a server connection. If no connection then reconnect.\"],mysql_query:[\"resource mysql_query(string query [, int link_identifier])\",\"Sends an SQL query to MySQL\"],mysql_real_escape_string:[\"string mysql_real_escape_string(string to_be_escaped [, int link_identifier])\",\"Escape special characters in a string for use in a SQL statement, taking into account the current charset of the connection\"],mysql_result:[\"mixed mysql_result(resource result, int row [, mixed field])\",\"Gets result data\"],mysql_select_db:[\"bool mysql_select_db(string database_name [, int link_identifier])\",\"Selects a MySQL database\"],mysql_set_charset:[\"bool mysql_set_charset(string csname [, int link_identifier])\",\"sets client character set\"],mysql_stat:[\"string mysql_stat([int link_identifier])\",\"Returns a string containing status information\"],mysql_thread_id:[\"int mysql_thread_id([int link_identifier])\",\"Returns the thread id of current connection\"],mysql_unbuffered_query:[\"resource mysql_unbuffered_query(string query [, int link_identifier])\",\"Sends an SQL query to MySQL, without fetching and buffering the result rows\"],mysqli_affected_rows:[\"mixed mysqli_affected_rows(object link)\",\"Get number of affected rows in previous MySQL operation\"],mysqli_autocommit:[\"bool mysqli_autocommit(object link, bool mode)\",\"Turn auto commit on or of\"],mysqli_cache_stats:[\"array mysqli_cache_stats(void)\",\"Returns statistics about the zval cache\"],mysqli_change_user:[\"bool mysqli_change_user(object link, string user, string password, string database)\",\"Change logged-in user of the active connection\"],mysqli_character_set_name:[\"string mysqli_character_set_name(object link)\",\"Returns the name of the character set used for this connection\"],mysqli_close:[\"bool mysqli_close(object link)\",\"Close connection\"],mysqli_commit:[\"bool mysqli_commit(object link)\",\"Commit outstanding actions and close transaction\"],mysqli_connect:[\"object mysqli_connect([string hostname [,string username [,string passwd [,string dbname [,int port [,string socket]]]]]])\",\"Open a connection to a mysql server\"],mysqli_connect_errno:[\"int mysqli_connect_errno(void)\",\"Returns the numerical value of the error message from last connect command\"],mysqli_connect_error:[\"string mysqli_connect_error(void)\",\"Returns the text of the error message from previous MySQL operation\"],mysqli_data_seek:[\"bool mysqli_data_seek(object result, int offset)\",\"Move internal result pointer\"],mysqli_debug:[\"void mysqli_debug(string debug)\",\"\"],mysqli_dump_debug_info:[\"bool mysqli_dump_debug_info(object link)\",\"\"],mysqli_embedded_server_end:[\"void mysqli_embedded_server_end(void)\",\"\"],mysqli_embedded_server_start:[\"bool mysqli_embedded_server_start(bool start, array arguments, array groups)\",\"initialize and start embedded server\"],mysqli_errno:[\"int mysqli_errno(object link)\",\"Returns the numerical value of the error message from previous MySQL operation\"],mysqli_error:[\"string mysqli_error(object link)\",\"Returns the text of the error message from previous MySQL operation\"],mysqli_fetch_all:[\"mixed mysqli_fetch_all (object result [,int resulttype])\",\"Fetches all result rows as an associative array, a numeric array, or both\"],mysqli_fetch_array:[\"mixed mysqli_fetch_array (object result [,int resulttype])\",\"Fetch a result row as an associative array, a numeric array, or both\"],mysqli_fetch_assoc:[\"mixed mysqli_fetch_assoc (object result)\",\"Fetch a result row as an associative array\"],mysqli_fetch_field:[\"mixed mysqli_fetch_field (object result)\",\"Get column information from a result and return as an object\"],mysqli_fetch_field_direct:[\"mixed mysqli_fetch_field_direct (object result, int offset)\",\"Fetch meta-data for a single field\"],mysqli_fetch_fields:[\"mixed mysqli_fetch_fields (object result)\",\"Return array of objects containing field meta-data\"],mysqli_fetch_lengths:[\"mixed mysqli_fetch_lengths (object result)\",\"Get the length of each output in a result\"],mysqli_fetch_object:[\"mixed mysqli_fetch_object (object result [, string class_name [, NULL|array ctor_params]])\",\"Fetch a result row as an object\"],mysqli_fetch_row:[\"array mysqli_fetch_row (object result)\",\"Get a result row as an enumerated array\"],mysqli_field_count:[\"int mysqli_field_count(object link)\",\"Fetch the number of fields returned by the last query for the given link\"],mysqli_field_seek:[\"int mysqli_field_seek(object result, int fieldnr)\",\"Set result pointer to a specified field offset\"],mysqli_field_tell:[\"int mysqli_field_tell(object result)\",\"Get current field offset of result pointer\"],mysqli_free_result:[\"void mysqli_free_result(object result)\",\"Free query result memory for the given result handle\"],mysqli_get_charset:[\"object mysqli_get_charset(object link)\",\"returns a character set object\"],mysqli_get_client_info:[\"string mysqli_get_client_info(void)\",\"Get MySQL client info\"],mysqli_get_client_stats:[\"array mysqli_get_client_stats(void)\",\"Returns statistics about the zval cache\"],mysqli_get_client_version:[\"int mysqli_get_client_version(void)\",\"Get MySQL client info\"],mysqli_get_connection_stats:[\"array mysqli_get_connection_stats(void)\",\"Returns statistics about the zval cache\"],mysqli_get_host_info:[\"string mysqli_get_host_info (object link)\",\"Get MySQL host info\"],mysqli_get_proto_info:[\"int mysqli_get_proto_info(object link)\",\"Get MySQL protocol information\"],mysqli_get_server_info:[\"string mysqli_get_server_info(object link)\",\"Get MySQL server info\"],mysqli_get_server_version:[\"int mysqli_get_server_version(object link)\",\"Return the MySQL version for the server referenced by the given link\"],mysqli_get_warnings:[\"object mysqli_get_warnings(object link) */\",'PHP_FUNCTION(mysqli_get_warnings) {  MY_MYSQL   *mysql;  zval    *mysql_link;  MYSQLI_RESOURCE  *mysqli_resource;  MYSQLI_WARNING  *w;   if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), \"O\", &mysql_link, mysqli_link_class_entry) == FAILURE) {   return;  }  MYSQLI_FETCH_RESOURCE(mysql, MY_MYSQL*, &mysql_link, \"mysqli_link\", MYSQLI_STATUS_VALID);   if (mysql_warning_count(mysql->mysql)) {   w = php_get_warnings(mysql->mysql TSRMLS_CC);   } else {   RETURN_FALSE;  }  mysqli_resource = (MYSQLI_RESOURCE *)ecalloc (1, sizeof(MYSQLI_RESOURCE));  mysqli_resource->ptr = mysqli_resource->info = (void *)w;  mysqli_resource->status = MYSQLI_STATUS_VALID;  MYSQLI_RETURN_RESOURCE(mysqli_resource, mysqli_warning_class_entry);  } /* }}}'],mysqli_info:[\"string mysqli_info(object link)\",\"Get information about the most recent query\"],mysqli_init:[\"resource mysqli_init(void)\",\"Initialize mysqli and return a resource for use with mysql_real_connect\"],mysqli_insert_id:[\"mixed mysqli_insert_id(object link)\",\"Get the ID generated from the previous INSERT operation\"],mysqli_kill:[\"bool mysqli_kill(object link, int processid)\",\"Kill a mysql process on the server\"],mysqli_link_construct:[\"object mysqli_link_construct()\",\"\"],mysqli_more_results:[\"bool mysqli_more_results(object link)\",\"check if there any more query results from a multi query\"],mysqli_multi_query:[\"bool mysqli_multi_query(object link, string query)\",\"allows to execute multiple queries\"],mysqli_next_result:[\"bool mysqli_next_result(object link)\",\"read next result from multi_query\"],mysqli_num_fields:[\"int mysqli_num_fields(object result)\",\"Get number of fields in result\"],mysqli_num_rows:[\"mixed mysqli_num_rows(object result)\",\"Get number of rows in result\"],mysqli_options:[\"bool mysqli_options(object link, int flags, mixed values)\",\"Set options\"],mysqli_ping:[\"bool mysqli_ping(object link)\",\"Ping a server connection or reconnect if there is no connection\"],mysqli_poll:[\"int mysqli_poll(array read, array write, array error, long sec [, long usec])\",\"Poll connections\"],mysqli_prepare:[\"mixed mysqli_prepare(object link, string query)\",\"Prepare a SQL statement for execution\"],mysqli_query:[\"mixed mysqli_query(object link, string query [,int resultmode]) */\",'PHP_FUNCTION(mysqli_query) {  MY_MYSQL   *mysql;  zval    *mysql_link;  MYSQLI_RESOURCE  *mysqli_resource;  MYSQL_RES    *result;  char    *query = NULL;  unsigned int   query_len;  unsigned long   resultmode = MYSQLI_STORE_RESULT;   if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), \"Os|l\", &mysql_link, mysqli_link_class_entry, &query, &query_len, &resultmode) == FAILURE) {   return;  }   if (!query_len) {   php_error_docref(NULL TSRMLS_CC, E_WARNING, \"Empty query\");   RETURN_FALSE;  }  if ((resultmode & ~MYSQLI_ASYNC) != MYSQLI_USE_RESULT && (resultmode & ~MYSQLI_ASYNC) != MYSQLI_STORE_RESULT) {   php_error_docref(NULL TSRMLS_CC, E_WARNING, \"Invalid value for resultmode\");   RETURN_FALSE;  }   MYSQLI_FETCH_RESOURCE(mysql, MY_MYSQL*, &mysql_link, \"mysqli_link\", MYSQLI_STATUS_VALID);   MYSQLI_DISABLE_MQ;   #ifdef MYSQLI_USE_MYSQLND  if (resultmode & MYSQLI_ASYNC) {   if (mysqli_async_query(mysql->mysql, query, query_len)) {    MYSQLI_REPORT_MYSQL_ERROR(mysql->mysql);    RETURN_FALSE;   }   mysql->async_result_fetch_type = resultmode & ~MYSQLI_ASYNC;   RETURN_TRUE;  } #endif   if (mysql_real_query(mysql->mysql, query, query_len)) {   MYSQLI_REPORT_MYSQL_ERROR(mysql->mysql);   RETURN_FALSE;  }   if (!mysql_field_count(mysql->mysql)) {   /* no result set - not a SELECT'],mysqli_real_connect:[\"bool mysqli_real_connect(object link [,string hostname [,string username [,string passwd [,string dbname [,int port [,string socket [,int flags]]]]]]])\",\"Open a connection to a mysql server\"],mysqli_real_escape_string:[\"string mysqli_real_escape_string(object link, string escapestr)\",\"Escapes special characters in a string for use in a SQL statement, taking into account the current charset of the connection\"],mysqli_real_query:[\"bool mysqli_real_query(object link, string query)\",\"Binary-safe version of mysql_query()\"],mysqli_reap_async_query:[\"int mysqli_reap_async_query(object link)\",\"Poll connections\"],mysqli_refresh:[\"bool mysqli_refresh(object link, long options)\",\"Flush tables or caches, or reset replication server information\"],mysqli_report:[\"bool mysqli_report(int flags)\",\"sets report level\"],mysqli_rollback:[\"bool mysqli_rollback(object link)\",\"Undo actions from current transaction\"],mysqli_select_db:[\"bool mysqli_select_db(object link, string dbname)\",\"Select a MySQL database\"],mysqli_set_charset:[\"bool mysqli_set_charset(object link, string csname)\",\"sets client character set\"],mysqli_set_local_infile_default:[\"void mysqli_set_local_infile_default(object link)\",\"unsets user defined handler for load local infile command\"],mysqli_set_local_infile_handler:[\"bool mysqli_set_local_infile_handler(object link, callback read_func)\",\"Set callback functions for LOAD DATA LOCAL INFILE\"],mysqli_sqlstate:[\"string mysqli_sqlstate(object link)\",\"Returns the SQLSTATE error from previous MySQL operation\"],mysqli_ssl_set:[\"bool mysqli_ssl_set(object link ,string key ,string cert ,string ca ,string capath ,string cipher])\",\"\"],mysqli_stat:[\"mixed mysqli_stat(object link)\",\"Get current system status\"],mysqli_stmt_affected_rows:[\"mixed mysqli_stmt_affected_rows(object stmt)\",\"Return the number of rows affected in the last query for the given link\"],mysqli_stmt_attr_get:[\"int mysqli_stmt_attr_get(object stmt, long attr)\",\"\"],mysqli_stmt_attr_set:[\"int mysqli_stmt_attr_set(object stmt, long attr, long mode)\",\"\"],mysqli_stmt_bind_param:[\"bool mysqli_stmt_bind_param(object stmt, string types, mixed variable [,mixed,....])\",\"Bind variables to a prepared statement as parameters\"],mysqli_stmt_bind_result:[\"bool mysqli_stmt_bind_result(object stmt, mixed var, [,mixed, ...])\",\"Bind variables to a prepared statement for result storage\"],mysqli_stmt_close:[\"bool mysqli_stmt_close(object stmt)\",\"Close statement\"],mysqli_stmt_data_seek:[\"void mysqli_stmt_data_seek(object stmt, int offset)\",\"Move internal result pointer\"],mysqli_stmt_errno:[\"int mysqli_stmt_errno(object stmt)\",\"\"],mysqli_stmt_error:[\"string mysqli_stmt_error(object stmt)\",\"\"],mysqli_stmt_execute:[\"bool mysqli_stmt_execute(object stmt)\",\"Execute a prepared statement\"],mysqli_stmt_fetch:[\"mixed mysqli_stmt_fetch(object stmt)\",\"Fetch results from a prepared statement into the bound variables\"],mysqli_stmt_field_count:[\"int mysqli_stmt_field_count(object stmt) {\",\"Return the number of result columns for the given statement\"],mysqli_stmt_free_result:[\"void mysqli_stmt_free_result(object stmt)\",\"Free stored result memory for the given statement handle\"],mysqli_stmt_get_result:[\"object mysqli_stmt_get_result(object link)\",\"Buffer result set on client\"],mysqli_stmt_get_warnings:[\"object mysqli_stmt_get_warnings(object link) */\",'PHP_FUNCTION(mysqli_stmt_get_warnings) {  MY_STMT    *stmt;  zval    *stmt_link;  MYSQLI_RESOURCE  *mysqli_resource;  MYSQLI_WARNING  *w;   if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), \"O\", &stmt_link, mysqli_stmt_class_entry) == FAILURE) {   return;  }  MYSQLI_FETCH_RESOURCE(stmt, MY_STMT*, &stmt_link, \"mysqli_stmt\", MYSQLI_STATUS_VALID);   if (mysqli_stmt_warning_count(stmt->stmt)) {   w = php_get_warnings(mysqli_stmt_get_connection(stmt->stmt) TSRMLS_CC);   } else {   RETURN_FALSE;  }  mysqli_resource = (MYSQLI_RESOURCE *)ecalloc (1, sizeof(MYSQLI_RESOURCE));  mysqli_resource->ptr = mysqli_resource->info = (void *)w;  mysqli_resource->status = MYSQLI_STATUS_VALID;  MYSQLI_RETURN_RESOURCE(mysqli_resource, mysqli_warning_class_entry); } /* }}}'],mysqli_stmt_init:[\"mixed mysqli_stmt_init(object link)\",\"Initialize statement object\"],mysqli_stmt_insert_id:[\"mixed mysqli_stmt_insert_id(object stmt)\",\"Get the ID generated from the previous INSERT operation\"],mysqli_stmt_next_result:[\"bool mysqli_stmt_next_result(object link)\",\"read next result from multi_query\"],mysqli_stmt_num_rows:[\"mixed mysqli_stmt_num_rows(object stmt)\",\"Return the number of rows in statements result set\"],mysqli_stmt_param_count:[\"int mysqli_stmt_param_count(object stmt)\",\"Return the number of parameter for the given statement\"],mysqli_stmt_prepare:[\"bool mysqli_stmt_prepare(object stmt, string query)\",\"prepare server side statement with query\"],mysqli_stmt_reset:[\"bool mysqli_stmt_reset(object stmt)\",\"reset a prepared statement\"],mysqli_stmt_result_metadata:[\"mixed mysqli_stmt_result_metadata(object stmt)\",\"return result set from statement\"],mysqli_stmt_send_long_data:[\"bool mysqli_stmt_send_long_data(object stmt, int param_nr, string data)\",\"\"],mysqli_stmt_sqlstate:[\"string mysqli_stmt_sqlstate(object stmt)\",\"\"],mysqli_stmt_store_result:[\"bool mysqli_stmt_store_result(stmt)\",\"\"],mysqli_store_result:[\"object mysqli_store_result(object link)\",\"Buffer result set on client\"],mysqli_thread_id:[\"int mysqli_thread_id(object link)\",\"Return the current thread ID\"],mysqli_thread_safe:[\"bool mysqli_thread_safe(void)\",\"Return whether thread safety is given or not\"],mysqli_use_result:[\"mixed mysqli_use_result(object link)\",\"Directly retrieve query results - do not buffer results on client side\"],mysqli_warning_count:[\"int mysqli_warning_count (object link)\",\"Return number of warnings from the last query for the given link\"],natcasesort:[\"void natcasesort(array &array_arg)\",\"Sort an array using case-insensitive natural sort\"],natsort:[\"void natsort(array &array_arg)\",\"Sort an array using natural sort\"],next:[\"mixed next(array array_arg)\",\"Move array argument's internal pointer to the next element and return it\"],ngettext:[\"string ngettext(string MSGID1, string MSGID2, int N)\",\"Plural version of gettext()\"],nl2br:[\"string nl2br(string str [, bool is_xhtml])\",\"Converts newlines to HTML line breaks\"],nl_langinfo:[\"string nl_langinfo(int item)\",\"Query language and locale information\"],normalizer_is_normalize:[\"bool normalizer_is_normalize( string $input [, string $form = FORM_C] )\",\"* Test if a string is in a given normalization form.\"],normalizer_normalize:[\"string normalizer_normalize( string $input [, string $form = FORM_C] )\",\"* Normalize a string.\"],nsapi_request_headers:[\"array nsapi_request_headers(void)\",\"Get all headers from the request\"],nsapi_response_headers:[\"array nsapi_response_headers(void)\",\"Get all headers from the response\"],nsapi_virtual:[\"bool nsapi_virtual(string uri)\",\"Perform an NSAPI sub-request\"],number_format:[\"string number_format(float number [, int num_decimal_places [, string dec_seperator, string thousands_seperator]])\",\"Formats a number with grouped thousands\"],numfmt_create:[\"NumberFormatter numfmt_create( string $locale, int style[, string $pattern ] )\",\"* Create number formatter.\"],numfmt_format:[\"mixed numfmt_format( NumberFormatter $nf, mixed $num[, int type] )\",\"* Format a number.\"],numfmt_format_currency:[\"mixed numfmt_format_currency( NumberFormatter $nf, double $num, string $currency )\",\"* Format a number as currency.\"],numfmt_get_attribute:[\"mixed numfmt_get_attribute( NumberFormatter $nf, int $attr )\",\"* Get formatter attribute value.\"],numfmt_get_error_code:[\"int numfmt_get_error_code( NumberFormatter $nf )\",\"* Get formatter's last error code.\"],numfmt_get_error_message:[\"string numfmt_get_error_message( NumberFormatter $nf )\",\"* Get text description for formatter's last error code.\"],numfmt_get_locale:[\"string numfmt_get_locale( NumberFormatter $nf[, int type] )\",\"* Get formatter locale.\"],numfmt_get_pattern:[\"string numfmt_get_pattern( NumberFormatter $nf )\",\"* Get formatter pattern.\"],numfmt_get_symbol:[\"string numfmt_get_symbol( NumberFormatter $nf, int $attr )\",\"* Get formatter symbol value.\"],numfmt_get_text_attribute:[\"string numfmt_get_text_attribute( NumberFormatter $nf, int $attr )\",\"* Get formatter attribute value.\"],numfmt_parse:[\"mixed numfmt_parse( NumberFormatter $nf, string $str[, int $type, int &$position ])\",\"* Parse a number.\"],numfmt_parse_currency:[\"double numfmt_parse_currency( NumberFormatter $nf, string $str, string $&currency[, int $&position] )\",\"* Parse a number as currency.\"],numfmt_parse_message:[\"array numfmt_parse_message( string $locale, string $pattern, string $source )\",\"* Parse a message.\"],numfmt_set_attribute:[\"bool numfmt_set_attribute( NumberFormatter $nf, int $attr, mixed $value )\",\"* Get formatter attribute value.\"],numfmt_set_pattern:[\"bool numfmt_set_pattern( NumberFormatter $nf, string $pattern )\",\"* Set formatter pattern.\"],numfmt_set_symbol:[\"bool numfmt_set_symbol( NumberFormatter $nf, int $attr, string $symbol )\",\"* Set formatter symbol value.\"],numfmt_set_text_attribute:[\"bool numfmt_set_text_attribute( NumberFormatter $nf, int $attr, string $value )\",\"* Get formatter attribute value.\"],ob_clean:[\"bool ob_clean(void)\",\"Clean (delete) the current output buffer\"],ob_end_clean:[\"bool ob_end_clean(void)\",\"Clean the output buffer, and delete current output buffer\"],ob_end_flush:[\"bool ob_end_flush(void)\",\"Flush (send) the output buffer, and delete current output buffer\"],ob_flush:[\"bool ob_flush(void)\",\"Flush (send) contents of the output buffer. The last buffer content is sent to next buffer\"],ob_get_clean:[\"bool ob_get_clean(void)\",\"Get current buffer contents and delete current output buffer\"],ob_get_contents:[\"string ob_get_contents(void)\",\"Return the contents of the output buffer\"],ob_get_flush:[\"bool ob_get_flush(void)\",\"Get current buffer contents, flush (send) the output buffer, and delete current output buffer\"],ob_get_length:[\"int ob_get_length(void)\",\"Return the length of the output buffer\"],ob_get_level:[\"int ob_get_level(void)\",\"Return the nesting level of the output buffer\"],ob_get_status:[\"false|array ob_get_status([bool full_status])\",\"Return the status of the active or all output buffers\"],ob_gzhandler:[\"string ob_gzhandler(string str, int mode)\",\"Encode str based on accept-encoding setting - designed to be called from ob_start()\"],ob_iconv_handler:[\"string ob_iconv_handler(string contents, int status)\",\"Returns str in output buffer converted to the iconv.output_encoding character set\"],ob_implicit_flush:[\"void ob_implicit_flush([int flag])\",\"Turn implicit flush on/off and is equivalent to calling flush() after every output call\"],ob_list_handlers:[\"false|array ob_list_handlers()\",\"*  List all output_buffers in an array\"],ob_start:[\"bool ob_start([ string|array user_function [, int chunk_size [, bool erase]]])\",\"Turn on Output Buffering (specifying an optional output handler).\"],oci_bind_array_by_name:[\"bool oci_bind_array_by_name(resource stmt, string name, array &var, int max_table_length [, int max_item_length [, int type ]])\",\"Bind a PHP array to an Oracle PL/SQL type by name\"],oci_bind_by_name:[\"bool oci_bind_by_name(resource stmt, string name, mixed &var, [, int maxlength [, int type]])\",\"Bind a PHP variable to an Oracle placeholder by name\"],oci_cancel:[\"bool oci_cancel(resource stmt)\",\"Cancel reading from a cursor\"],oci_close:[\"bool oci_close(resource connection)\",\"Disconnect from database\"],oci_collection_append:[\"bool oci_collection_append(string value)\",\"Append an object to the collection\"],oci_collection_assign:[\"bool oci_collection_assign(object from)\",\"Assign a collection from another existing collection\"],oci_collection_element_assign:[\"bool oci_collection_element_assign(int index, string val)\",\"Assign element val to collection at index ndx\"],oci_collection_element_get:[\"string oci_collection_element_get(int ndx)\",\"Retrieve the value at collection index ndx\"],oci_collection_max:[\"int oci_collection_max()\",\"Return the max value of a collection. For a varray this is the maximum length of the array\"],oci_collection_size:[\"int oci_collection_size()\",\"Return the size of a collection\"],oci_collection_trim:[\"bool oci_collection_trim(int num)\",\"Trim num elements from the end of a collection\"],oci_commit:[\"bool oci_commit(resource connection)\",\"Commit the current context\"],oci_connect:[\"resource oci_connect(string user, string pass [, string db [, string charset [, int session_mode ]])\",\"Connect to an Oracle database and log on. Returns a new session.\"],oci_define_by_name:[\"bool oci_define_by_name(resource stmt, string name, mixed &var [, int type])\",\"Define a PHP variable to an Oracle column by name\"],oci_error:[\"array oci_error([resource stmt|connection|global])\",\"Return the last error of stmt|connection|global. If no error happened returns false.\"],oci_execute:[\"bool oci_execute(resource stmt [, int mode])\",\"Execute a parsed statement\"],oci_fetch:[\"bool oci_fetch(resource stmt)\",\"Prepare a new row of data for reading\"],oci_fetch_all:[\"int oci_fetch_all(resource stmt, array &output[, int skip[, int maxrows[, int flags]]])\",\"Fetch all rows of result data into an array\"],oci_fetch_array:[\"array oci_fetch_array( resource stmt [, int mode ])\",\"Fetch a result row as an array\"],oci_fetch_assoc:[\"array oci_fetch_assoc( resource stmt )\",\"Fetch a result row as an associative array\"],oci_fetch_object:[\"object oci_fetch_object( resource stmt )\",\"Fetch a result row as an object\"],oci_fetch_row:[\"array oci_fetch_row( resource stmt )\",\"Fetch a result row as an enumerated array\"],oci_field_is_null:[\"bool oci_field_is_null(resource stmt, int col)\",\"Tell whether a column is NULL\"],oci_field_name:[\"string oci_field_name(resource stmt, int col)\",\"Tell the name of a column\"],oci_field_precision:[\"int oci_field_precision(resource stmt, int col)\",\"Tell the precision of a column\"],oci_field_scale:[\"int oci_field_scale(resource stmt, int col)\",\"Tell the scale of a column\"],oci_field_size:[\"int oci_field_size(resource stmt, int col)\",\"Tell the maximum data size of a column\"],oci_field_type:[\"mixed oci_field_type(resource stmt, int col)\",\"Tell the data type of a column\"],oci_field_type_raw:[\"int oci_field_type_raw(resource stmt, int col)\",\"Tell the raw oracle data type of a column\"],oci_free_collection:[\"bool oci_free_collection()\",\"Deletes collection object\"],oci_free_descriptor:[\"bool oci_free_descriptor()\",\"Deletes large object description\"],oci_free_statement:[\"bool oci_free_statement(resource stmt)\",\"Free all resources associated with a statement\"],oci_internal_debug:[\"void oci_internal_debug(int onoff)\",\"Toggle internal debugging output for the OCI extension\"],oci_lob_append:[\"bool oci_lob_append( object lob )\",\"Appends data from a LOB to another LOB\"],oci_lob_close:[\"bool oci_lob_close()\",\"Closes lob descriptor\"],oci_lob_copy:[\"bool oci_lob_copy( object lob_to, object lob_from [, int length ] )\",\"Copies data from a LOB to another LOB\"],oci_lob_eof:[\"bool oci_lob_eof()\",\"Checks if EOF is reached\"],oci_lob_erase:[\"int oci_lob_erase( [ int offset [, int length ] ] )\",\"Erases a specified portion of the internal LOB, starting at a specified offset\"],oci_lob_export:[\"bool oci_lob_export([string filename [, int start [, int length]]])\",\"Writes a large object into a file\"],oci_lob_flush:[\"bool oci_lob_flush( [ int flag ] )\",\"Flushes the LOB buffer\"],oci_lob_import:[\"bool oci_lob_import( string filename )\",\"Loads file into a LOB\"],oci_lob_is_equal:[\"bool oci_lob_is_equal( object lob1, object lob2 )\",\"Tests to see if two LOB/FILE locators are equal\"],oci_lob_load:[\"string oci_lob_load()\",\"Loads a large object\"],oci_lob_read:[\"string oci_lob_read( int length )\",\"Reads particular part of a large object\"],oci_lob_rewind:[\"bool oci_lob_rewind()\",\"Rewind pointer of a LOB\"],oci_lob_save:[\"bool oci_lob_save( string data [, int offset ])\",\"Saves a large object\"],oci_lob_seek:[\"bool oci_lob_seek( int offset [, int whence ])\",\"Moves the pointer of a LOB\"],oci_lob_size:[\"int oci_lob_size()\",\"Returns size of a large object\"],oci_lob_tell:[\"int oci_lob_tell()\",\"Tells LOB pointer position\"],oci_lob_truncate:[\"bool oci_lob_truncate( [ int length ])\",\"Truncates a LOB\"],oci_lob_write:[\"int oci_lob_write( string string [, int length ])\",\"Writes data to current position of a LOB\"],oci_lob_write_temporary:[\"bool oci_lob_write_temporary(string var [, int lob_type])\",\"Writes temporary blob\"],oci_new_collection:[\"object oci_new_collection(resource connection, string tdo [, string schema])\",\"Initialize a new collection\"],oci_new_connect:[\"resource oci_new_connect(string user, string pass [, string db])\",\"Connect to an Oracle database and log on. Returns a new session.\"],oci_new_cursor:[\"resource oci_new_cursor(resource connection)\",\"Return a new cursor (Statement-Handle) - use this to bind ref-cursors!\"],oci_new_descriptor:[\"object oci_new_descriptor(resource connection [, int type])\",\"Initialize a new empty descriptor LOB/FILE (LOB is default)\"],oci_num_fields:[\"int oci_num_fields(resource stmt)\",\"Return the number of result columns in a statement\"],oci_num_rows:[\"int oci_num_rows(resource stmt)\",\"Return the row count of an OCI statement\"],oci_parse:[\"resource oci_parse(resource connection, string query)\",\"Parse a query and return a statement\"],oci_password_change:[\"bool oci_password_change(resource connection, string username, string old_password, string new_password)\",\"Changes the password of an account\"],oci_pconnect:[\"resource oci_pconnect(string user, string pass [, string db [, string charset ]])\",\"Connect to an Oracle database using a persistent connection and log on. Returns a new session.\"],oci_result:[\"string oci_result(resource stmt, mixed column)\",\"Return a single column of result data\"],oci_rollback:[\"bool oci_rollback(resource connection)\",\"Rollback the current context\"],oci_server_version:[\"string oci_server_version(resource connection)\",\"Return a string containing server version information\"],oci_set_action:[\"bool oci_set_action(resource connection, string value)\",\"Sets the action attribute on the connection\"],oci_set_client_identifier:[\"bool oci_set_client_identifier(resource connection, string value)\",\"Sets the client identifier attribute on the connection\"],oci_set_client_info:[\"bool oci_set_client_info(resource connection, string value)\",\"Sets the client info attribute on the connection\"],oci_set_edition:[\"bool oci_set_edition(string value)\",\"Sets the edition attribute for all subsequent connections created\"],oci_set_module_name:[\"bool oci_set_module_name(resource connection, string value)\",\"Sets the module attribute on the connection\"],oci_set_prefetch:[\"bool oci_set_prefetch(resource stmt, int prefetch_rows)\",\"Sets the number of rows to be prefetched on execute to prefetch_rows for stmt\"],oci_statement_type:[\"string oci_statement_type(resource stmt)\",\"Return the query type of an OCI statement\"],ocifetchinto:[\"int ocifetchinto(resource stmt, array &output [, int mode])\",\"Fetch a row of result data into an array\"],ocigetbufferinglob:[\"bool ocigetbufferinglob()\",\"Returns current state of buffering for a LOB\"],ocisetbufferinglob:[\"bool ocisetbufferinglob( boolean flag )\",\"Enables/disables buffering for a LOB\"],octdec:[\"int octdec(string octal_number)\",\"Returns the decimal equivalent of an octal string\"],odbc_autocommit:[\"mixed odbc_autocommit(resource connection_id [, int OnOff])\",\"Toggle autocommit mode or get status\"],odbc_binmode:[\"bool odbc_binmode(int result_id, int mode)\",\"Handle binary column data\"],odbc_close:[\"void odbc_close(resource connection_id)\",\"Close an ODBC connection\"],odbc_close_all:[\"void odbc_close_all(void)\",\"Close all ODBC connections\"],odbc_columnprivileges:[\"resource odbc_columnprivileges(resource connection_id, string catalog, string schema, string table, string column)\",\"Returns a result identifier that can be used to fetch a list of columns and associated privileges for the specified table\"],odbc_columns:[\"resource odbc_columns(resource connection_id [, string qualifier [, string owner [, string table_name [, string column_name]]]])\",\"Returns a result identifier that can be used to fetch a list of column names in specified tables\"],odbc_commit:[\"bool odbc_commit(resource connection_id)\",\"Commit an ODBC transaction\"],odbc_connect:[\"resource odbc_connect(string DSN, string user, string password [, int cursor_option])\",\"Connect to a datasource\"],odbc_cursor:[\"string odbc_cursor(resource result_id)\",\"Get cursor name\"],odbc_data_source:[\"array odbc_data_source(resource connection_id, int fetch_type)\",\"Return information about the currently connected data source\"],odbc_error:[\"string odbc_error([resource connection_id])\",\"Get the last error code\"],odbc_errormsg:[\"string odbc_errormsg([resource connection_id])\",\"Get the last error message\"],odbc_exec:[\"resource odbc_exec(resource connection_id, string query [, int flags])\",\"Prepare and execute an SQL statement\"],odbc_execute:[\"bool odbc_execute(resource result_id [, array parameters_array])\",\"Execute a prepared statement\"],odbc_fetch_array:[\"array odbc_fetch_array(int result [, int rownumber])\",\"Fetch a result row as an associative array\"],odbc_fetch_into:[\"int odbc_fetch_into(resource result_id, array &result_array, [, int rownumber])\",\"Fetch one result row into an array\"],odbc_fetch_object:[\"object odbc_fetch_object(int result [, int rownumber])\",\"Fetch a result row as an object\"],odbc_fetch_row:[\"bool odbc_fetch_row(resource result_id [, int row_number])\",\"Fetch a row\"],odbc_field_len:[\"int odbc_field_len(resource result_id, int field_number)\",\"Get the length (precision) of a column\"],odbc_field_name:[\"string odbc_field_name(resource result_id, int field_number)\",\"Get a column name\"],odbc_field_num:[\"int odbc_field_num(resource result_id, string field_name)\",\"Return column number\"],odbc_field_scale:[\"int odbc_field_scale(resource result_id, int field_number)\",\"Get the scale of a column\"],odbc_field_type:[\"string odbc_field_type(resource result_id, int field_number)\",\"Get the datatype of a column\"],odbc_foreignkeys:[\"resource odbc_foreignkeys(resource connection_id, string pk_qualifier, string pk_owner, string pk_table, string fk_qualifier, string fk_owner, string fk_table)\",\"Returns a result identifier to either a list of foreign keys in the specified table or a list of foreign keys in other tables that refer to the primary key in the specified table\"],odbc_free_result:[\"bool odbc_free_result(resource result_id)\",\"Free resources associated with a result\"],odbc_gettypeinfo:[\"resource odbc_gettypeinfo(resource connection_id [, int data_type])\",\"Returns a result identifier containing information about data types supported by the data source\"],odbc_longreadlen:[\"bool odbc_longreadlen(int result_id, int length)\",\"Handle LONG columns\"],odbc_next_result:[\"bool odbc_next_result(resource result_id)\",\"Checks if multiple results are avaiable\"],odbc_num_fields:[\"int odbc_num_fields(resource result_id)\",\"Get number of columns in a result\"],odbc_num_rows:[\"int odbc_num_rows(resource result_id)\",\"Get number of rows in a result\"],odbc_pconnect:[\"resource odbc_pconnect(string DSN, string user, string password [, int cursor_option])\",\"Establish a persistent connection to a datasource\"],odbc_prepare:[\"resource odbc_prepare(resource connection_id, string query)\",\"Prepares a statement for execution\"],odbc_primarykeys:[\"resource odbc_primarykeys(resource connection_id, string qualifier, string owner, string table)\",\"Returns a result identifier listing the column names that comprise the primary key for a table\"],odbc_procedurecolumns:[\"resource odbc_procedurecolumns(resource connection_id [, string qualifier, string owner, string proc, string column])\",\"Returns a result identifier containing the list of input and output parameters, as well as the columns that make up the result set for the specified procedures\"],odbc_procedures:[\"resource odbc_procedures(resource connection_id [, string qualifier, string owner, string name])\",\"Returns a result identifier containg the list of procedure names in a datasource\"],odbc_result:[\"mixed odbc_result(resource result_id, mixed field)\",\"Get result data\"],odbc_result_all:[\"int odbc_result_all(resource result_id [, string format])\",\"Print result as HTML table\"],odbc_rollback:[\"bool odbc_rollback(resource connection_id)\",\"Rollback a transaction\"],odbc_setoption:[\"bool odbc_setoption(resource conn_id|result_id, int which, int option, int value)\",\"Sets connection or statement options\"],odbc_specialcolumns:[\"resource odbc_specialcolumns(resource connection_id, int type, string qualifier, string owner, string table, int scope, int nullable)\",\"Returns a result identifier containing either the optimal set of columns that uniquely identifies a row in the table or columns that are automatically updated when any value in the row is updated by a transaction\"],odbc_statistics:[\"resource odbc_statistics(resource connection_id, string qualifier, string owner, string name, int unique, int accuracy)\",\"Returns a result identifier that contains statistics about a single table and the indexes associated with the table\"],odbc_tableprivileges:[\"resource odbc_tableprivileges(resource connection_id, string qualifier, string owner, string name)\",\"Returns a result identifier containing a list of tables and the privileges associated with each table\"],odbc_tables:[\"resource odbc_tables(resource connection_id [, string qualifier [, string owner [, string name [, string table_types]]]])\",\"Call the SQLTables function\"],opendir:[\"mixed opendir(string path[, resource context])\",\"Open a directory and return a dir_handle\"],openlog:[\"bool openlog(string ident, int option, int facility)\",\"Open connection to system logger\"],openssl_csr_export:[\"bool openssl_csr_export(resource csr, string &out [, bool notext=true])\",\"Exports a CSR to file or a var\"],openssl_csr_export_to_file:[\"bool openssl_csr_export_to_file(resource csr, string outfilename [, bool notext=true])\",\"Exports a CSR to file\"],openssl_csr_get_public_key:[\"mixed openssl_csr_get_public_key(mixed csr)\",\"Returns the subject of a CERT or FALSE on error\"],openssl_csr_get_subject:[\"mixed openssl_csr_get_subject(mixed csr)\",\"Returns the subject of a CERT or FALSE on error\"],openssl_csr_new:[\"bool openssl_csr_new(array dn, resource &privkey [, array configargs [, array extraattribs]])\",\"Generates a privkey and CSR\"],openssl_csr_sign:[\"resource openssl_csr_sign(mixed csr, mixed x509, mixed priv_key, long days [, array config_args [, long serial]])\",\"Signs a cert with another CERT\"],openssl_decrypt:[\"string openssl_decrypt(string data, string method, string password [, bool raw_input=false])\",\"Takes raw or base64 encoded string and dectupt it using given method and key\"],openssl_dh_compute_key:[\"string openssl_dh_compute_key(string pub_key, resource dh_key)\",\"Computes shared sicret for public value of remote DH key and local DH key\"],openssl_digest:[\"string openssl_digest(string data, string method [, bool raw_output=false])\",\"Computes digest hash value for given data using given method, returns raw or binhex encoded string\"],openssl_encrypt:[\"string openssl_encrypt(string data, string method, string password [, bool raw_output=false])\",\"Encrypts given data with given method and key, returns raw or base64 encoded string\"],openssl_error_string:[\"mixed openssl_error_string(void)\",\"Returns a description of the last error, and alters the index of the error messages. Returns false when the are no more messages\"],openssl_get_cipher_methods:[\"array openssl_get_cipher_methods([bool aliases = false])\",\"Return array of available cipher methods\"],openssl_get_md_methods:[\"array openssl_get_md_methods([bool aliases = false])\",\"Return array of available digest methods\"],openssl_open:[\"bool openssl_open(string data, &string opendata, string ekey, mixed privkey)\",\"Opens data\"],openssl_pkcs12_export:[\"bool openssl_pkcs12_export(mixed x509, string &out, mixed priv_key, string pass[, array args])\",\"Creates and exports a PKCS12 to a var\"],openssl_pkcs12_export_to_file:[\"bool openssl_pkcs12_export_to_file(mixed x509, string filename, mixed priv_key, string pass[, array args])\",\"Creates and exports a PKCS to file\"],openssl_pkcs12_read:[\"bool openssl_pkcs12_read(string PKCS12, array &certs, string pass)\",\"Parses a PKCS12 to an array\"],openssl_pkcs7_decrypt:[\"bool openssl_pkcs7_decrypt(string infilename, string outfilename, mixed recipcert [, mixed recipkey])\",\"Decrypts the S/MIME message in the file name infilename and output the results to the file name outfilename.  recipcert is a CERT for one of the recipients. recipkey specifies the private key matching recipcert, if recipcert does not include the key\"],openssl_pkcs7_encrypt:[\"bool openssl_pkcs7_encrypt(string infile, string outfile, mixed recipcerts, array headers [, long flags [, long cipher]])\",\"Encrypts the message in the file named infile with the certificates in recipcerts and output the result to the file named outfile\"],openssl_pkcs7_sign:[\"bool openssl_pkcs7_sign(string infile, string outfile, mixed signcert, mixed signkey, array headers [, long flags [, string extracertsfilename]])\",\"Signs the MIME message in the file named infile with signcert/signkey and output the result to file name outfile. headers lists plain text headers to exclude from the signed portion of the message, and should include to, from and subject as a minimum\"],openssl_pkcs7_verify:[\"bool openssl_pkcs7_verify(string filename, long flags [, string signerscerts [, array cainfo [, string extracerts [, string content]]]])\",\"Verifys that the data block is intact, the signer is who they say they are, and returns the CERTs of the signers\"],openssl_pkey_export:[\"bool openssl_pkey_export(mixed key, &mixed out [, string passphrase [, array config_args]])\",\"Gets an exportable representation of a key into a string or file\"],openssl_pkey_export_to_file:[\"bool openssl_pkey_export_to_file(mixed key, string outfilename [, string passphrase, array config_args)\",\"Gets an exportable representation of a key into a file\"],openssl_pkey_free:[\"void openssl_pkey_free(int key)\",\"Frees a key\"],openssl_pkey_get_details:[\"resource openssl_pkey_get_details(resource key)\",\"returns an array with the key details (bits, pkey, type)\"],openssl_pkey_get_private:[\"int openssl_pkey_get_private(string key [, string passphrase])\",\"Gets private keys\"],openssl_pkey_get_public:[\"int openssl_pkey_get_public(mixed cert)\",\"Gets public key from X.509 certificate\"],openssl_pkey_new:[\"resource openssl_pkey_new([array configargs])\",\"Generates a new private key\"],openssl_private_decrypt:[\"bool openssl_private_decrypt(string data, string &decrypted, mixed key [, int padding])\",\"Decrypts data with private key\"],openssl_private_encrypt:[\"bool openssl_private_encrypt(string data, string &crypted, mixed key [, int padding])\",\"Encrypts data with private key\"],openssl_public_decrypt:[\"bool openssl_public_decrypt(string data, string &crypted, resource key [, int padding])\",\"Decrypts data with public key\"],openssl_public_encrypt:[\"bool openssl_public_encrypt(string data, string &crypted, mixed key [, int padding])\",\"Encrypts data with public key\"],openssl_random_pseudo_bytes:[\"string openssl_random_pseudo_bytes(integer length [, &bool returned_strong_result])\",\"Returns a string of the length specified filled with random pseudo bytes\"],openssl_seal:[\"int openssl_seal(string data, &string sealdata, &array ekeys, array pubkeys)\",\"Seals data\"],openssl_sign:[\"bool openssl_sign(string data, &string signature, mixed key[, mixed method])\",\"Signs data\"],openssl_verify:[\"int openssl_verify(string data, string signature, mixed key[, mixed method])\",\"Verifys data\"],openssl_x509_check_private_key:[\"bool openssl_x509_check_private_key(mixed cert, mixed key)\",\"Checks if a private key corresponds to a CERT\"],openssl_x509_checkpurpose:[\"int openssl_x509_checkpurpose(mixed x509cert, int purpose, array cainfo [, string untrustedfile])\",\"Checks the CERT to see if it can be used for the purpose in purpose. cainfo holds information about trusted CAs\"],openssl_x509_export:[\"bool openssl_x509_export(mixed x509, string &out [, bool notext = true])\",\"Exports a CERT to file or a var\"],openssl_x509_export_to_file:[\"bool openssl_x509_export_to_file(mixed x509, string outfilename [, bool notext = true])\",\"Exports a CERT to file or a var\"],openssl_x509_free:[\"void openssl_x509_free(resource x509)\",\"Frees X.509 certificates\"],openssl_x509_parse:[\"array openssl_x509_parse(mixed x509 [, bool shortnames=true])\",\"Returns an array of the fields/values of the CERT\"],openssl_x509_read:[\"resource openssl_x509_read(mixed cert)\",\"Reads X.509 certificates\"],ord:[\"int ord(string character)\",\"Returns ASCII value of character\"],output_add_rewrite_var:[\"bool output_add_rewrite_var(string name, string value)\",\"Add URL rewriter values\"],output_reset_rewrite_vars:[\"bool output_reset_rewrite_vars(void)\",\"Reset(clear) URL rewriter values\"],pack:[\"string pack(string format, mixed arg1 [, mixed arg2 [, mixed ...]])\",\"Takes one or more arguments and packs them into a binary string according to the format argument\"],parse_ini_file:[\"array parse_ini_file(string filename [, bool process_sections [, int scanner_mode]])\",\"Parse configuration file\"],parse_ini_string:[\"array parse_ini_string(string ini_string [, bool process_sections [, int scanner_mode]])\",\"Parse configuration string\"],parse_locale:[\"static array parse_locale($locale)\",\"* parses a locale-id into an array the different parts of it\"],parse_str:[\"void parse_str(string encoded_string [, array result])\",\"Parses GET/POST/COOKIE data and sets global variables\"],parse_url:[\"mixed parse_url(string url, [int url_component])\",\"Parse a URL and return its components\"],passthru:[\"void passthru(string command [, int &return_value])\",\"Execute an external program and display raw output\"],pathinfo:[\"array pathinfo(string path[, int options])\",\"Returns information about a certain string\"],pclose:[\"int pclose(resource fp)\",\"Close a file pointer opened by popen()\"],pcnlt_sigwaitinfo:[\"int pcnlt_sigwaitinfo(array set[, array &siginfo])\",\"Synchronously wait for queued signals\"],pcntl_alarm:[\"int pcntl_alarm(int seconds)\",\"Set an alarm clock for delivery of a signal\"],pcntl_exec:[\"bool pcntl_exec(string path [, array args [, array envs]])\",\"Executes specified program in current process space as defined by exec(2)\"],pcntl_fork:[\"int pcntl_fork(void)\",\"Forks the currently running process following the same behavior as the UNIX fork() system call\"],pcntl_getpriority:[\"int pcntl_getpriority([int pid [, int process_identifier]])\",\"Get the priority of any process\"],pcntl_setpriority:[\"bool pcntl_setpriority(int priority [, int pid [, int process_identifier]])\",\"Change the priority of any process\"],pcntl_signal:[\"bool pcntl_signal(int signo, callback handle [, bool restart_syscalls])\",\"Assigns a system signal handler to a PHP function\"],pcntl_signal_dispatch:[\"bool pcntl_signal_dispatch()\",\"Dispatch signals to signal handlers\"],pcntl_sigprocmask:[\"bool pcntl_sigprocmask(int how, array set[, array &oldset])\",\"Examine and change blocked signals\"],pcntl_sigtimedwait:[\"int pcntl_sigtimedwait(array set[, array &siginfo[, int seconds[, int nanoseconds]]])\",\"Wait for queued signals\"],pcntl_wait:[\"int pcntl_wait(int &status)\",\"Waits on or returns the status of a forked child as defined by the waitpid() system call\"],pcntl_waitpid:[\"int pcntl_waitpid(int pid, int &status, int options)\",\"Waits on or returns the status of a forked child as defined by the waitpid() system call\"],pcntl_wexitstatus:[\"int pcntl_wexitstatus(int status)\",\"Returns the status code of a child's exit\"],pcntl_wifexited:[\"bool pcntl_wifexited(int status)\",\"Returns true if the child status code represents a successful exit\"],pcntl_wifsignaled:[\"bool pcntl_wifsignaled(int status)\",\"Returns true if the child status code represents a process that was terminated due to a signal\"],pcntl_wifstopped:[\"bool pcntl_wifstopped(int status)\",\"Returns true if the child status code represents a stopped process (WUNTRACED must have been used with waitpid)\"],pcntl_wstopsig:[\"int pcntl_wstopsig(int status)\",\"Returns the number of the signal that caused the process to stop who's status code is passed\"],pcntl_wtermsig:[\"int pcntl_wtermsig(int status)\",\"Returns the number of the signal that terminated the process who's status code is passed\"],pdo_drivers:[\"array pdo_drivers()\",\"Return array of available PDO drivers\"],pfsockopen:[\"resource pfsockopen(string hostname, int port [, int errno [, string errstr [, float timeout]]])\",\"Open persistent Internet or Unix domain socket connection\"],pg_affected_rows:[\"int pg_affected_rows(resource result)\",\"Returns the number of affected tuples\"],pg_cancel_query:[\"bool pg_cancel_query(resource connection)\",\"Cancel request\"],pg_client_encoding:[\"string pg_client_encoding([resource connection])\",\"Get the current client encoding\"],pg_close:[\"bool pg_close([resource connection])\",\"Close a PostgreSQL connection\"],pg_connect:[\"resource pg_connect(string connection_string[, int connect_type] | [string host, string port [, string options [, string tty,]]] string database)\",\"Open a PostgreSQL connection\"],pg_connection_busy:[\"bool pg_connection_busy(resource connection)\",\"Get connection is busy or not\"],pg_connection_reset:[\"bool pg_connection_reset(resource connection)\",\"Reset connection (reconnect)\"],pg_connection_status:[\"int pg_connection_status(resource connnection)\",\"Get connection status\"],pg_convert:[\"array pg_convert(resource db, string table, array values[, int options])\",\"Check and convert values for PostgreSQL SQL statement\"],pg_copy_from:[\"bool pg_copy_from(resource connection, string table_name , array rows [, string delimiter [, string null_as]])\",\"Copy table from array\"],pg_copy_to:[\"array pg_copy_to(resource connection, string table_name [, string delimiter [, string null_as]])\",\"Copy table to array\"],pg_dbname:[\"string pg_dbname([resource connection])\",\"Get the database name\"],pg_delete:[\"mixed pg_delete(resource db, string table, array ids[, int options])\",\"Delete records has ids (id=>value)\"],pg_end_copy:[\"bool pg_end_copy([resource connection])\",\"Sync with backend. Completes the Copy command\"],pg_escape_bytea:[\"string pg_escape_bytea([resource connection,] string data)\",\"Escape binary for bytea type\"],pg_escape_string:[\"string pg_escape_string([resource connection,] string data)\",\"Escape string for text/char type\"],pg_execute:[\"resource pg_execute([resource connection,] string stmtname, array params)\",\"Execute a prepared query\"],pg_fetch_all:[\"array pg_fetch_all(resource result)\",\"Fetch all rows into array\"],pg_fetch_all_columns:[\"array pg_fetch_all_columns(resource result [, int column_number])\",\"Fetch all rows into array\"],pg_fetch_array:[\"array pg_fetch_array(resource result [, int row [, int result_type]])\",\"Fetch a row as an array\"],pg_fetch_assoc:[\"array pg_fetch_assoc(resource result [, int row])\",\"Fetch a row as an assoc array\"],pg_fetch_object:[\"object pg_fetch_object(resource result [, int row [, string class_name [, NULL|array ctor_params]]])\",\"Fetch a row as an object\"],pg_fetch_result:[\"mixed pg_fetch_result(resource result, [int row_number,] mixed field_name)\",\"Returns values from a result identifier\"],pg_fetch_row:[\"array pg_fetch_row(resource result [, int row [, int result_type]])\",\"Get a row as an enumerated array\"],pg_field_is_null:[\"int pg_field_is_null(resource result, [int row,] mixed field_name_or_number)\",\"Test if a field is NULL\"],pg_field_name:[\"string pg_field_name(resource result, int field_number)\",\"Returns the name of the field\"],pg_field_num:[\"int pg_field_num(resource result, string field_name)\",\"Returns the field number of the named field\"],pg_field_prtlen:[\"int pg_field_prtlen(resource result, [int row,] mixed field_name_or_number)\",\"Returns the printed length\"],pg_field_size:[\"int pg_field_size(resource result, int field_number)\",\"Returns the internal size of the field\"],pg_field_table:[\"mixed pg_field_table(resource result, int field_number[, bool oid_only])\",\"Returns the name of the table field belongs to, or table's oid if oid_only is true\"],pg_field_type:[\"string pg_field_type(resource result, int field_number)\",\"Returns the type name for the given field\"],pg_field_type_oid:[\"string pg_field_type_oid(resource result, int field_number)\",\"Returns the type oid for the given field\"],pg_free_result:[\"bool pg_free_result(resource result)\",\"Free result memory\"],pg_get_notify:[\"array pg_get_notify([resource connection[, result_type]])\",\"Get asynchronous notification\"],pg_get_pid:[\"int pg_get_pid([resource connection)\",\"Get backend(server) pid\"],pg_get_result:[\"resource pg_get_result(resource connection)\",\"Get asynchronous query result\"],pg_host:[\"string pg_host([resource connection])\",\"Returns the host name associated with the connection\"],pg_insert:[\"mixed pg_insert(resource db, string table, array values[, int options])\",\"Insert values (filed=>value) to table\"],pg_last_error:[\"string pg_last_error([resource connection])\",\"Get the error message string\"],pg_last_notice:[\"string pg_last_notice(resource connection)\",\"Returns the last notice set by the backend\"],pg_last_oid:[\"string pg_last_oid(resource result)\",\"Returns the last object identifier\"],pg_lo_close:[\"bool pg_lo_close(resource large_object)\",\"Close a large object\"],pg_lo_create:[\"mixed pg_lo_create([resource connection],[mixed large_object_oid])\",\"Create a large object\"],pg_lo_export:[\"bool pg_lo_export([resource connection, ] int objoid, string filename)\",\"Export large object direct to filesystem\"],pg_lo_import:[\"int pg_lo_import([resource connection, ] string filename [, mixed oid])\",\"Import large object direct from filesystem\"],pg_lo_open:[\"resource pg_lo_open([resource connection,] int large_object_oid, string mode)\",\"Open a large object and return fd\"],pg_lo_read:[\"string pg_lo_read(resource large_object [, int len])\",\"Read a large object\"],pg_lo_read_all:[\"int pg_lo_read_all(resource large_object)\",\"Read a large object and send straight to browser\"],pg_lo_seek:[\"bool pg_lo_seek(resource large_object, int offset [, int whence])\",\"Seeks position of large object\"],pg_lo_tell:[\"int pg_lo_tell(resource large_object)\",\"Returns current position of large object\"],pg_lo_unlink:[\"bool pg_lo_unlink([resource connection,] string large_object_oid)\",\"Delete a large object\"],pg_lo_write:[\"int pg_lo_write(resource large_object, string buf [, int len])\",\"Write a large object\"],pg_meta_data:[\"array pg_meta_data(resource db, string table)\",\"Get meta_data\"],pg_num_fields:[\"int pg_num_fields(resource result)\",\"Return the number of fields in the result\"],pg_num_rows:[\"int pg_num_rows(resource result)\",\"Return the number of rows in the result\"],pg_options:[\"string pg_options([resource connection])\",\"Get the options associated with the connection\"],pg_parameter_status:[\"string|false pg_parameter_status([resource connection,] string param_name)\",\"Returns the value of a server parameter\"],pg_pconnect:[\"resource pg_pconnect(string connection_string | [string host, string port [, string options [, string tty,]]] string database)\",\"Open a persistent PostgreSQL connection\"],pg_ping:[\"bool pg_ping([resource connection])\",\"Ping database. If connection is bad, try to reconnect.\"],pg_port:[\"int pg_port([resource connection])\",\"Return the port number associated with the connection\"],pg_prepare:[\"resource pg_prepare([resource connection,] string stmtname, string query)\",\"Prepare a query for future execution\"],pg_put_line:[\"bool pg_put_line([resource connection,] string query)\",\"Send null-terminated string to backend server\"],pg_query:[\"resource pg_query([resource connection,] string query)\",\"Execute a query\"],pg_query_params:[\"resource pg_query_params([resource connection,] string query, array params)\",\"Execute a query\"],pg_result_error:[\"string pg_result_error(resource result)\",\"Get error message associated with result\"],pg_result_error_field:[\"string pg_result_error_field(resource result, int fieldcode)\",\"Get error message field associated with result\"],pg_result_seek:[\"bool pg_result_seek(resource result, int offset)\",\"Set internal row offset\"],pg_result_status:[\"mixed pg_result_status(resource result[, long result_type])\",\"Get status of query result\"],pg_select:[\"mixed pg_select(resource db, string table, array ids[, int options])\",\"Select records that has ids (id=>value)\"],pg_send_execute:[\"bool pg_send_execute(resource connection, string stmtname, array params)\",\"Executes prevriously prepared stmtname asynchronously\"],pg_send_prepare:[\"bool pg_send_prepare(resource connection, string stmtname, string query)\",\"Asynchronously prepare a query for future execution\"],pg_send_query:[\"bool pg_send_query(resource connection, string query)\",\"Send asynchronous query\"],pg_send_query_params:[\"bool pg_send_query_params(resource connection, string query, array params)\",\"Send asynchronous parameterized query\"],pg_set_client_encoding:[\"int pg_set_client_encoding([resource connection,] string encoding)\",\"Set client encoding\"],pg_set_error_verbosity:[\"int pg_set_error_verbosity([resource connection,] int verbosity)\",\"Set error verbosity\"],pg_trace:[\"bool pg_trace(string filename [, string mode [, resource connection]])\",\"Enable tracing a PostgreSQL connection\"],pg_transaction_status:[\"int pg_transaction_status(resource connnection)\",\"Get transaction status\"],pg_tty:[\"string pg_tty([resource connection])\",\"Return the tty name associated with the connection\"],pg_unescape_bytea:[\"string pg_unescape_bytea(string data)\",\"Unescape binary for bytea type\"],pg_untrace:[\"bool pg_untrace([resource connection])\",\"Disable tracing of a PostgreSQL connection\"],pg_update:[\"mixed pg_update(resource db, string table, array fields, array ids[, int options])\",\"Update table using values (field=>value) and ids (id=>value)\"],pg_version:[\"array pg_version([resource connection])\",\"Returns an array with client, protocol and server version (when available)\"],php_egg_logo_guid:[\"string php_egg_logo_guid(void)\",\"Return the special ID used to request the PHP logo in phpinfo screens\"],php_ini_loaded_file:[\"string php_ini_loaded_file(void)\",\"Return the actual loaded ini filename\"],php_ini_scanned_files:[\"string php_ini_scanned_files(void)\",\"Return comma-separated string of .ini files parsed from the additional ini dir\"],php_logo_guid:[\"string php_logo_guid(void)\",\"Return the special ID used to request the PHP logo in phpinfo screens\"],php_real_logo_guid:[\"string php_real_logo_guid(void)\",\"Return the special ID used to request the PHP logo in phpinfo screens\"],php_sapi_name:[\"string php_sapi_name(void)\",\"Return the current SAPI module name\"],php_snmpv3:[\"void php_snmpv3(INTERNAL_FUNCTION_PARAMETERS, int st)\",\"* * Generic SNMPv3 object fetcher * From here is passed on the the common internal object fetcher. * * st=SNMP_CMD_GET   snmp3_get() - query an agent and return a single value. * st=SNMP_CMD_GETNEXT   snmp3_getnext() - query an agent and return the next single value. * st=SNMP_CMD_WALK   snmp3_walk() - walk the mib and return a single dimensional array  *                       containing the values. * st=SNMP_CMD_REALWALK   snmp3_real_walk() - walk the mib and return an  *                            array of oid,value pairs. * st=SNMP_CMD_SET  snmp3_set() - query an agent and set a single value *\"],php_strip_whitespace:[\"string php_strip_whitespace(string file_name)\",\"Return source with stripped comments and whitespace\"],php_uname:[\"string php_uname(void)\",\"Return information about the system PHP was built on\"],phpcredits:[\"void phpcredits([int flag])\",\"Prints the list of people who've contributed to the PHP project\"],phpinfo:[\"void phpinfo([int what])\",\"Output a page of useful information about PHP and the current request\"],phpversion:[\"string phpversion([string extension])\",\"Return the current PHP version\"],pi:[\"float pi(void)\",\"Returns an approximation of pi\"],png2wbmp:[\"bool png2wbmp (string f_org, string f_dest, int d_height, int d_width, int threshold)\",\"Convert PNG image to WBMP image\"],popen:[\"resource popen(string command, string mode)\",\"Execute a command and open either a read or a write pipe to it\"],posix_access:[\"bool posix_access(string file [, int mode])\",\"Determine accessibility of a file (POSIX.1 5.6.3)\"],posix_ctermid:[\"string posix_ctermid(void)\",\"Generate terminal path name (POSIX.1, 4.7.1)\"],posix_get_last_error:[\"int posix_get_last_error(void)\",\"Retrieve the error number set by the last posix function which failed.\"],posix_getcwd:[\"string posix_getcwd(void)\",\"Get working directory pathname (POSIX.1, 5.2.2)\"],posix_getegid:[\"int posix_getegid(void)\",\"Get the current effective group id (POSIX.1, 4.2.1)\"],posix_geteuid:[\"int posix_geteuid(void)\",\"Get the current effective user id (POSIX.1, 4.2.1)\"],posix_getgid:[\"int posix_getgid(void)\",\"Get the current group id (POSIX.1, 4.2.1)\"],posix_getgrgid:[\"array posix_getgrgid(long gid)\",\"Group database access (POSIX.1, 9.2.1)\"],posix_getgrnam:[\"array posix_getgrnam(string groupname)\",\"Group database access (POSIX.1, 9.2.1)\"],posix_getgroups:[\"array posix_getgroups(void)\",\"Get supplementary group id's (POSIX.1, 4.2.3)\"],posix_getlogin:[\"string posix_getlogin(void)\",\"Get user name (POSIX.1, 4.2.4)\"],posix_getpgid:[\"int posix_getpgid(void)\",\"Get the process group id of the specified process (This is not a POSIX function, but a SVR4ism, so we compile conditionally)\"],posix_getpgrp:[\"int posix_getpgrp(void)\",\"Get current process group id (POSIX.1, 4.3.1)\"],posix_getpid:[\"int posix_getpid(void)\",\"Get the current process id (POSIX.1, 4.1.1)\"],posix_getppid:[\"int posix_getppid(void)\",\"Get the parent process id (POSIX.1, 4.1.1)\"],posix_getpwnam:[\"array posix_getpwnam(string groupname)\",\"User database access (POSIX.1, 9.2.2)\"],posix_getpwuid:[\"array posix_getpwuid(long uid)\",\"User database access (POSIX.1, 9.2.2)\"],posix_getrlimit:[\"array posix_getrlimit(void)\",\"Get system resource consumption limits (This is not a POSIX function, but a BSDism and a SVR4ism. We compile conditionally)\"],posix_getsid:[\"int posix_getsid(void)\",\"Get process group id of session leader (This is not a POSIX function, but a SVR4ism, so be compile conditionally)\"],posix_getuid:[\"int posix_getuid(void)\",\"Get the current user id (POSIX.1, 4.2.1)\"],posix_initgroups:[\"bool posix_initgroups(string name, int base_group_id)\",\"Calculate the group access list for the user specified in name.\"],posix_isatty:[\"bool posix_isatty(int fd)\",\"Determine if filedesc is a tty (POSIX.1, 4.7.1)\"],posix_kill:[\"bool posix_kill(int pid, int sig)\",\"Send a signal to a process (POSIX.1, 3.3.2)\"],posix_mkfifo:[\"bool posix_mkfifo(string pathname, int mode)\",\"Make a FIFO special file (POSIX.1, 5.4.2)\"],posix_mknod:[\"bool posix_mknod(string pathname, int mode [, int major [, int minor]])\",\"Make a special or ordinary file (POSIX.1)\"],posix_setegid:[\"bool posix_setegid(long uid)\",\"Set effective group id\"],posix_seteuid:[\"bool posix_seteuid(long uid)\",\"Set effective user id\"],posix_setgid:[\"bool posix_setgid(int uid)\",\"Set group id (POSIX.1, 4.2.2)\"],posix_setpgid:[\"bool posix_setpgid(int pid, int pgid)\",\"Set process group id for job control (POSIX.1, 4.3.3)\"],posix_setsid:[\"int posix_setsid(void)\",\"Create session and set process group id (POSIX.1, 4.3.2)\"],posix_setuid:[\"bool posix_setuid(long uid)\",\"Set user id (POSIX.1, 4.2.2)\"],posix_strerror:[\"string posix_strerror(int errno)\",\"Retrieve the system error message associated with the given errno.\"],posix_times:[\"array posix_times(void)\",\"Get process times (POSIX.1, 4.5.2)\"],posix_ttyname:[\"string posix_ttyname(int fd)\",\"Determine terminal device name (POSIX.1, 4.7.2)\"],posix_uname:[\"array posix_uname(void)\",\"Get system name (POSIX.1, 4.4.1)\"],pow:[\"number pow(number base, number exponent)\",\"Returns base raised to the power of exponent. Returns integer result when possible\"],preg_filter:[\"mixed preg_filter(mixed regex, mixed replace, mixed subject [, int limit [, int &count]])\",\"Perform Perl-style regular expression replacement and only return matches.\"],preg_grep:[\"array preg_grep(string regex, array input [, int flags])\",\"Searches array and returns entries which match regex\"],preg_last_error:[\"int preg_last_error()\",\"Returns the error code of the last regexp execution.\"],preg_match:[\"int preg_match(string pattern, string subject [, array &subpatterns [, int flags [, int offset]]])\",\"Perform a Perl-style regular expression match\"],preg_match_all:[\"int preg_match_all(string pattern, string subject, array &subpatterns [, int flags [, int offset]])\",\"Perform a Perl-style global regular expression match\"],preg_quote:[\"string preg_quote(string str [, string delim_char])\",\"Quote regular expression characters plus an optional character\"],preg_replace:[\"mixed preg_replace(mixed regex, mixed replace, mixed subject [, int limit [, int &count]])\",\"Perform Perl-style regular expression replacement.\"],preg_replace_callback:[\"mixed preg_replace_callback(mixed regex, mixed callback, mixed subject [, int limit [, int &count]])\",\"Perform Perl-style regular expression replacement using replacement callback.\"],preg_split:[\"array preg_split(string pattern, string subject [, int limit [, int flags]])\",\"Split string into an array using a perl-style regular expression as a delimiter\"],prev:[\"mixed prev(array array_arg)\",\"Move array argument's internal pointer to the previous element and return it\"],print:[\"int print(string arg)\",\"Output a string\"],print_r:[\"mixed print_r(mixed var [, bool return])\",\"Prints out or returns information about the specified variable\"],printf:[\"int printf(string format [, mixed arg1 [, mixed ...]])\",\"Output a formatted string\"],proc_close:[\"int proc_close(resource process)\",\"close a process opened by proc_open\"],proc_get_status:[\"array proc_get_status(resource process)\",\"get information about a process opened by proc_open\"],proc_nice:[\"bool proc_nice(int priority)\",\"Change the priority of the current process\"],proc_open:[\"resource proc_open(string command, array descriptorspec, array &pipes [, string cwd [, array env [, array other_options]]])\",\"Run a process with more control over it's file descriptors\"],proc_terminate:[\"bool proc_terminate(resource process [, long signal])\",\"kill a process opened by proc_open\"],property_exists:[\"bool property_exists(mixed object_or_class, string property_name)\",\"Checks if the object or class has a property\"],pspell_add_to_personal:[\"bool pspell_add_to_personal(int pspell, string word)\",\"Adds a word to a personal list\"],pspell_add_to_session:[\"bool pspell_add_to_session(int pspell, string word)\",\"Adds a word to the current session\"],pspell_check:[\"bool pspell_check(int pspell, string word)\",\"Returns true if word is valid\"],pspell_clear_session:[\"bool pspell_clear_session(int pspell)\",\"Clears the current session\"],pspell_config_create:[\"int pspell_config_create(string language [, string spelling [, string jargon [, string encoding]]])\",\"Create a new config to be used later to create a manager\"],pspell_config_data_dir:[\"bool pspell_config_data_dir(int conf, string directory)\",\"location of language data files\"],pspell_config_dict_dir:[\"bool pspell_config_dict_dir(int conf, string directory)\",\"location of the main word list\"],pspell_config_ignore:[\"bool pspell_config_ignore(int conf, int ignore)\",\"Ignore words <= n chars\"],pspell_config_mode:[\"bool pspell_config_mode(int conf, long mode)\",\"Select mode for config (PSPELL_FAST, PSPELL_NORMAL or PSPELL_BAD_SPELLERS)\"],pspell_config_personal:[\"bool pspell_config_personal(int conf, string personal)\",\"Use a personal dictionary for this config\"],pspell_config_repl:[\"bool pspell_config_repl(int conf, string repl)\",\"Use a personal dictionary with replacement pairs for this config\"],pspell_config_runtogether:[\"bool pspell_config_runtogether(int conf, bool runtogether)\",\"Consider run-together words as valid components\"],pspell_config_save_repl:[\"bool pspell_config_save_repl(int conf, bool save)\",\"Save replacement pairs when personal list is saved for this config\"],pspell_new:[\"int pspell_new(string language [, string spelling [, string jargon [, string encoding [, int mode]]]])\",\"Load a dictionary\"],pspell_new_config:[\"int pspell_new_config(int config)\",\"Load a dictionary based on the given config\"],pspell_new_personal:[\"int pspell_new_personal(string personal, string language [, string spelling [, string jargon [, string encoding [, int mode]]]])\",\"Load a dictionary with a personal wordlist\"],pspell_save_wordlist:[\"bool pspell_save_wordlist(int pspell)\",\"Saves the current (personal) wordlist\"],pspell_store_replacement:[\"bool pspell_store_replacement(int pspell, string misspell, string correct)\",\"Notify the dictionary of a user-selected replacement\"],pspell_suggest:[\"array pspell_suggest(int pspell, string word)\",\"Returns array of suggestions\"],putenv:[\"bool putenv(string setting)\",\"Set the value of an environment variable\"],quoted_printable_decode:[\"string quoted_printable_decode(string str)\",\"Convert a quoted-printable string to an 8 bit string\"],quoted_printable_encode:[\"string quoted_printable_encode(string str) */\",'PHP_FUNCTION(quoted_printable_encode) {  char *str, *new_str;  int str_len;  size_t new_str_len;   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, \"s\", &str, &str_len) != SUCCESS) {   return;  }   if (!str_len) {   RETURN_EMPTY_STRING();  }   new_str = (char *)php_quot_print_encode((unsigned char *)str, (size_t)str_len, &new_str_len);  RETURN_STRINGL(new_str, new_str_len, 0); } /* }}}'],quotemeta:[\"string quotemeta(string str)\",\"Quotes meta characters\"],rad2deg:[\"float rad2deg(float number)\",\"Converts the radian number to the equivalent number in degrees\"],rand:[\"int rand([int min, int max])\",\"Returns a random number\"],range:[\"array range(mixed low, mixed high[, int step])\",\"Create an array containing the range of integers or characters from low to high (inclusive)\"],rawurldecode:[\"string rawurldecode(string str)\",\"Decodes URL-encodes string\"],rawurlencode:[\"string rawurlencode(string str)\",\"URL-encodes string\"],readdir:[\"string readdir([resource dir_handle])\",\"Read directory entry from dir_handle\"],readfile:[\"int readfile(string filename [, bool use_include_path[, resource context]])\",\"Output a file or a URL\"],readgzfile:[\"int readgzfile(string filename [, int use_include_path])\",\"Output a .gz-file\"],readline:[\"string readline([string prompt])\",\"Reads a line\"],readline_add_history:[\"bool readline_add_history(string prompt)\",\"Adds a line to the history\"],readline_callback_handler_install:[\"void readline_callback_handler_install(string prompt, mixed callback)\",\"Initializes the readline callback interface and terminal, prints the prompt and returns immediately\"],readline_callback_handler_remove:[\"bool readline_callback_handler_remove()\",\"Removes a previously installed callback handler and restores terminal settings\"],readline_callback_read_char:[\"void readline_callback_read_char()\",\"Informs the readline callback interface that a character is ready for input\"],readline_clear_history:[\"bool readline_clear_history(void)\",\"Clears the history\"],readline_completion_function:[\"bool readline_completion_function(string funcname)\",\"Readline completion function?\"],readline_info:[\"mixed readline_info([string varname [, string newvalue]])\",\"Gets/sets various internal readline variables.\"],readline_list_history:[\"array readline_list_history(void)\",\"Lists the history\"],readline_on_new_line:[\"void readline_on_new_line(void)\",\"Inform readline that the cursor has moved to a new line\"],readline_read_history:[\"bool readline_read_history([string filename])\",\"Reads the history\"],readline_redisplay:[\"void readline_redisplay(void)\",\"Ask readline to redraw the display\"],readline_write_history:[\"bool readline_write_history([string filename])\",\"Writes the history\"],readlink:[\"string readlink(string filename)\",\"Return the target of a symbolic link\"],realpath:[\"string realpath(string path)\",\"Return the resolved path\"],realpath_cache_get:[\"bool realpath_cache_get()\",\"Get current size of realpath cache\"],realpath_cache_size:[\"bool realpath_cache_size()\",\"Get current size of realpath cache\"],recode_file:[\"bool recode_file(string request, resource input, resource output)\",\"Recode file input into file output according to request\"],recode_string:[\"string recode_string(string request, string str)\",\"Recode string str according to request string\"],register_shutdown_function:[\"void register_shutdown_function(string function_name)\",\"Register a user-level function to be called on request termination\"],register_tick_function:[\"bool register_tick_function(string function_name [, mixed arg [, mixed ... ]])\",\"Registers a tick callback function\"],rename:[\"bool rename(string old_name, string new_name[, resource context])\",\"Rename a file\"],require:[\"bool require(string path)\",\"Includes and evaluates the specified file, erroring if the file cannot be included\"],require_once:[\"bool require_once(string path)\",\"Includes and evaluates the specified file, erroring if the file cannot be included\"],reset:[\"mixed reset(array array_arg)\",\"Set array argument's internal pointer to the first element and return it\"],restore_error_handler:[\"void restore_error_handler(void)\",\"Restores the previously defined error handler function\"],restore_exception_handler:[\"void restore_exception_handler(void)\",\"Restores the previously defined exception handler function\"],restore_include_path:[\"void restore_include_path()\",\"Restore the value of the include_path configuration option\"],rewind:[\"bool rewind(resource fp)\",\"Rewind the position of a file pointer\"],rewinddir:[\"void rewinddir([resource dir_handle])\",\"Rewind dir_handle back to the start\"],rmdir:[\"bool rmdir(string dirname[, resource context])\",\"Remove a directory\"],round:[\"float round(float number [, int precision [, int mode]])\",\"Returns the number rounded to specified precision\"],rsort:[\"bool rsort(array &array_arg [, int sort_flags])\",\"Sort an array in reverse order\"],rtrim:[\"string rtrim(string str [, string character_mask])\",\"Removes trailing whitespace\"],scandir:[\"array scandir(string dir [, int sorting_order [, resource context]])\",\"List files & directories inside the specified path\"],sem_acquire:[\"bool sem_acquire(resource id)\",\"Acquires the semaphore with the given id, blocking if necessary\"],sem_get:[\"resource sem_get(int key [, int max_acquire [, int perm [, int auto_release]])\",\"Return an id for the semaphore with the given key, and allow max_acquire (default 1) processes to acquire it simultaneously\"],sem_release:[\"bool sem_release(resource id)\",\"Releases the semaphore with the given id\"],sem_remove:[\"bool sem_remove(resource id)\",\"Removes semaphore from Unix systems\"],serialize:[\"string serialize(mixed variable)\",\"Returns a string representation of variable (which can later be unserialized)\"],session_cache_expire:[\"int session_cache_expire([int new_cache_expire])\",\"Return the current cache expire. If new_cache_expire is given, the current cache_expire is replaced with new_cache_expire\"],session_cache_limiter:[\"string session_cache_limiter([string new_cache_limiter])\",\"Return the current cache limiter. If new_cache_limited is given, the current cache_limiter is replaced with new_cache_limiter\"],session_decode:[\"bool session_decode(string data)\",\"Deserializes data and reinitializes the variables\"],session_destroy:[\"bool session_destroy(void)\",\"Destroy the current session and all data associated with it\"],session_encode:[\"string session_encode(void)\",\"Serializes the current setup and returns the serialized representation\"],session_get_cookie_params:[\"array session_get_cookie_params(void)\",\"Return the session cookie parameters\"],session_id:[\"string session_id([string newid])\",\"Return the current session id. If newid is given, the session id is replaced with newid\"],session_is_registered:[\"bool session_is_registered(string varname)\",\"Checks if a variable is registered in session\"],session_module_name:[\"string session_module_name([string newname])\",\"Return the current module name used for accessing session data. If newname is given, the module name is replaced with newname\"],session_name:[\"string session_name([string newname])\",\"Return the current session name. If newname is given, the session name is replaced with newname\"],session_regenerate_id:[\"bool session_regenerate_id([bool delete_old_session])\",\"Update the current session id with a newly generated one. If delete_old_session is set to true, remove the old session.\"],session_register:[\"bool session_register(mixed var_names [, mixed ...])\",\"Adds varname(s) to the list of variables which are freezed at the session end\"],session_save_path:[\"string session_save_path([string newname])\",\"Return the current save path passed to module_name. If newname is given, the save path is replaced with newname\"],session_set_cookie_params:[\"void session_set_cookie_params(int lifetime [, string path [, string domain [, bool secure[, bool httponly]]]])\",\"Set session cookie parameters\"],session_set_save_handler:[\"void session_set_save_handler(string open, string close, string read, string write, string destroy, string gc)\",\"Sets user-level functions\"],session_start:[\"bool session_start(void)\",\"Begin session - reinitializes freezed variables, registers browsers etc\"],session_unregister:[\"bool session_unregister(string varname)\",\"Removes varname from the list of variables which are freezed at the session end\"],session_unset:[\"void session_unset(void)\",\"Unset all registered variables\"],session_write_close:[\"void session_write_close(void)\",\"Write session data and end session\"],set_error_handler:[\"string set_error_handler(string error_handler [, int error_types])\",\"Sets a user-defined error handler function.  Returns the previously defined error handler, or false on error\"],set_exception_handler:[\"string set_exception_handler(callable exception_handler)\",\"Sets a user-defined exception handler function.  Returns the previously defined exception handler, or false on error\"],set_include_path:[\"string set_include_path(string new_include_path)\",\"Sets the include_path configuration option\"],set_magic_quotes_runtime:[\"bool set_magic_quotes_runtime(int new_setting)\",\"Set the current active configuration setting of magic_quotes_runtime and return previous\"],set_time_limit:[\"bool set_time_limit(int seconds)\",\"Sets the maximum time a script can run\"],setcookie:[\"bool setcookie(string name [, string value [, int expires [, string path [, string domain [, bool secure[, bool httponly]]]]]])\",\"Send a cookie\"],setlocale:[\"string setlocale(mixed category, string locale [, string ...])\",\"Set locale information\"],setrawcookie:[\"bool setrawcookie(string name [, string value [, int expires [, string path [, string domain [, bool secure[, bool httponly]]]]]])\",\"Send a cookie with no url encoding of the value\"],settype:[\"bool settype(mixed var, string type)\",\"Set the type of the variable\"],sha1:[\"string sha1(string str [, bool raw_output])\",\"Calculate the sha1 hash of a string\"],sha1_file:[\"string sha1_file(string filename [, bool raw_output])\",\"Calculate the sha1 hash of given filename\"],shell_exec:[\"string shell_exec(string cmd)\",\"Execute command via shell and return complete output as string\"],shm_attach:[\"int shm_attach(int key [, int memsize [, int perm]])\",\"Creates or open a shared memory segment\"],shm_detach:[\"bool shm_detach(resource shm_identifier)\",\"Disconnects from shared memory segment\"],shm_get_var:[\"mixed shm_get_var(resource id, int variable_key)\",\"Returns a variable from shared memory\"],shm_has_var:[\"bool shm_has_var(resource id, int variable_key)\",\"Checks whether a specific entry exists\"],shm_put_var:[\"bool shm_put_var(resource shm_identifier, int variable_key, mixed variable)\",\"Inserts or updates a variable in shared memory\"],shm_remove:[\"bool shm_remove(resource shm_identifier)\",\"Removes shared memory from Unix systems\"],shm_remove_var:[\"bool shm_remove_var(resource id, int variable_key)\",\"Removes variable from shared memory\"],shmop_close:[\"void shmop_close (int shmid)\",\"closes a shared memory segment\"],shmop_delete:[\"bool shmop_delete (int shmid)\",\"mark segment for deletion\"],shmop_open:[\"int shmop_open (int key, string flags, int mode, int size)\",\"gets and attaches a shared memory segment\"],shmop_read:[\"string shmop_read (int shmid, int start, int count)\",\"reads from a shm segment\"],shmop_size:[\"int shmop_size (int shmid)\",\"returns the shm size\"],shmop_write:[\"int shmop_write (int shmid, string data, int offset)\",\"writes to a shared memory segment\"],shuffle:[\"bool shuffle(array array_arg)\",\"Randomly shuffle the contents of an array\"],similar_text:[\"int similar_text(string str1, string str2 [, float percent])\",\"Calculates the similarity between two strings\"],simplexml_import_dom:[\"simplemxml_element simplexml_import_dom(domNode node [, string class_name])\",\"Get a simplexml_element object from dom to allow for processing\"],simplexml_load_file:[\"simplemxml_element simplexml_load_file(string filename [, string class_name [, int options [, string ns [, bool is_prefix]]]])\",\"Load a filename and return a simplexml_element object to allow for processing\"],simplexml_load_string:[\"simplemxml_element simplexml_load_string(string data [, string class_name [, int options [, string ns [, bool is_prefix]]]])\",\"Load a string and return a simplexml_element object to allow for processing\"],sin:[\"float sin(float number)\",\"Returns the sine of the number in radians\"],sinh:[\"float sinh(float number)\",\"Returns the hyperbolic sine of the number, defined as (exp(number) - exp(-number))/2\"],sleep:[\"void sleep(int seconds)\",\"Delay for a given number of seconds\"],smfi_addheader:[\"bool smfi_addheader(string headerf, string headerv)\",\"Adds a header to the current message.\"],smfi_addrcpt:[\"bool smfi_addrcpt(string rcpt)\",\"Add a recipient to the message envelope.\"],smfi_chgheader:[\"bool smfi_chgheader(string headerf, string headerv)\",\"Changes a header's value for the current message.\"],smfi_delrcpt:[\"bool smfi_delrcpt(string rcpt)\",\"Removes the named recipient from the current message's envelope.\"],smfi_getsymval:[\"string smfi_getsymval(string macro)\",\"Returns the value of the given macro or NULL if the macro is not defined.\"],smfi_replacebody:[\"bool smfi_replacebody(string body)\",\"Replaces the body of the current message. If called more than once,    subsequent calls result in data being appended to the new body.\"],smfi_setflags:[\"void smfi_setflags(long flags)\",\"Sets the flags describing the actions the filter may take.\"],smfi_setreply:[\"bool smfi_setreply(string rcode, string xcode, string message)\",\"Directly set the SMTP error reply code for this connection.    This code will be used on subsequent error replies resulting from actions taken by this filter.\"],smfi_settimeout:[\"void smfi_settimeout(long timeout)\",\"Sets the number of seconds libmilter will wait for an MTA connection before timing out a socket.\"],snmp2_get:[\"string snmp2_get(string host, string community, string object_id [, int timeout [, int retries]])\",\"Fetch a SNMP object\"],snmp2_getnext:[\"string snmp2_getnext(string host, string community, string object_id [, int timeout [, int retries]])\",\"Fetch a SNMP object\"],snmp2_real_walk:[\"array snmp2_real_walk(string host, string community, string object_id [, int timeout [, int retries]])\",\"Return all objects including their respective object id withing the specified one\"],snmp2_set:[\"int snmp2_set(string host, string community, string object_id, string type, mixed value [, int timeout [, int retries]])\",\"Set the value of a SNMP object\"],snmp2_walk:[\"array snmp2_walk(string host, string community, string object_id [, int timeout [, int retries]])\",\"Return all objects under the specified object id\"],snmp3_get:[\"int snmp3_get(string host, string sec_name, string sec_level, string auth_protocol, string auth_passphrase, string priv_protocol, string priv_passphrase, string object_id [, int timeout [, int retries]])\",\"Fetch the value of a SNMP object\"],snmp3_getnext:[\"int snmp3_getnext(string host, string sec_name, string sec_level, string auth_protocol, string auth_passphrase, string priv_protocol, string priv_passphrase, string object_id [, int timeout [, int retries]])\",\"Fetch the value of a SNMP object\"],snmp3_real_walk:[\"int snmp3_real_walk(string host, string sec_name, string sec_level, string auth_protocol, string auth_passphrase, string priv_protocol, string priv_passphrase, string object_id [, int timeout [, int retries]])\",\"Fetch the value of a SNMP object\"],snmp3_set:[\"int snmp3_set(string host, string sec_name, string sec_level, string auth_protocol, string auth_passphrase, string priv_protocol, string priv_passphrase, string object_id, string type, mixed value [, int timeout [, int retries]])\",\"Fetch the value of a SNMP object\"],snmp3_walk:[\"int snmp3_walk(string host, string sec_name, string sec_level, string auth_protocol, string auth_passphrase, string priv_protocol, string priv_passphrase, string object_id [, int timeout [, int retries]])\",\"Fetch the value of a SNMP object\"],snmp_get_quick_print:[\"bool snmp_get_quick_print(void)\",\"Return the current status of quick_print\"],snmp_get_valueretrieval:[\"int snmp_get_valueretrieval()\",\"Return the method how the SNMP values will be returned\"],snmp_read_mib:[\"int snmp_read_mib(string filename)\",\"Reads and parses a MIB file into the active MIB tree.\"],snmp_set_enum_print:[\"void snmp_set_enum_print(int enum_print)\",\"Return all values that are enums with their enum value instead of the raw integer\"],snmp_set_oid_output_format:[\"void snmp_set_oid_output_format(int oid_format)\",\"Set the OID output format.\"],snmp_set_quick_print:[\"void snmp_set_quick_print(int quick_print)\",\"Return all objects including their respective object id withing the specified one\"],snmp_set_valueretrieval:[\"void snmp_set_valueretrieval(int method)\",\"Specify the method how the SNMP values will be returned\"],snmpget:[\"string snmpget(string host, string community, string object_id [, int timeout [, int retries]])\",\"Fetch a SNMP object\"],snmpgetnext:[\"string snmpgetnext(string host, string community, string object_id [, int timeout [, int retries]])\",\"Fetch a SNMP object\"],snmprealwalk:[\"array snmprealwalk(string host, string community, string object_id [, int timeout [, int retries]])\",\"Return all objects including their respective object id withing the specified one\"],snmpset:[\"int snmpset(string host, string community, string object_id, string type, mixed value [, int timeout [, int retries]])\",\"Set the value of a SNMP object\"],snmpwalk:[\"array snmpwalk(string host, string community, string object_id [, int timeout [, int retries]])\",\"Return all objects under the specified object id\"],socket_accept:[\"resource socket_accept(resource socket)\",\"Accepts a connection on the listening socket fd\"],socket_bind:[\"bool socket_bind(resource socket, string addr [, int port])\",\"Binds an open socket to a listening port, port is only specified in AF_INET family.\"],socket_clear_error:[\"void socket_clear_error([resource socket])\",\"Clears the error on the socket or the last error code.\"],socket_close:[\"void socket_close(resource socket)\",\"Closes a file descriptor\"],socket_connect:[\"bool socket_connect(resource socket, string addr [, int port])\",\"Opens a connection to addr:port on the socket specified by socket\"],socket_create:[\"resource socket_create(int domain, int type, int protocol)\",\"Creates an endpoint for communication in the domain specified by domain, of type specified by type\"],socket_create_listen:[\"resource socket_create_listen(int port[, int backlog])\",\"Opens a socket on port to accept connections\"],socket_create_pair:[\"bool socket_create_pair(int domain, int type, int protocol, array &fd)\",\"Creates a pair of indistinguishable sockets and stores them in fds.\"],socket_get_option:[\"mixed socket_get_option(resource socket, int level, int optname)\",\"Gets socket options for the socket\"],socket_getpeername:[\"bool socket_getpeername(resource socket, string &addr[, int &port])\",\"Queries the remote side of the given socket which may either result in host/port or in a UNIX filesystem path, dependent on its type.\"],socket_getsockname:[\"bool socket_getsockname(resource socket, string &addr[, int &port])\",\"Queries the remote side of the given socket which may either result in host/port or in a UNIX filesystem path, dependent on its type.\"],socket_last_error:[\"int socket_last_error([resource socket])\",\"Returns the last socket error (either the last used or the provided socket resource)\"],socket_listen:[\"bool socket_listen(resource socket[, int backlog])\",\"Sets the maximum number of connections allowed to be waited for on the socket specified by fd\"],socket_read:[\"string socket_read(resource socket, int length [, int type])\",\"Reads a maximum of length bytes from socket\"],socket_recv:[\"int socket_recv(resource socket, string &buf, int len, int flags)\",\"Receives data from a connected socket\"],socket_recvfrom:[\"int socket_recvfrom(resource socket, string &buf, int len, int flags, string &name [, int &port])\",\"Receives data from a socket, connected or not\"],socket_select:[\"int socket_select(array &read_fds, array &write_fds, array &except_fds, int tv_sec[, int tv_usec])\",\"Runs the select() system call on the sets mentioned with a timeout specified by tv_sec and tv_usec\"],socket_send:[\"int socket_send(resource socket, string buf, int len, int flags)\",\"Sends data to a connected socket\"],socket_sendto:[\"int socket_sendto(resource socket, string buf, int len, int flags, string addr [, int port])\",\"Sends a message to a socket, whether it is connected or not\"],socket_set_block:[\"bool socket_set_block(resource socket)\",\"Sets blocking mode on a socket resource\"],socket_set_nonblock:[\"bool socket_set_nonblock(resource socket)\",\"Sets nonblocking mode on a socket resource\"],socket_set_option:[\"bool socket_set_option(resource socket, int level, int optname, int|array optval)\",\"Sets socket options for the socket\"],socket_shutdown:[\"bool socket_shutdown(resource socket[, int how])\",\"Shuts down a socket for receiving, sending, or both.\"],socket_strerror:[\"string socket_strerror(int errno)\",\"Returns a string describing an error\"],socket_write:[\"int socket_write(resource socket, string buf[, int length])\",\"Writes the buffer to the socket resource, length is optional\"],solid_fetch_prev:[\"bool solid_fetch_prev(resource result_id)\",\"\"],sort:[\"bool sort(array &array_arg [, int sort_flags])\",\"Sort an array\"],soundex:[\"string soundex(string str)\",\"Calculate the soundex key of a string\"],spl_autoload:[\"void spl_autoload(string class_name [, string file_extensions])\",\"Default implementation for __autoload()\"],spl_autoload_call:[\"void spl_autoload_call(string class_name)\",\"Try all registerd autoload function to load the requested class\"],spl_autoload_extensions:[\"string spl_autoload_extensions([string file_extensions])\",\"Register and return default file extensions for spl_autoload\"],spl_autoload_functions:[\"false|array spl_autoload_functions()\",\"Return all registered __autoload() functionns\"],spl_autoload_register:['bool spl_autoload_register([mixed autoload_function = \"spl_autoload\" [, throw = true [, prepend]]])',\"Register given function as __autoload() implementation\"],spl_autoload_unregister:[\"bool spl_autoload_unregister(mixed autoload_function)\",\"Unregister given function as __autoload() implementation\"],spl_classes:[\"array spl_classes()\",\"Return an array containing the names of all clsses and interfaces defined in SPL\"],spl_object_hash:[\"string spl_object_hash(object obj)\",\"Return hash id for given object\"],split:[\"array split(string pattern, string string [, int limit])\",\"Split string into array by regular expression\"],spliti:[\"array spliti(string pattern, string string [, int limit])\",\"Split string into array by regular expression case-insensitive\"],sprintf:[\"string sprintf(string format [, mixed arg1 [, mixed ...]])\",\"Return a formatted string\"],sql_regcase:[\"string sql_regcase(string string)\",\"Make regular expression for case insensitive match\"],sqlite_array_query:[\"array sqlite_array_query(resource db, string query [ , int result_type [, bool decode_binary]])\",\"Executes a query against a given database and returns an array of arrays.\"],sqlite_busy_timeout:[\"void sqlite_busy_timeout(resource db, int ms)\",\"Set busy timeout duration. If ms <= 0, all busy handlers are disabled.\"],sqlite_changes:[\"int sqlite_changes(resource db)\",\"Returns the number of rows that were changed by the most recent SQL statement.\"],sqlite_close:[\"void sqlite_close(resource db)\",\"Closes an open sqlite database.\"],sqlite_column:[\"mixed sqlite_column(resource result, mixed index_or_name [, bool decode_binary])\",\"Fetches a column from the current row of a result set.\"],sqlite_create_aggregate:[\"bool sqlite_create_aggregate(resource db, string funcname, mixed step_func, mixed finalize_func[, long num_args])\",\"Registers an aggregate function for queries.\"],sqlite_create_function:[\"bool sqlite_create_function(resource db, string funcname, mixed callback[, long num_args])\",'Registers a \"regular\" function for queries.'],sqlite_current:[\"array sqlite_current(resource result [, int result_type [, bool decode_binary]])\",\"Fetches the current row from a result set as an array.\"],sqlite_error_string:[\"string sqlite_error_string(int error_code)\",\"Returns the textual description of an error code.\"],sqlite_escape_string:[\"string sqlite_escape_string(string item)\",\"Escapes a string for use as a query parameter.\"],sqlite_exec:[\"boolean sqlite_exec(string query, resource db[, string &error_message])\",\"Executes a result-less query against a given database\"],sqlite_factory:[\"object sqlite_factory(string filename [, int mode [, string &error_message]])\",\"Opens a SQLite database and creates an object for it. Will create the database if it does not exist.\"],sqlite_fetch_all:[\"array sqlite_fetch_all(resource result [, int result_type [, bool decode_binary]])\",\"Fetches all rows from a result set as an array of arrays.\"],sqlite_fetch_array:[\"array sqlite_fetch_array(resource result [, int result_type [, bool decode_binary]])\",\"Fetches the next row from a result set as an array.\"],sqlite_fetch_column_types:[\"resource sqlite_fetch_column_types(string table_name, resource db [, int result_type])\",\"Return an array of column types from a particular table.\"],sqlite_fetch_object:[\"object sqlite_fetch_object(resource result [, string class_name [, NULL|array ctor_params [, bool decode_binary]]])\",\"Fetches the next row from a result set as an object.\"],sqlite_fetch_single:[\"string sqlite_fetch_single(resource result [, bool decode_binary])\",\"Fetches the first column of a result set as a string.\"],sqlite_field_name:[\"string sqlite_field_name(resource result, int field_index)\",\"Returns the name of a particular field of a result set.\"],sqlite_has_prev:[\"bool sqlite_has_prev(resource result)\",\"* Returns whether a previous row is available.\"],sqlite_key:[\"int sqlite_key(resource result)\",\"Return the current row index of a buffered result.\"],sqlite_last_error:[\"int sqlite_last_error(resource db)\",\"Returns the error code of the last error for a database.\"],sqlite_last_insert_rowid:[\"int sqlite_last_insert_rowid(resource db)\",\"Returns the rowid of the most recently inserted row.\"],sqlite_libencoding:[\"string sqlite_libencoding()\",\"Returns the encoding (iso8859 or UTF-8) of the linked SQLite library.\"],sqlite_libversion:[\"string sqlite_libversion()\",\"Returns the version of the linked SQLite library.\"],sqlite_next:[\"bool sqlite_next(resource result)\",\"Seek to the next row number of a result set.\"],sqlite_num_fields:[\"int sqlite_num_fields(resource result)\",\"Returns the number of fields in a result set.\"],sqlite_num_rows:[\"int sqlite_num_rows(resource result)\",\"Returns the number of rows in a buffered result set.\"],sqlite_open:[\"resource sqlite_open(string filename [, int mode [, string &error_message]])\",\"Opens a SQLite database. Will create the database if it does not exist.\"],sqlite_popen:[\"resource sqlite_popen(string filename [, int mode [, string &error_message]])\",\"Opens a persistent handle to a SQLite database. Will create the database if it does not exist.\"],sqlite_prev:[\"bool sqlite_prev(resource result)\",\"* Seek to the previous row number of a result set.\"],sqlite_query:[\"resource sqlite_query(string query, resource db [, int result_type [, string &error_message]])\",\"Executes a query against a given database and returns a result handle.\"],sqlite_rewind:[\"bool sqlite_rewind(resource result)\",\"Seek to the first row number of a buffered result set.\"],sqlite_seek:[\"bool sqlite_seek(resource result, int row)\",\"Seek to a particular row number of a buffered result set.\"],sqlite_single_query:[\"array sqlite_single_query(resource db, string query [, bool first_row_only [, bool decode_binary]])\",\"Executes a query and returns either an array for one single column or the value of the first row.\"],sqlite_udf_decode_binary:[\"string sqlite_udf_decode_binary(string data)\",\"Decode binary encoding on a string parameter passed to an UDF.\"],sqlite_udf_encode_binary:[\"string sqlite_udf_encode_binary(string data)\",\"Apply binary encoding (if required) to a string to return from an UDF.\"],sqlite_unbuffered_query:[\"resource sqlite_unbuffered_query(string query, resource db [ , int result_type [, string &error_message]])\",\"Executes a query that does not prefetch and buffer all data.\"],sqlite_valid:[\"bool sqlite_valid(resource result)\",\"Returns whether more rows are available.\"],sqrt:[\"float sqrt(float number)\",\"Returns the square root of the number\"],srand:[\"void srand([int seed])\",\"Seeds random number generator\"],sscanf:[\"mixed sscanf(string str, string format [, string ...])\",\"Implements an ANSI C compatible sscanf\"],stat:[\"array stat(string filename)\",\"Give information about a file\"],str_getcsv:[\"array str_getcsv(string input[, string delimiter[, string enclosure[, string escape]]])\",\"Parse a CSV string into an array\"],str_ireplace:[\"mixed str_ireplace(mixed search, mixed replace, mixed subject [, int &replace_count])\",\"Replaces all occurrences of search in haystack with replace / case-insensitive\"],str_pad:[\"string str_pad(string input, int pad_length [, string pad_string [, int pad_type]])\",\"Returns input string padded on the left or right to specified length with pad_string\"],str_repeat:[\"string str_repeat(string input, int mult)\",\"Returns the input string repeat mult times\"],str_replace:[\"mixed str_replace(mixed search, mixed replace, mixed subject [, int &replace_count])\",\"Replaces all occurrences of search in haystack with replace\"],str_rot13:[\"string str_rot13(string str)\",\"Perform the rot13 transform on a string\"],str_shuffle:[\"void str_shuffle(string str)\",\"Shuffles string. One permutation of all possible is created\"],str_split:[\"array str_split(string str [, int split_length])\",\"Convert a string to an array. If split_length is specified, break the string down into chunks each split_length characters long.\"],str_word_count:[\"mixed str_word_count(string str, [int format [, string charlist]])\",'Counts the number of words inside a string. If format of 1 is specified,     then the function will return an array containing all the words     found inside the string. If format of 2 is specified, then the function     will return an associated array where the position of the word is the key     and the word itself is the value.          For the purpose of this function, \\'word\\' is defined as a locale dependent     string containing alphabetic characters, which also may contain, but not start     with \"\\'\" and \"-\" characters.'],strcasecmp:[\"int strcasecmp(string str1, string str2)\",\"Binary safe case-insensitive string comparison\"],strchr:[\"string strchr(string haystack, string needle)\",\"An alias for strstr\"],strcmp:[\"int strcmp(string str1, string str2)\",\"Binary safe string comparison\"],strcoll:[\"int strcoll(string str1, string str2)\",\"Compares two strings using the current locale\"],strcspn:[\"int strcspn(string str, string mask [, start [, len]])\",\"Finds length of initial segment consisting entirely of characters not found in mask. If start or/and length is provide works like strcspn(substr($s,$start,$len),$bad_chars)\"],stream_bucket_append:[\"void stream_bucket_append(resource brigade, resource bucket)\",\"Append bucket to brigade\"],stream_bucket_make_writeable:[\"object stream_bucket_make_writeable(resource brigade)\",\"Return a bucket object from the brigade for operating on\"],stream_bucket_new:[\"resource stream_bucket_new(resource stream, string buffer)\",\"Create a new bucket for use on the current stream\"],stream_bucket_prepend:[\"void stream_bucket_prepend(resource brigade, resource bucket)\",\"Prepend bucket to brigade\"],stream_context_create:[\"resource stream_context_create([array options[, array params]])\",\"Create a file context and optionally set parameters\"],stream_context_get_default:[\"resource stream_context_get_default([array options])\",\"Get a handle on the default file/stream context and optionally set parameters\"],stream_context_get_options:[\"array stream_context_get_options(resource context|resource stream)\",\"Retrieve options for a stream/wrapper/context\"],stream_context_get_params:[\"array stream_context_get_params(resource context|resource stream)\",\"Get parameters of a file context\"],stream_context_set_default:[\"resource stream_context_set_default(array options)\",\"Set default file/stream context, returns the context as a resource\"],stream_context_set_option:[\"bool stream_context_set_option(resource context|resource stream, string wrappername, string optionname, mixed value)\",\"Set an option for a wrapper\"],stream_context_set_params:[\"bool stream_context_set_params(resource context|resource stream, array options)\",\"Set parameters for a file context\"],stream_copy_to_stream:[\"long stream_copy_to_stream(resource source, resource dest [, long maxlen [, long pos]])\",\"Reads up to maxlen bytes from source stream and writes them to dest stream.\"],stream_filter_append:[\"resource stream_filter_append(resource stream, string filtername[, int read_write[, string filterparams]])\",\"Append a filter to a stream\"],stream_filter_prepend:[\"resource stream_filter_prepend(resource stream, string filtername[, int read_write[, string filterparams]])\",\"Prepend a filter to a stream\"],stream_filter_register:[\"bool stream_filter_register(string filtername, string classname)\",\"Registers a custom filter handler class\"],stream_filter_remove:[\"bool stream_filter_remove(resource stream_filter)\",\"Flushes any data in the filter's internal buffer, removes it from the chain, and frees the resource\"],stream_get_contents:[\"string stream_get_contents(resource source [, long maxlen [, long offset]])\",\"Reads all remaining bytes (or up to maxlen bytes) from a stream and returns them as a string.\"],stream_get_filters:[\"array stream_get_filters(void)\",\"Returns a list of registered filters\"],stream_get_line:[\"string stream_get_line(resource stream, int maxlen [, string ending])\",\"Read up to maxlen bytes from a stream or until the ending string is found\"],stream_get_meta_data:[\"array stream_get_meta_data(resource fp)\",\"Retrieves header/meta data from streams/file pointers\"],stream_get_transports:[\"array stream_get_transports()\",\"Retrieves list of registered socket transports\"],stream_get_wrappers:[\"array stream_get_wrappers()\",\"Retrieves list of registered stream wrappers\"],stream_is_local:[\"bool stream_is_local(resource stream|string url)\",\"\"],stream_resolve_include_path:[\"string stream_resolve_include_path(string filename)\",\"Determine what file will be opened by calls to fopen() with a relative path\"],stream_select:[\"int stream_select(array &read_streams, array &write_streams, array &except_streams, int tv_sec[, int tv_usec])\",\"Runs the select() system call on the sets of streams with a timeout specified by tv_sec and tv_usec\"],stream_set_blocking:[\"bool stream_set_blocking(resource socket, int mode)\",\"Set blocking/non-blocking mode on a socket or stream\"],stream_set_timeout:[\"bool stream_set_timeout(resource stream, int seconds [, int microseconds])\",\"Set timeout on stream read to seconds + microseonds\"],stream_set_write_buffer:[\"int stream_set_write_buffer(resource fp, int buffer)\",\"Set file write buffer\"],stream_socket_accept:[\"resource stream_socket_accept(resource serverstream, [ double timeout [, string &peername ]])\",\"Accept a client connection from a server socket\"],stream_socket_client:[\"resource stream_socket_client(string remoteaddress [, long &errcode [, string &errstring [, double timeout [, long flags [, resource context]]]]])\",\"Open a client connection to a remote address\"],stream_socket_enable_crypto:[\"int stream_socket_enable_crypto(resource stream, bool enable [, int cryptokind [, resource sessionstream]])\",\"Enable or disable a specific kind of crypto on the stream\"],stream_socket_get_name:[\"string stream_socket_get_name(resource stream, bool want_peer)\",\"Returns either the locally bound or remote name for a socket stream\"],stream_socket_pair:[\"array stream_socket_pair(int domain, int type, int protocol)\",\"Creates a pair of connected, indistinguishable socket streams\"],stream_socket_recvfrom:[\"string stream_socket_recvfrom(resource stream, long amount [, long flags [, string &remote_addr]])\",\"Receives data from a socket stream\"],stream_socket_sendto:[\"long stream_socket_sendto(resouce stream, string data [, long flags [, string target_addr]])\",\"Send data to a socket stream.  If target_addr is specified it must be in dotted quad (or [ipv6]) format\"],stream_socket_server:[\"resource stream_socket_server(string localaddress [, long &errcode [, string &errstring [, long flags [, resource context]]]])\",\"Create a server socket bound to localaddress\"],stream_socket_shutdown:[\"int stream_socket_shutdown(resource stream, int how)\",\"causes all or part of a full-duplex connection on the socket associated  with stream to be shut down.  If how is SHUT_RD,  further receptions will  be disallowed. If how is SHUT_WR, further transmissions will be disallowed.  If how is SHUT_RDWR,  further  receptions and transmissions will be  disallowed.\"],stream_supports_lock:[\"bool stream_supports_lock(resource stream)\",\"Tells wether the stream supports locking through flock().\"],stream_wrapper_register:[\"bool stream_wrapper_register(string protocol, string classname[, integer flags])\",\"Registers a custom URL protocol handler class\"],stream_wrapper_restore:[\"bool stream_wrapper_restore(string protocol)\",\"Restore the original protocol handler, overriding if necessary\"],stream_wrapper_unregister:[\"bool stream_wrapper_unregister(string protocol)\",\"Unregister a wrapper for the life of the current request.\"],strftime:[\"string strftime(string format [, int timestamp])\",\"Format a local time/date according to locale settings\"],strip_tags:[\"string strip_tags(string str [, string allowable_tags])\",\"Strips HTML and PHP tags from a string\"],stripcslashes:[\"string stripcslashes(string str)\",\"Strips backslashes from a string. Uses C-style conventions\"],stripos:[\"int stripos(string haystack, string needle [, int offset])\",\"Finds position of first occurrence of a string within another, case insensitive\"],stripslashes:[\"string stripslashes(string str)\",\"Strips backslashes from a string\"],stristr:[\"string stristr(string haystack, string needle[, bool part])\",\"Finds first occurrence of a string within another, case insensitive\"],strlen:[\"int strlen(string str)\",\"Get string length\"],strnatcasecmp:[\"int strnatcasecmp(string s1, string s2)\",\"Returns the result of case-insensitive string comparison using 'natural' algorithm\"],strnatcmp:[\"int strnatcmp(string s1, string s2)\",\"Returns the result of string comparison using 'natural' algorithm\"],strncasecmp:[\"int strncasecmp(string str1, string str2, int len)\",\"Binary safe string comparison\"],strncmp:[\"int strncmp(string str1, string str2, int len)\",\"Binary safe string comparison\"],strpbrk:[\"array strpbrk(string haystack, string char_list)\",\"Search a string for any of a set of characters\"],strpos:[\"int strpos(string haystack, string needle [, int offset])\",\"Finds position of first occurrence of a string within another\"],strptime:[\"string strptime(string timestamp, string format)\",\"Parse a time/date generated with strftime()\"],strrchr:[\"string strrchr(string haystack, string needle)\",\"Finds the last occurrence of a character in a string within another\"],strrev:[\"string strrev(string str)\",\"Reverse a string\"],strripos:[\"int strripos(string haystack, string needle [, int offset])\",\"Finds position of last occurrence of a string within another string\"],strrpos:[\"int strrpos(string haystack, string needle [, int offset])\",\"Finds position of last occurrence of a string within another string\"],strspn:[\"int strspn(string str, string mask [, start [, len]])\",\"Finds length of initial segment consisting entirely of characters found in mask. If start or/and length is provided works like strspn(substr($s,$start,$len),$good_chars)\"],strstr:[\"string strstr(string haystack, string needle[, bool part])\",\"Finds first occurrence of a string within another\"],strtok:[\"string strtok([string str,] string token)\",\"Tokenize a string\"],strtolower:[\"string strtolower(string str)\",\"Makes a string lowercase\"],strtotime:[\"int strtotime(string time [, int now ])\",\"Convert string representation of date and time to a timestamp\"],strtoupper:[\"string strtoupper(string str)\",\"Makes a string uppercase\"],strtr:[\"string strtr(string str, string from[, string to])\",\"Translates characters in str using given translation tables\"],strval:[\"string strval(mixed var)\",\"Get the string value of a variable\"],substr:[\"string substr(string str, int start [, int length])\",\"Returns part of a string\"],substr_compare:[\"int substr_compare(string main_str, string str, int offset [, int length [, bool case_sensitivity]])\",\"Binary safe optionally case insensitive comparison of 2 strings from an offset, up to length characters\"],substr_count:[\"int substr_count(string haystack, string needle [, int offset [, int length]])\",\"Returns the number of times a substring occurs in the string\"],substr_replace:[\"mixed substr_replace(mixed str, mixed repl, mixed start [, mixed length])\",\"Replaces part of a string with another string\"],sybase_affected_rows:[\"int sybase_affected_rows([resource link_id])\",\"Get number of affected rows in last query\"],sybase_close:[\"bool sybase_close([resource link_id])\",\"Close Sybase connection\"],sybase_connect:[\"int sybase_connect([string host [, string user [, string password [, string charset [, string appname [, bool new]]]]]])\",\"Open Sybase server connection\"],sybase_data_seek:[\"bool sybase_data_seek(resource result, int offset)\",\"Move internal row pointer\"],sybase_deadlock_retry_count:[\"void sybase_deadlock_retry_count(int retry_count)\",\"Sets deadlock retry count\"],sybase_fetch_array:[\"array sybase_fetch_array(resource result)\",\"Fetch row as array\"],sybase_fetch_assoc:[\"array sybase_fetch_assoc(resource result)\",\"Fetch row as array without numberic indices\"],sybase_fetch_field:[\"object sybase_fetch_field(resource result [, int offset])\",\"Get field information\"],sybase_fetch_object:[\"object sybase_fetch_object(resource result [, mixed object])\",\"Fetch row as object\"],sybase_fetch_row:[\"array sybase_fetch_row(resource result)\",\"Get row as enumerated array\"],sybase_field_seek:[\"bool sybase_field_seek(resource result, int offset)\",\"Set field offset\"],sybase_free_result:[\"bool sybase_free_result(resource result)\",\"Free result memory\"],sybase_get_last_message:[\"string sybase_get_last_message(void)\",\"Returns the last message from server (over min_message_severity)\"],sybase_min_client_severity:[\"void sybase_min_client_severity(int severity)\",\"Sets minimum client severity\"],sybase_min_server_severity:[\"void sybase_min_server_severity(int severity)\",\"Sets minimum server severity\"],sybase_num_fields:[\"int sybase_num_fields(resource result)\",\"Get number of fields in result\"],sybase_num_rows:[\"int sybase_num_rows(resource result)\",\"Get number of rows in result\"],sybase_pconnect:[\"int sybase_pconnect([string host [, string user [, string password [, string charset [, string appname]]]]])\",\"Open persistent Sybase connection\"],sybase_query:[\"int sybase_query(string query [, resource link_id])\",\"Send Sybase query\"],sybase_result:[\"string sybase_result(resource result, int row, mixed field)\",\"Get result data\"],sybase_select_db:[\"bool sybase_select_db(string database [, resource link_id])\",\"Select Sybase database\"],sybase_set_message_handler:[\"bool sybase_set_message_handler(mixed error_func [, resource connection])\",\"Set the error handler, to be called when a server message is raised.     If error_func is NULL the handler will be deleted\"],sybase_unbuffered_query:[\"int sybase_unbuffered_query(string query [, resource link_id])\",\"Send Sybase query\"],symlink:[\"int symlink(string target, string link)\",\"Create a symbolic link\"],sys_get_temp_dir:[\"string sys_get_temp_dir()\",\"Returns directory path used for temporary files\"],sys_getloadavg:[\"array sys_getloadavg()\",\"\"],syslog:[\"bool syslog(int priority, string message)\",\"Generate a system log message\"],system:[\"int system(string command [, int &return_value])\",\"Execute an external program and display output\"],tan:[\"float tan(float number)\",\"Returns the tangent of the number in radians\"],tanh:[\"float tanh(float number)\",\"Returns the hyperbolic tangent of the number, defined as sinh(number)/cosh(number)\"],tempnam:[\"string tempnam(string dir, string prefix)\",\"Create a unique filename in a directory\"],textdomain:[\"string textdomain(string domain)\",'Set the textdomain to \"domain\". Returns the current domain'],tidy_access_count:[\"int tidy_access_count()\",\"Returns the Number of Tidy accessibility warnings encountered for specified document.\"],tidy_clean_repair:[\"boolean tidy_clean_repair()\",\"Execute configured cleanup and repair operations on parsed markup\"],tidy_config_count:[\"int tidy_config_count()\",\"Returns the Number of Tidy configuration errors encountered for specified document.\"],tidy_diagnose:[\"boolean tidy_diagnose()\",\"Run configured diagnostics on parsed and repaired markup.\"],tidy_error_count:[\"int tidy_error_count()\",\"Returns the Number of Tidy errors encountered for specified document.\"],tidy_get_body:[\"TidyNode tidy_get_body(resource tidy)\",\"Returns a TidyNode Object starting from the <BODY> tag of the tidy parse tree\"],tidy_get_config:[\"array tidy_get_config()\",\"Get current Tidy configuarion\"],tidy_get_error_buffer:[\"string tidy_get_error_buffer([boolean detailed])\",\"Return warnings and errors which occured parsing the specified document\"],tidy_get_head:[\"TidyNode tidy_get_head()\",\"Returns a TidyNode Object starting from the <HEAD> tag of the tidy parse tree\"],tidy_get_html:[\"TidyNode tidy_get_html()\",\"Returns a TidyNode Object starting from the <HTML> tag of the tidy parse tree\"],tidy_get_html_ver:[\"int tidy_get_html_ver()\",\"Get the Detected HTML version for the specified document.\"],tidy_get_opt_doc:[\"string tidy_get_opt_doc(tidy resource, string optname)\",\"Returns the documentation for the given option name\"],tidy_get_output:[\"string tidy_get_output()\",\"Return a string representing the parsed tidy markup\"],tidy_get_release:[\"string tidy_get_release()\",\"Get release date (version) for Tidy library\"],tidy_get_root:[\"TidyNode tidy_get_root()\",\"Returns a TidyNode Object representing the root of the tidy parse tree\"],tidy_get_status:[\"int tidy_get_status()\",\"Get status of specfied document.\"],tidy_getopt:[\"mixed tidy_getopt(string option)\",\"Returns the value of the specified configuration option for the tidy document.\"],tidy_is_xhtml:[\"boolean tidy_is_xhtml()\",\"Indicates if the document is a XHTML document.\"],tidy_is_xml:[\"boolean tidy_is_xml()\",\"Indicates if the document is a generic (non HTML/XHTML) XML document.\"],tidy_parse_file:[\"boolean tidy_parse_file(string file [, mixed config_options [, string encoding [, bool use_include_path]]])\",\"Parse markup in file or URI\"],tidy_parse_string:[\"bool tidy_parse_string(string input [, mixed config_options [, string encoding]])\",\"Parse a document stored in a string\"],tidy_repair_file:[\"boolean tidy_repair_file(string filename [, mixed config_file [, string encoding [, bool use_include_path]]])\",\"Repair a file using an optionally provided configuration file\"],tidy_repair_string:[\"boolean tidy_repair_string(string data [, mixed config_file [, string encoding]])\",\"Repair a string using an optionally provided configuration file\"],tidy_warning_count:[\"int tidy_warning_count()\",\"Returns the Number of Tidy warnings encountered for specified document.\"],time:[\"int time(void)\",\"Return current UNIX timestamp\"],time_nanosleep:[\"mixed time_nanosleep(long seconds, long nanoseconds)\",\"Delay for a number of seconds and nano seconds\"],time_sleep_until:[\"mixed time_sleep_until(float timestamp)\",\"Make the script sleep until the specified time\"],timezone_abbreviations_list:[\"array timezone_abbreviations_list()\",\"Returns associative array containing dst, offset and the timezone name\"],timezone_identifiers_list:[\"array timezone_identifiers_list([long what[, string country]])\",\"Returns numerically index array with all timezone identifiers.\"],timezone_location_get:[\"array timezone_location_get()\",\"Returns location information for a timezone, including country code, latitude/longitude and comments\"],timezone_name_from_abbr:[\"string timezone_name_from_abbr(string abbr[, long gmtOffset[, long isdst]])\",\"Returns the timezone name from abbrevation\"],timezone_name_get:[\"string timezone_name_get(DateTimeZone object)\",\"Returns the name of the timezone.\"],timezone_offset_get:[\"long timezone_offset_get(DateTimeZone object, DateTime object)\",\"Returns the timezone offset.\"],timezone_open:[\"DateTimeZone timezone_open(string timezone)\",\"Returns new DateTimeZone object\"],timezone_transitions_get:[\"array timezone_transitions_get(DateTimeZone object [, long timestamp_begin [, long timestamp_end ]])\",\"Returns numerically indexed array containing associative array for all transitions in the specified range for the timezone.\"],timezone_version_get:[\"array timezone_version_get()\",\"Returns the Olson database version number.\"],tmpfile:[\"resource tmpfile(void)\",\"Create a temporary file that will be deleted automatically after use\"],token_get_all:[\"array token_get_all(string source)\",\"\"],token_name:[\"string token_name(int type)\",\"\"],touch:[\"bool touch(string filename [, int time [, int atime]])\",\"Set modification time of file\"],trigger_error:[\"void trigger_error(string messsage [, int error_type])\",\"Generates a user-level error/warning/notice message\"],trim:[\"string trim(string str [, string character_mask])\",\"Strips whitespace from the beginning and end of a string\"],uasort:[\"bool uasort(array array_arg, string cmp_function)\",\"Sort an array with a user-defined comparison function and maintain index association\"],ucfirst:[\"string ucfirst(string str)\",\"Make a string's first character lowercase\"],ucwords:[\"string ucwords(string str)\",\"Uppercase the first character of every word in a string\"],uksort:[\"bool uksort(array array_arg, string cmp_function)\",\"Sort an array by keys using a user-defined comparison function\"],umask:[\"int umask([int mask])\",\"Return or change the umask\"],uniqid:[\"string uniqid([string prefix [, bool more_entropy]])\",\"Generates a unique ID\"],unixtojd:[\"int unixtojd([int timestamp])\",\"Convert UNIX timestamp to Julian Day\"],unlink:[\"bool unlink(string filename[, context context])\",\"Delete a file\"],unpack:[\"array unpack(string format, string input)\",\"Unpack binary string into named array elements according to format argument\"],unregister_tick_function:[\"void unregister_tick_function(string function_name)\",\"Unregisters a tick callback function\"],unserialize:[\"mixed unserialize(string variable_representation)\",\"Takes a string representation of variable and recreates it\"],unset:[\"void unset (mixed var [, mixed var])\",\"Unset a given variable\"],urldecode:[\"string urldecode(string str)\",\"Decodes URL-encoded string\"],urlencode:[\"string urlencode(string str)\",\"URL-encodes string\"],usleep:[\"void usleep(int micro_seconds)\",\"Delay for a given number of micro seconds\"],usort:[\"bool usort(array array_arg, string cmp_function)\",\"Sort an array by values using a user-defined comparison function\"],utf8_decode:[\"string utf8_decode(string data)\",\"Converts a UTF-8 encoded string to ISO-8859-1\"],utf8_encode:[\"string utf8_encode(string data)\",\"Encodes an ISO-8859-1 string to UTF-8\"],var_dump:[\"void var_dump(mixed var)\",\"Dumps a string representation of variable to output\"],var_export:[\"mixed var_export(mixed var [, bool return])\",\"Outputs or returns a string representation of a variable\"],variant_abs:[\"mixed variant_abs(mixed left)\",\"Returns the absolute value of a variant\"],variant_add:[\"mixed variant_add(mixed left, mixed right)\",'\"Adds\" two variant values together and returns the result'],variant_and:[\"mixed variant_and(mixed left, mixed right)\",\"performs a bitwise AND operation between two variants and returns the result\"],variant_cast:[\"object variant_cast(object variant, int type)\",\"Convert a variant into a new variant object of another type\"],variant_cat:[\"mixed variant_cat(mixed left, mixed right)\",\"concatenates two variant values together and returns the result\"],variant_cmp:[\"int variant_cmp(mixed left, mixed right [, int lcid [, int flags]])\",\"Compares two variants\"],variant_date_from_timestamp:[\"object variant_date_from_timestamp(int timestamp)\",\"Returns a variant date representation of a unix timestamp\"],variant_date_to_timestamp:[\"int variant_date_to_timestamp(object variant)\",\"Converts a variant date/time value to unix timestamp\"],variant_div:[\"mixed variant_div(mixed left, mixed right)\",\"Returns the result from dividing two variants\"],variant_eqv:[\"mixed variant_eqv(mixed left, mixed right)\",\"Performs a bitwise equivalence on two variants\"],variant_fix:[\"mixed variant_fix(mixed left)\",\"Returns the integer part ? of a variant\"],variant_get_type:[\"int variant_get_type(object variant)\",\"Returns the VT_XXX type code for a variant\"],variant_idiv:[\"mixed variant_idiv(mixed left, mixed right)\",\"Converts variants to integers and then returns the result from dividing them\"],variant_imp:[\"mixed variant_imp(mixed left, mixed right)\",\"Performs a bitwise implication on two variants\"],variant_int:[\"mixed variant_int(mixed left)\",\"Returns the integer portion of a variant\"],variant_mod:[\"mixed variant_mod(mixed left, mixed right)\",\"Divides two variants and returns only the remainder\"],variant_mul:[\"mixed variant_mul(mixed left, mixed right)\",\"multiplies the values of the two variants and returns the result\"],variant_neg:[\"mixed variant_neg(mixed left)\",\"Performs logical negation on a variant\"],variant_not:[\"mixed variant_not(mixed left)\",\"Performs bitwise not negation on a variant\"],variant_or:[\"mixed variant_or(mixed left, mixed right)\",\"Performs a logical disjunction on two variants\"],variant_pow:[\"mixed variant_pow(mixed left, mixed right)\",\"Returns the result of performing the power function with two variants\"],variant_round:[\"mixed variant_round(mixed left, int decimals)\",\"Rounds a variant to the specified number of decimal places\"],variant_set:[\"void variant_set(object variant, mixed value)\",\"Assigns a new value for a variant object\"],variant_set_type:[\"void variant_set_type(object variant, int type)\",'Convert a variant into another type.  Variant is modified \"in-place\"'],variant_sub:[\"mixed variant_sub(mixed left, mixed right)\",\"subtracts the value of the right variant from the left variant value and returns the result\"],variant_xor:[\"mixed variant_xor(mixed left, mixed right)\",\"Performs a logical exclusion on two variants\"],version_compare:[\"int version_compare(string ver1, string ver2 [, string oper])\",'Compares two \"PHP-standardized\" version number strings'],vfprintf:[\"int vfprintf(resource stream, string format, array args)\",\"Output a formatted string into a stream\"],virtual:[\"bool virtual(string filename)\",\"Perform an Apache sub-request\"],vprintf:[\"int vprintf(string format, array args)\",\"Output a formatted string\"],vsprintf:[\"string vsprintf(string format, array args)\",\"Return a formatted string\"],wddx_add_vars:[\"int wddx_add_vars(resource packet_id,  mixed var_names [, mixed ...])\",\"Serializes given variables and adds them to packet given by packet_id\"],wddx_deserialize:[\"mixed wddx_deserialize(mixed packet)\",\"Deserializes given packet and returns a PHP value\"],wddx_packet_end:[\"string wddx_packet_end(resource packet_id)\",\"Ends specified WDDX packet and returns the string containing the packet\"],wddx_packet_start:[\"resource wddx_packet_start([string comment])\",\"Starts a WDDX packet with optional comment and returns the packet id\"],wddx_serialize_value:[\"string wddx_serialize_value(mixed var [, string comment])\",\"Creates a new packet and serializes the given value\"],wddx_serialize_vars:[\"string wddx_serialize_vars(mixed var_name [, mixed ...])\",\"Creates a new packet and serializes given variables into a struct\"],wordwrap:[\"string wordwrap(string str [, int width [, string break [, boolean cut]]])\",\"Wraps buffer to selected number of characters using string break char\"],xml_error_string:[\"string xml_error_string(int code)\",\"Get XML parser error string\"],xml_get_current_byte_index:[\"int xml_get_current_byte_index(resource parser)\",\"Get current byte index for an XML parser\"],xml_get_current_column_number:[\"int xml_get_current_column_number(resource parser)\",\"Get current column number for an XML parser\"],xml_get_current_line_number:[\"int xml_get_current_line_number(resource parser)\",\"Get current line number for an XML parser\"],xml_get_error_code:[\"int xml_get_error_code(resource parser)\",\"Get XML parser error code\"],xml_parse:[\"int xml_parse(resource parser, string data [, int isFinal])\",\"Start parsing an XML document\"],xml_parse_into_struct:[\"int xml_parse_into_struct(resource parser, string data, array &values [, array &index ])\",\"Parsing a XML document\"],xml_parser_create:[\"resource xml_parser_create([string encoding])\",\"Create an XML parser\"],xml_parser_create_ns:[\"resource xml_parser_create_ns([string encoding [, string sep]])\",\"Create an XML parser\"],xml_parser_free:[\"int xml_parser_free(resource parser)\",\"Free an XML parser\"],xml_parser_get_option:[\"int xml_parser_get_option(resource parser, int option)\",\"Get options from an XML parser\"],xml_parser_set_option:[\"int xml_parser_set_option(resource parser, int option, mixed value)\",\"Set options in an XML parser\"],xml_set_character_data_handler:[\"int xml_set_character_data_handler(resource parser, string hdl)\",\"Set up character data handler\"],xml_set_default_handler:[\"int xml_set_default_handler(resource parser, string hdl)\",\"Set up default handler\"],xml_set_element_handler:[\"int xml_set_element_handler(resource parser, string shdl, string ehdl)\",\"Set up start and end element handlers\"],xml_set_end_namespace_decl_handler:[\"int xml_set_end_namespace_decl_handler(resource parser, string hdl)\",\"Set up character data handler\"],xml_set_external_entity_ref_handler:[\"int xml_set_external_entity_ref_handler(resource parser, string hdl)\",\"Set up external entity reference handler\"],xml_set_notation_decl_handler:[\"int xml_set_notation_decl_handler(resource parser, string hdl)\",\"Set up notation declaration handler\"],xml_set_object:[\"int xml_set_object(resource parser, object &obj)\",\"Set up object which should be used for callbacks\"],xml_set_processing_instruction_handler:[\"int xml_set_processing_instruction_handler(resource parser, string hdl)\",\"Set up processing instruction (PI) handler\"],xml_set_start_namespace_decl_handler:[\"int xml_set_start_namespace_decl_handler(resource parser, string hdl)\",\"Set up character data handler\"],xml_set_unparsed_entity_decl_handler:[\"int xml_set_unparsed_entity_decl_handler(resource parser, string hdl)\",\"Set up unparsed entity declaration handler\"],xmlrpc_decode:[\"array xmlrpc_decode(string xml [, string encoding])\",\"Decodes XML into native PHP types\"],xmlrpc_decode_request:[\"array xmlrpc_decode_request(string xml, string& method [, string encoding])\",\"Decodes XML into native PHP types\"],xmlrpc_encode:[\"string xmlrpc_encode(mixed value)\",\"Generates XML for a PHP value\"],xmlrpc_encode_request:[\"string xmlrpc_encode_request(string method, mixed params [, array output_options])\",\"Generates XML for a method request\"],xmlrpc_get_type:[\"string xmlrpc_get_type(mixed value)\",\"Gets xmlrpc type for a PHP value. Especially useful for base64 and datetime strings\"],xmlrpc_is_fault:[\"bool xmlrpc_is_fault(array)\",\"Determines if an array value represents an XMLRPC fault.\"],xmlrpc_parse_method_descriptions:[\"array xmlrpc_parse_method_descriptions(string xml)\",\"Decodes XML into a list of method descriptions\"],xmlrpc_server_add_introspection_data:[\"int xmlrpc_server_add_introspection_data(resource server, array desc)\",\"Adds introspection documentation\"],xmlrpc_server_call_method:[\"mixed xmlrpc_server_call_method(resource server, string xml, mixed user_data [, array output_options])\",\"Parses XML requests and call methods\"],xmlrpc_server_create:[\"resource xmlrpc_server_create(void)\",\"Creates an xmlrpc server\"],xmlrpc_server_destroy:[\"int xmlrpc_server_destroy(resource server)\",\"Destroys server resources\"],xmlrpc_server_register_introspection_callback:[\"bool xmlrpc_server_register_introspection_callback(resource server, string function)\",\"Register a PHP function to generate documentation\"],xmlrpc_server_register_method:[\"bool xmlrpc_server_register_method(resource server, string method_name, string function)\",\"Register a PHP function to handle method matching method_name\"],xmlrpc_set_type:[\"bool xmlrpc_set_type(string value, string type)\",\"Sets xmlrpc type, base64 or datetime, for a PHP string value\"],xmlwriter_end_attribute:[\"bool xmlwriter_end_attribute(resource xmlwriter)\",\"End attribute - returns FALSE on error\"],xmlwriter_end_cdata:[\"bool xmlwriter_end_cdata(resource xmlwriter)\",\"End current CDATA - returns FALSE on error\"],xmlwriter_end_comment:[\"bool xmlwriter_end_comment(resource xmlwriter)\",\"Create end comment - returns FALSE on error\"],xmlwriter_end_document:[\"bool xmlwriter_end_document(resource xmlwriter)\",\"End current document - returns FALSE on error\"],xmlwriter_end_dtd:[\"bool xmlwriter_end_dtd(resource xmlwriter)\",\"End current DTD - returns FALSE on error\"],xmlwriter_end_dtd_attlist:[\"bool xmlwriter_end_dtd_attlist(resource xmlwriter)\",\"End current DTD AttList - returns FALSE on error\"],xmlwriter_end_dtd_element:[\"bool xmlwriter_end_dtd_element(resource xmlwriter)\",\"End current DTD element - returns FALSE on error\"],xmlwriter_end_dtd_entity:[\"bool xmlwriter_end_dtd_entity(resource xmlwriter)\",\"End current DTD Entity - returns FALSE on error\"],xmlwriter_end_element:[\"bool xmlwriter_end_element(resource xmlwriter)\",\"End current element - returns FALSE on error\"],xmlwriter_end_pi:[\"bool xmlwriter_end_pi(resource xmlwriter)\",\"End current PI - returns FALSE on error\"],xmlwriter_flush:[\"mixed xmlwriter_flush(resource xmlwriter [,bool empty])\",\"Output current buffer\"],xmlwriter_full_end_element:[\"bool xmlwriter_full_end_element(resource xmlwriter)\",\"End current element - returns FALSE on error\"],xmlwriter_open_memory:[\"resource xmlwriter_open_memory()\",\"Create new xmlwriter using memory for string output\"],xmlwriter_open_uri:[\"resource xmlwriter_open_uri(resource xmlwriter, string source)\",\"Create new xmlwriter using source uri for output\"],xmlwriter_output_memory:[\"string xmlwriter_output_memory(resource xmlwriter [,bool flush])\",\"Output current buffer as string\"],xmlwriter_set_indent:[\"bool xmlwriter_set_indent(resource xmlwriter, bool indent)\",\"Toggle indentation on/off - returns FALSE on error\"],xmlwriter_set_indent_string:[\"bool xmlwriter_set_indent_string(resource xmlwriter, string indentString)\",\"Set string used for indenting - returns FALSE on error\"],xmlwriter_start_attribute:[\"bool xmlwriter_start_attribute(resource xmlwriter, string name)\",\"Create start attribute - returns FALSE on error\"],xmlwriter_start_attribute_ns:[\"bool xmlwriter_start_attribute_ns(resource xmlwriter, string prefix, string name, string uri)\",\"Create start namespaced attribute - returns FALSE on error\"],xmlwriter_start_cdata:[\"bool xmlwriter_start_cdata(resource xmlwriter)\",\"Create start CDATA tag - returns FALSE on error\"],xmlwriter_start_comment:[\"bool xmlwriter_start_comment(resource xmlwriter)\",\"Create start comment - returns FALSE on error\"],xmlwriter_start_document:[\"bool xmlwriter_start_document(resource xmlwriter, string version, string encoding, string standalone)\",\"Create document tag - returns FALSE on error\"],xmlwriter_start_dtd:[\"bool xmlwriter_start_dtd(resource xmlwriter, string name, string pubid, string sysid)\",\"Create start DTD tag - returns FALSE on error\"],xmlwriter_start_dtd_attlist:[\"bool xmlwriter_start_dtd_attlist(resource xmlwriter, string name)\",\"Create start DTD AttList - returns FALSE on error\"],xmlwriter_start_dtd_element:[\"bool xmlwriter_start_dtd_element(resource xmlwriter, string name)\",\"Create start DTD element - returns FALSE on error\"],xmlwriter_start_dtd_entity:[\"bool xmlwriter_start_dtd_entity(resource xmlwriter, string name, bool isparam)\",\"Create start DTD Entity - returns FALSE on error\"],xmlwriter_start_element:[\"bool xmlwriter_start_element(resource xmlwriter, string name)\",\"Create start element tag - returns FALSE on error\"],xmlwriter_start_element_ns:[\"bool xmlwriter_start_element_ns(resource xmlwriter, string prefix, string name, string uri)\",\"Create start namespaced element tag - returns FALSE on error\"],xmlwriter_start_pi:[\"bool xmlwriter_start_pi(resource xmlwriter, string target)\",\"Create start PI tag - returns FALSE on error\"],xmlwriter_text:[\"bool xmlwriter_text(resource xmlwriter, string content)\",\"Write text - returns FALSE on error\"],xmlwriter_write_attribute:[\"bool xmlwriter_write_attribute(resource xmlwriter, string name, string content)\",\"Write full attribute - returns FALSE on error\"],xmlwriter_write_attribute_ns:[\"bool xmlwriter_write_attribute_ns(resource xmlwriter, string prefix, string name, string uri, string content)\",\"Write full namespaced attribute - returns FALSE on error\"],xmlwriter_write_cdata:[\"bool xmlwriter_write_cdata(resource xmlwriter, string content)\",\"Write full CDATA tag - returns FALSE on error\"],xmlwriter_write_comment:[\"bool xmlwriter_write_comment(resource xmlwriter, string content)\",\"Write full comment tag - returns FALSE on error\"],xmlwriter_write_dtd:[\"bool xmlwriter_write_dtd(resource xmlwriter, string name, string pubid, string sysid, string subset)\",\"Write full DTD tag - returns FALSE on error\"],xmlwriter_write_dtd_attlist:[\"bool xmlwriter_write_dtd_attlist(resource xmlwriter, string name, string content)\",\"Write full DTD AttList tag - returns FALSE on error\"],xmlwriter_write_dtd_element:[\"bool xmlwriter_write_dtd_element(resource xmlwriter, string name, string content)\",\"Write full DTD element tag - returns FALSE on error\"],xmlwriter_write_dtd_entity:[\"bool xmlwriter_write_dtd_entity(resource xmlwriter, string name, string content [, int pe [, string pubid [, string sysid [, string ndataid]]]])\",\"Write full DTD Entity tag - returns FALSE on error\"],xmlwriter_write_element:[\"bool xmlwriter_write_element(resource xmlwriter, string name[, string content])\",\"Write full element tag - returns FALSE on error\"],xmlwriter_write_element_ns:[\"bool xmlwriter_write_element_ns(resource xmlwriter, string prefix, string name, string uri[, string content])\",\"Write full namesapced element tag - returns FALSE on error\"],xmlwriter_write_pi:[\"bool xmlwriter_write_pi(resource xmlwriter, string target, string content)\",\"Write full PI tag - returns FALSE on error\"],xmlwriter_write_raw:[\"bool xmlwriter_write_raw(resource xmlwriter, string content)\",\"Write text - returns FALSE on error\"],xsl_xsltprocessor_get_parameter:[\"string xsl_xsltprocessor_get_parameter(string namespace, string name);\",\"\"],xsl_xsltprocessor_has_exslt_support:[\"bool xsl_xsltprocessor_has_exslt_support();\",\"\"],xsl_xsltprocessor_import_stylesheet:[\"void xsl_xsltprocessor_import_stylesheet(domdocument doc);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html# Since:\"],xsl_xsltprocessor_register_php_functions:[\"void xsl_xsltprocessor_register_php_functions([mixed $restrict]);\",\"\"],xsl_xsltprocessor_remove_parameter:[\"bool xsl_xsltprocessor_remove_parameter(string namespace, string name);\",\"\"],xsl_xsltprocessor_set_parameter:[\"bool xsl_xsltprocessor_set_parameter(string namespace, mixed name [, string value]);\",\"\"],xsl_xsltprocessor_set_profiling:[\"bool xsl_xsltprocessor_set_profiling(string filename) */\",'PHP_FUNCTION(xsl_xsltprocessor_set_profiling) {  zval *id;  xsl_object *intern;  char *filename = NULL;  int filename_len;  DOM_GET_THIS(id);   if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS() TSRMLS_CC, \"s!\", &filename, &filename_len) == SUCCESS) {   intern = (xsl_object *)zend_object_store_get_object(id TSRMLS_CC);   if (intern->profiling) {    efree(intern->profiling);   }   if (filename != NULL) {    intern->profiling = estrndup(filename,filename_len);   } else {    intern->profiling = NULL;   }   RETURN_TRUE;  } else {   WRONG_PARAM_COUNT;  } } /* }}} end xsl_xsltprocessor_set_profiling'],xsl_xsltprocessor_transform_to_doc:[\"domdocument xsl_xsltprocessor_transform_to_doc(domnode doc);\",\"URL: http://www.w3.org/TR/2003/WD-DOM-Level-3-Core-20030226/DOM3-Core.html# Since:\"],xsl_xsltprocessor_transform_to_uri:[\"int xsl_xsltprocessor_transform_to_uri(domdocument doc, string uri);\",\"\"],xsl_xsltprocessor_transform_to_xml:[\"string xsl_xsltprocessor_transform_to_xml(domdocument doc);\",\"\"],zend_logo_guid:[\"string zend_logo_guid(void)\",\"Return the special ID used to request the Zend logo in phpinfo screens\"],zend_version:[\"string zend_version(void)\",\"Get the version of the Zend Engine\"],zip_close:[\"void zip_close(resource zip)\",\"Close a Zip archive\"],zip_entry_close:[\"void zip_entry_close(resource zip_ent)\",\"Close a zip entry\"],zip_entry_compressedsize:[\"int zip_entry_compressedsize(resource zip_entry)\",\"Return the compressed size of a ZZip entry\"],zip_entry_compressionmethod:[\"string zip_entry_compressionmethod(resource zip_entry)\",\"Return a string containing the compression method used on a particular entry\"],zip_entry_filesize:[\"int zip_entry_filesize(resource zip_entry)\",\"Return the actual filesize of a ZZip entry\"],zip_entry_name:[\"string zip_entry_name(resource zip_entry)\",\"Return the name given a ZZip entry\"],zip_entry_open:[\"bool zip_entry_open(resource zip_dp, resource zip_entry [, string mode])\",\"Open a Zip File, pointed by the resource entry\"],zip_entry_read:[\"mixed zip_entry_read(resource zip_entry [, int len])\",\"Read from an open directory entry\"],zip_open:[\"resource zip_open(string filename)\",\"Create new zip using source uri for output\"],zip_read:[\"resource zip_read(resource zip)\",\"Returns the next file in the archive\"],zlib_get_coding_type:[\"string zlib_get_coding_type(void)\",\"Returns the coding type used for output compression\"]},i={$_COOKIE:{type:\"array\"},$_ENV:{type:\"array\"},$_FILES:{type:\"array\"},$_GET:{type:\"array\"},$_POST:{type:\"array\"},$_REQUEST:{type:\"array\"},$_SERVER:{type:\"array\",value:{DOCUMENT_ROOT:1,GATEWAY_INTERFACE:1,HTTP_ACCEPT:1,HTTP_ACCEPT_CHARSET:1,HTTP_ACCEPT_ENCODING:1,HTTP_ACCEPT_LANGUAGE:1,HTTP_CONNECTION:1,HTTP_HOST:1,HTTP_REFERER:1,HTTP_USER_AGENT:1,PATH_TRANSLATED:1,PHP_SELF:1,QUERY_STRING:1,REMOTE_ADDR:1,REMOTE_PORT:1,REQUEST_METHOD:1,REQUEST_URI:1,SCRIPT_FILENAME:1,SCRIPT_NAME:1,SERVER_ADMIN:1,SERVER_NAME:1,SERVER_PORT:1,SERVER_PROTOCOL:1,SERVER_SIGNATURE:1,SERVER_SOFTWARE:1}},$_SESSION:{type:\"array\"},$GLOBALS:{type:\"array\"}},o=function(){};(function(){this.getCompletions=function(e,t,n,r){var i=t.getTokenAt(n.row,n.column);if(!i)return[];if(i.type===\"identifier\")return this.getFunctionCompletions(e,t,n,r);if(s(i,\"variable\"))return this.getVariableCompletions(e,t,n,r);var o=t.getLine(n.row).substr(0,n.column);return i.type===\"string\"&&/(\\$[\\w]*)\\[[\"']([^'\"]*)$/i.test(o)?this.getArrayKeyCompletions(e,t,n,r):[]},this.getFunctionCompletions=function(e,t,n,i){var s=Object.keys(r);return s.map(function(e){return{caption:e,snippet:e+\"($0)\",meta:\"php function\",score:Number.MAX_VALUE,docHTML:r[e][1]}})},this.getVariableCompletions=function(e,t,n,r){var s=Object.keys(i);return s.map(function(e){return{caption:e,value:e,meta:\"php variable\",score:Number.MAX_VALUE}})},this.getArrayKeyCompletions=function(e,t,n,r){var s=t.getLine(n.row).substr(0,n.column),o=s.match(/(\\$[\\w]*)\\[[\"']([^'\"]*)$/i)[1];if(!i[o])return[];var u=[];return i[o].type===\"array\"&&i[o].value&&(u=Object.keys(i[o].value)),u.map(function(e){return{caption:e,value:e,meta:\"php array key\",score:Number.MAX_VALUE}})}}).call(o.prototype),t.PhpCompletions=o}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/javascript\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./behaviour/cstyle\").CstyleBehaviour,f=e(\"./folding/cstyle\").FoldMode,l=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new a,this.foldingRules=new f};r.inherits(l,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens,o=i.state;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"||e==\"no_regex\"){var u=t.match(/^.*(?:\\bcase\\b.*:|[\\{\\(\\[])\\s*$/);u&&(r+=n)}else if(e==\"doc-start\"){if(o==\"start\"||o==\"no_regex\")return\"\";var u=t.match(/^\\s*(\\/?)\\*/);u&&(u[1]&&(r+=\" \"),r+=\"* \")}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/javascript_worker\",\"JavaScriptWorker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/javascript\"}.call(l.prototype),t.Mode=l}),define(\"ace/mode/css_completions\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={background:{\"#$0\":1},\"background-color\":{\"#$0\":1,transparent:1,fixed:1},\"background-image\":{\"url('/$0')\":1},\"background-repeat\":{repeat:1,\"repeat-x\":1,\"repeat-y\":1,\"no-repeat\":1,inherit:1},\"background-position\":{bottom:2,center:2,left:2,right:2,top:2,inherit:2},\"background-attachment\":{scroll:1,fixed:1},\"background-size\":{cover:1,contain:1},\"background-clip\":{\"border-box\":1,\"padding-box\":1,\"content-box\":1},\"background-origin\":{\"border-box\":1,\"padding-box\":1,\"content-box\":1},border:{\"solid $0\":1,\"dashed $0\":1,\"dotted $0\":1,\"#$0\":1},\"border-color\":{\"#$0\":1},\"border-style\":{solid:2,dashed:2,dotted:2,\"double\":2,groove:2,hidden:2,inherit:2,inset:2,none:2,outset:2,ridged:2},\"border-collapse\":{collapse:1,separate:1},bottom:{px:1,em:1,\"%\":1},clear:{left:1,right:1,both:1,none:1},color:{\"#$0\":1,\"rgb(#$00,0,0)\":1},cursor:{\"default\":1,pointer:1,move:1,text:1,wait:1,help:1,progress:1,\"n-resize\":1,\"ne-resize\":1,\"e-resize\":1,\"se-resize\":1,\"s-resize\":1,\"sw-resize\":1,\"w-resize\":1,\"nw-resize\":1},display:{none:1,block:1,inline:1,\"inline-block\":1,\"table-cell\":1},\"empty-cells\":{show:1,hide:1},\"float\":{left:1,right:1,none:1},\"font-family\":{Arial:2,\"Comic Sans MS\":2,Consolas:2,\"Courier New\":2,Courier:2,Georgia:2,Monospace:2,\"Sans-Serif\":2,\"Segoe UI\":2,Tahoma:2,\"Times New Roman\":2,\"Trebuchet MS\":2,Verdana:1},\"font-size\":{px:1,em:1,\"%\":1},\"font-weight\":{bold:1,normal:1},\"font-style\":{italic:1,normal:1},\"font-variant\":{normal:1,\"small-caps\":1},height:{px:1,em:1,\"%\":1},left:{px:1,em:1,\"%\":1},\"letter-spacing\":{normal:1},\"line-height\":{normal:1},\"list-style-type\":{none:1,disc:1,circle:1,square:1,decimal:1,\"decimal-leading-zero\":1,\"lower-roman\":1,\"upper-roman\":1,\"lower-greek\":1,\"lower-latin\":1,\"upper-latin\":1,georgian:1,\"lower-alpha\":1,\"upper-alpha\":1},margin:{px:1,em:1,\"%\":1},\"margin-right\":{px:1,em:1,\"%\":1},\"margin-left\":{px:1,em:1,\"%\":1},\"margin-top\":{px:1,em:1,\"%\":1},\"margin-bottom\":{px:1,em:1,\"%\":1},\"max-height\":{px:1,em:1,\"%\":1},\"max-width\":{px:1,em:1,\"%\":1},\"min-height\":{px:1,em:1,\"%\":1},\"min-width\":{px:1,em:1,\"%\":1},overflow:{hidden:1,visible:1,auto:1,scroll:1},\"overflow-x\":{hidden:1,visible:1,auto:1,scroll:1},\"overflow-y\":{hidden:1,visible:1,auto:1,scroll:1},padding:{px:1,em:1,\"%\":1},\"padding-top\":{px:1,em:1,\"%\":1},\"padding-right\":{px:1,em:1,\"%\":1},\"padding-bottom\":{px:1,em:1,\"%\":1},\"padding-left\":{px:1,em:1,\"%\":1},\"page-break-after\":{auto:1,always:1,avoid:1,left:1,right:1},\"page-break-before\":{auto:1,always:1,avoid:1,left:1,right:1},position:{absolute:1,relative:1,fixed:1,\"static\":1},right:{px:1,em:1,\"%\":1},\"table-layout\":{fixed:1,auto:1},\"text-decoration\":{none:1,underline:1,\"line-through\":1,blink:1},\"text-align\":{left:1,right:1,center:1,justify:1},\"text-transform\":{capitalize:1,uppercase:1,lowercase:1,none:1},top:{px:1,em:1,\"%\":1},\"vertical-align\":{top:1,bottom:1},visibility:{hidden:1,visible:1},\"white-space\":{nowrap:1,normal:1,pre:1,\"pre-line\":1,\"pre-wrap\":1},width:{px:1,em:1,\"%\":1},\"word-spacing\":{normal:1},filter:{\"alpha(opacity=$0100)\":1},\"text-shadow\":{\"$02px 2px 2px #777\":1},\"text-overflow\":{\"ellipsis-word\":1,clip:1,ellipsis:1},\"-moz-border-radius\":1,\"-moz-border-radius-topright\":1,\"-moz-border-radius-bottomright\":1,\"-moz-border-radius-topleft\":1,\"-moz-border-radius-bottomleft\":1,\"-webkit-border-radius\":1,\"-webkit-border-top-right-radius\":1,\"-webkit-border-top-left-radius\":1,\"-webkit-border-bottom-right-radius\":1,\"-webkit-border-bottom-left-radius\":1,\"-moz-box-shadow\":1,\"-webkit-box-shadow\":1,transform:{\"rotate($00deg)\":1,\"skew($00deg)\":1},\"-moz-transform\":{\"rotate($00deg)\":1,\"skew($00deg)\":1},\"-webkit-transform\":{\"rotate($00deg)\":1,\"skew($00deg)\":1}},i=function(){};(function(){this.completionsDefined=!1,this.defineCompletions=function(){if(document){var e=document.createElement(\"c\").style;for(var t in e){if(typeof e[t]!=\"string\")continue;var n=t.replace(/[A-Z]/g,function(e){return\"-\"+e.toLowerCase()});r.hasOwnProperty(n)||(r[n]=1)}}this.completionsDefined=!0},this.getCompletions=function(e,t,n,r){this.completionsDefined||this.defineCompletions();var i=t.getTokenAt(n.row,n.column);if(!i)return[];if(e===\"ruleset\"){var s=t.getLine(n.row).substr(0,n.column);return/:[^;]+$/.test(s)?(/([\\w\\-]+):[^:]*$/.test(s),this.getPropertyValueCompletions(e,t,n,r)):this.getPropertyCompletions(e,t,n,r)}return[]},this.getPropertyCompletions=function(e,t,n,i){var s=Object.keys(r);return s.map(function(e){return{caption:e,snippet:e+\": $0\",meta:\"property\",score:Number.MAX_VALUE}})},this.getPropertyValueCompletions=function(e,t,n,i){var s=t.getLine(n.row).substr(0,n.column),o=(/([\\w\\-]+):[^:]*$/.exec(s)||{})[1];if(!o)return[];var u=[];return o in r&&typeof r[o]==\"object\"&&(u=Object.keys(r[o])),u.map(function(e){return{caption:e,snippet:e,meta:\"property value\",score:Number.MAX_VALUE}})}}).call(i.prototype),t.CssCompletions=i}),define(\"ace/mode/behaviour/css\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/mode/behaviour/cstyle\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"./cstyle\").CstyleBehaviour,o=e(\"../../token_iterator\").TokenIterator,u=function(){this.inherit(s),this.add(\"colon\",\"insertion\",function(e,t,n,r,i){if(i===\":\"){var s=n.getCursorPosition(),u=new o(r,s.row,s.column),a=u.getCurrentToken();a&&a.value.match(/\\s+/)&&(a=u.stepBackward());if(a&&a.type===\"support.type\"){var f=r.doc.getLine(s.row),l=f.substring(s.column,s.column+1);if(l===\":\")return{text:\"\",selection:[1,1]};if(!f.substring(s.column).match(/^\\s*;/))return{text:\":;\",selection:[1,1]}}}}),this.add(\"colon\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&s===\":\"){var u=n.getCursorPosition(),a=new o(r,u.row,u.column),f=a.getCurrentToken();f&&f.value.match(/\\s+/)&&(f=a.stepBackward());if(f&&f.type===\"support.type\"){var l=r.doc.getLine(i.start.row),c=l.substring(i.end.column,i.end.column+1);if(c===\";\")return i.end.column++,i}}}),this.add(\"semicolon\",\"insertion\",function(e,t,n,r,i){if(i===\";\"){var s=n.getCursorPosition(),o=r.doc.getLine(s.row),u=o.substring(s.column,s.column+1);if(u===\";\")return{text:\"\",selection:[1,1]}}})};r.inherits(u,s),t.CssBehaviour=u}),define(\"ace/mode/css\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/css_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/css_completions\",\"ace/mode/behaviour/css\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./css_highlight_rules\").CssHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./css_completions\").CssCompletions,f=e(\"./behaviour/css\").CssBehaviour,l=e(\"./folding/cstyle\").FoldMode,c=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new f,this.$completer=new a,this.foldingRules=new l};r.inherits(c,i),function(){this.foldingRules=\"cStyle\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e).tokens;if(i.length&&i[i.length-1].type==\"comment\")return r;var s=t.match(/^.*\\{\\s*$/);return s&&(r+=n),r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.getCompletions=function(e,t,n,r){return this.$completer.getCompletions(e,t,n,r)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/css_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/css\"}.call(c.prototype),t.Mode=c}),define(\"ace/mode/behaviour/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/token_iterator\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";function u(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"../../token_iterator\").TokenIterator,o=e(\"../../lib/lang\"),a=function(){this.add(\"string_dquotes\",\"insertion\",function(e,t,n,r,i){if(i=='\"'||i==\"'\"){var o=i,a=r.doc.getTextRange(n.getSelectionRange());if(a!==\"\"&&a!==\"'\"&&a!='\"'&&n.getWrapBehavioursEnabled())return{text:o+a+o,selection:!1};var f=n.getCursorPosition(),l=r.doc.getLine(f.row),c=l.substring(f.column,f.column+1),h=new s(r,f.row,f.column),p=h.getCurrentToken();if(c==o&&(u(p,\"attribute-value\")||u(p,\"string\")))return{text:\"\",selection:[1,1]};p||(p=h.stepBackward());if(!p)return;while(u(p,\"tag-whitespace\")||u(p,\"whitespace\"))p=h.stepBackward();var d=!c||c.match(/\\s/);if(u(p,\"attribute-equals\")&&(d||c==\">\")||u(p,\"decl-attribute-equals\")&&(d||c==\"?\"))return{text:o+o,selection:[1,1]}}}),this.add(\"string_dquotes\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&(s=='\"'||s==\"'\")){var o=r.doc.getLine(i.start.row),u=o.substring(i.start.column+1,i.start.column+2);if(u==s)return i.end.column++,i}}),this.add(\"autoclosing\",\"insertion\",function(e,t,n,r,i){if(i==\">\"){var o=n.getSelectionRange().start,a=new s(r,o.row,o.column),f=a.getCurrentToken()||a.stepBackward();if(!f||!(u(f,\"tag-name\")||u(f,\"tag-whitespace\")||u(f,\"attribute-name\")||u(f,\"attribute-equals\")||u(f,\"attribute-value\")))return;if(u(f,\"reference.attribute-value\"))return;if(u(f,\"attribute-value\")){var l=f.value.charAt(0);if(l=='\"'||l==\"'\"){var c=f.value.charAt(f.value.length-1),h=a.getCurrentTokenColumn()+f.value.length;if(h>o.column||h==o.column&&l!=c)return}}while(!u(f,\"tag-name\")){f=a.stepBackward();if(f.value==\"<\"){f=a.stepForward();break}}var p=a.getCurrentTokenRow(),d=a.getCurrentTokenColumn();if(u(a.stepBackward(),\"end-tag-open\"))return;var v=f.value;p==o.row&&(v=v.substring(0,o.column-d));if(this.voidElements.hasOwnProperty(v.toLowerCase()))return;return{text:\"></\"+v+\">\",selection:[1,1]}}}),this.add(\"autoindent\",\"insertion\",function(e,t,n,r,i){if(i==\"\\n\"){var o=n.getCursorPosition(),u=r.getLine(o.row),a=new s(r,o.row,o.column),f=a.getCurrentToken();if(f&&f.type.indexOf(\"tag-close\")!==-1){if(f.value==\"/>\")return;while(f&&f.type.indexOf(\"tag-name\")===-1)f=a.stepBackward();if(!f)return;var l=f.value,c=a.getCurrentTokenRow();f=a.stepBackward();if(!f||f.type.indexOf(\"end-tag\")!==-1)return;if(this.voidElements&&!this.voidElements[l]){var h=r.getTokenAt(o.row,o.column+1),u=r.getLine(c),p=this.$getIndent(u),d=p+r.getTabString();return h&&h.value===\"</\"?{text:\"\\n\"+d+\"\\n\"+p,selection:[1,d.length,1,d.length]}:{text:\"\\n\"+d}}}}})};r.inherits(a,i),t.XmlBehaviour=a}),define(\"ace/mode/folding/mixed\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=t.FoldMode=function(e,t){this.defaultMode=e,this.subModes=t};r.inherits(s,i),function(){this.$getMode=function(e){typeof e!=\"string\"&&(e=e[0]);for(var t in this.subModes)if(e.indexOf(t)===0)return this.subModes[t];return null},this.$tryMode=function(e,t,n,r){var i=this.$getMode(e);return i?i.getFoldWidget(t,n,r):\"\"},this.getFoldWidget=function(e,t,n){return this.$tryMode(e.getState(n-1),e,t,n)||this.$tryMode(e.getState(n),e,t,n)||this.defaultMode.getFoldWidget(e,t,n)},this.getFoldWidgetRange=function(e,t,n){var r=this.$getMode(e.getState(n-1));if(!r||!r.getFoldWidget(e,t,n))r=this.$getMode(e.getState(n));if(!r||!r.getFoldWidget(e,t,n))r=this.defaultMode;return r.getFoldWidgetRange(e,t,n)}}.call(s.prototype)}),define(\"ace/mode/folding/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/range\",\"ace/mode/folding/fold_mode\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";function l(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}var r=e(\"../../lib/oop\"),i=e(\"../../lib/lang\"),s=e(\"../../range\").Range,o=e(\"./fold_mode\").FoldMode,u=e(\"../../token_iterator\").TokenIterator,a=t.FoldMode=function(e,t){o.call(this),this.voidElements=e||{},this.optionalEndTags=r.mixin({},this.voidElements),t&&r.mixin(this.optionalEndTags,t)};r.inherits(a,o);var f=function(){this.tagName=\"\",this.closing=!1,this.selfClosing=!1,this.start={row:0,column:0},this.end={row:0,column:0}};(function(){this.getFoldWidget=function(e,t,n){var r=this._getFirstTagInLine(e,n);return r?r.closing||!r.tagName&&r.selfClosing?t==\"markbeginend\"?\"end\":\"\":!r.tagName||r.selfClosing||this.voidElements.hasOwnProperty(r.tagName.toLowerCase())?\"\":this._findEndTagInLine(e,n,r.tagName,r.end.column)?\"\":\"start\":\"\"},this._getFirstTagInLine=function(e,t){var n=e.getTokens(t),r=new f;for(var i=0;i<n.length;i++){var s=n[i];if(l(s,\"tag-open\")){r.end.column=r.start.column+s.value.length,r.closing=l(s,\"end-tag-open\"),s=n[++i];if(!s)return null;r.tagName=s.value,r.end.column+=s.value.length;for(i++;i<n.length;i++){s=n[i],r.end.column+=s.value.length;if(l(s,\"tag-close\")){r.selfClosing=s.value==\"/>\";break}}return r}if(l(s,\"tag-close\"))return r.selfClosing=s.value==\"/>\",r;r.start.column+=s.value.length}return null},this._findEndTagInLine=function(e,t,n,r){var i=e.getTokens(t),s=0;for(var o=0;o<i.length;o++){var u=i[o];s+=u.value.length;if(s<r)continue;if(l(u,\"end-tag-open\")){u=i[o+1];if(u&&u.value==n)return!0}}return!1},this._readTagForward=function(e){var t=e.getCurrentToken();if(!t)return null;var n=new f;do if(l(t,\"tag-open\"))n.closing=l(t,\"end-tag-open\"),n.start.row=e.getCurrentTokenRow(),n.start.column=e.getCurrentTokenColumn();else if(l(t,\"tag-name\"))n.tagName=t.value;else if(l(t,\"tag-close\"))return n.selfClosing=t.value==\"/>\",n.end.row=e.getCurrentTokenRow(),n.end.column=e.getCurrentTokenColumn()+t.value.length,e.stepForward(),n;while(t=e.stepForward());return null},this._readTagBackward=function(e){var t=e.getCurrentToken();if(!t)return null;var n=new f;do{if(l(t,\"tag-open\"))return n.closing=l(t,\"end-tag-open\"),n.start.row=e.getCurrentTokenRow(),n.start.column=e.getCurrentTokenColumn(),e.stepBackward(),n;l(t,\"tag-name\")?n.tagName=t.value:l(t,\"tag-close\")&&(n.selfClosing=t.value==\"/>\",n.end.row=e.getCurrentTokenRow(),n.end.column=e.getCurrentTokenColumn()+t.value.length)}while(t=e.stepBackward());return null},this._pop=function(e,t){while(e.length){var n=e[e.length-1];if(!t||n.tagName==t.tagName)return e.pop();if(this.optionalEndTags.hasOwnProperty(n.tagName)){e.pop();continue}return null}},this.getFoldWidgetRange=function(e,t,n){var r=this._getFirstTagInLine(e,n);if(!r)return null;var i=r.closing||r.selfClosing,o=[],a;if(!i){var f=new u(e,n,r.start.column),l={row:n,column:r.start.column+r.tagName.length+2};r.start.row==r.end.row&&(l.column=r.end.column);while(a=this._readTagForward(f)){if(a.selfClosing){if(!o.length)return a.start.column+=a.tagName.length+2,a.end.column-=2,s.fromPoints(a.start,a.end);continue}if(a.closing){this._pop(o,a);if(o.length==0)return s.fromPoints(l,a.start)}else o.push(a)}}else{var f=new u(e,n,r.end.column),c={row:n,column:r.start.column};while(a=this._readTagBackward(f)){if(a.selfClosing){if(!o.length)return a.start.column+=a.tagName.length+2,a.end.column-=2,s.fromPoints(a.start,a.end);continue}if(!a.closing){this._pop(o,a);if(o.length==0)return a.start.column+=a.tagName.length+2,a.start.row==a.end.row&&a.start.column<a.end.column&&(a.start.column=a.end.column),s.fromPoints(a.start,c)}else o.push(a)}}}}).call(a.prototype)}),define(\"ace/mode/folding/html\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/mixed\",\"ace/mode/folding/xml\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./mixed\").FoldMode,s=e(\"./xml\").FoldMode,o=e(\"./cstyle\").FoldMode,u=t.FoldMode=function(e,t){i.call(this,new s(e,t),{\"js-\":new o,\"css-\":new o})};r.inherits(u,i)}),define(\"ace/mode/html_completions\",[\"require\",\"exports\",\"module\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";function f(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}function l(e,t){var n=new r(e,t.row,t.column),i=n.getCurrentToken();while(i&&!f(i,\"tag-name\"))i=n.stepBackward();if(i)return i.value}function c(e,t){var n=new r(e,t.row,t.column),i=n.getCurrentToken();while(i&&!f(i,\"attribute-name\"))i=n.stepBackward();if(i)return i.value}var r=e(\"../token_iterator\").TokenIterator,i=[\"accesskey\",\"class\",\"contenteditable\",\"contextmenu\",\"dir\",\"draggable\",\"dropzone\",\"hidden\",\"id\",\"inert\",\"itemid\",\"itemprop\",\"itemref\",\"itemscope\",\"itemtype\",\"lang\",\"spellcheck\",\"style\",\"tabindex\",\"title\",\"translate\"],s=[\"onabort\",\"onblur\",\"oncancel\",\"oncanplay\",\"oncanplaythrough\",\"onchange\",\"onclick\",\"onclose\",\"oncontextmenu\",\"oncuechange\",\"ondblclick\",\"ondrag\",\"ondragend\",\"ondragenter\",\"ondragleave\",\"ondragover\",\"ondragstart\",\"ondrop\",\"ondurationchange\",\"onemptied\",\"onended\",\"onerror\",\"onfocus\",\"oninput\",\"oninvalid\",\"onkeydown\",\"onkeypress\",\"onkeyup\",\"onload\",\"onloadeddata\",\"onloadedmetadata\",\"onloadstart\",\"onmousedown\",\"onmousemove\",\"onmouseout\",\"onmouseover\",\"onmouseup\",\"onmousewheel\",\"onpause\",\"onplay\",\"onplaying\",\"onprogress\",\"onratechange\",\"onreset\",\"onscroll\",\"onseeked\",\"onseeking\",\"onselect\",\"onshow\",\"onstalled\",\"onsubmit\",\"onsuspend\",\"ontimeupdate\",\"onvolumechange\",\"onwaiting\"],o=i.concat(s),u={html:{manifest:1},head:{},title:{},base:{href:1,target:1},link:{href:1,hreflang:1,rel:{stylesheet:1,icon:1},media:{all:1,screen:1,print:1},type:{\"text/css\":1,\"image/png\":1,\"image/jpeg\":1,\"image/gif\":1},sizes:1},meta:{\"http-equiv\":{\"content-type\":1},name:{description:1,keywords:1},content:{\"text/html; charset=UTF-8\":1},charset:1},style:{type:1,media:{all:1,screen:1,print:1},scoped:1},script:{charset:1,type:{\"text/javascript\":1},src:1,defer:1,async:1},noscript:{href:1},body:{onafterprint:1,onbeforeprint:1,onbeforeunload:1,onhashchange:1,onmessage:1,onoffline:1,onpopstate:1,onredo:1,onresize:1,onstorage:1,onundo:1,onunload:1},section:{},nav:{},article:{pubdate:1},aside:{},h1:{},h2:{},h3:{},h4:{},h5:{},h6:{},header:{},footer:{},address:{},main:{},p:{},hr:{},pre:{},blockquote:{cite:1},ol:{start:1,reversed:1},ul:{},li:{value:1},dl:{},dt:{},dd:{},figure:{},figcaption:{},div:{},a:{href:1,target:{_blank:1,top:1},ping:1,rel:{nofollow:1,alternate:1,author:1,bookmark:1,help:1,license:1,next:1,noreferrer:1,prefetch:1,prev:1,search:1,tag:1},media:1,hreflang:1,type:1},em:{},strong:{},small:{},s:{},cite:{},q:{cite:1},dfn:{},abbr:{},data:{},time:{datetime:1},code:{},\"var\":{},samp:{},kbd:{},sub:{},sup:{},i:{},b:{},u:{},mark:{},ruby:{},rt:{},rp:{},bdi:{},bdo:{},span:{},br:{},wbr:{},ins:{cite:1,datetime:1},del:{cite:1,datetime:1},img:{alt:1,src:1,height:1,width:1,usemap:1,ismap:1},iframe:{name:1,src:1,height:1,width:1,sandbox:{\"allow-same-origin\":1,\"allow-top-navigation\":1,\"allow-forms\":1,\"allow-scripts\":1},seamless:{seamless:1}},embed:{src:1,height:1,width:1,type:1},object:{param:1,data:1,type:1,height:1,width:1,usemap:1,name:1,form:1,classid:1},param:{name:1,value:1},video:{src:1,autobuffer:1,autoplay:{autoplay:1},loop:{loop:1},controls:{controls:1},width:1,height:1,poster:1,muted:{muted:1},preload:{auto:1,metadata:1,none:1}},audio:{src:1,autobuffer:1,autoplay:{autoplay:1},loop:{loop:1},controls:{controls:1},muted:{muted:1},preload:{auto:1,metadata:1,none:1}},source:{src:1,type:1,media:1},track:{kind:1,src:1,srclang:1,label:1,\"default\":1},canvas:{width:1,height:1},map:{name:1},area:{shape:1,coords:1,href:1,hreflang:1,alt:1,target:1,media:1,rel:1,ping:1,type:1},svg:{},math:{},table:{summary:1},caption:{},colgroup:{span:1},col:{span:1},tbody:{},thead:{},tfoot:{},tr:{},td:{headers:1,rowspan:1,colspan:1},th:{headers:1,rowspan:1,colspan:1,scope:1},form:{\"accept-charset\":1,action:1,autocomplete:1,enctype:{\"multipart/form-data\":1,\"application/x-www-form-urlencoded\":1},method:{get:1,post:1},name:1,novalidate:1,target:{_blank:1,top:1}},fieldset:{disabled:1,form:1,name:1},legend:{},label:{form:1,\"for\":1},input:{type:{text:1,password:1,hidden:1,checkbox:1,submit:1,radio:1,file:1,button:1,reset:1,image:31,color:1,date:1,datetime:1,\"datetime-local\":1,email:1,month:1,number:1,range:1,search:1,tel:1,time:1,url:1,week:1},accept:1,alt:1,autocomplete:{on:1,off:1},autofocus:{autofocus:1},checked:{checked:1},disabled:{disabled:1},form:1,formaction:1,formenctype:{\"application/x-www-form-urlencoded\":1,\"multipart/form-data\":1,\"text/plain\":1},formmethod:{get:1,post:1},formnovalidate:{formnovalidate:1},formtarget:{_blank:1,_self:1,_parent:1,_top:1},height:1,list:1,max:1,maxlength:1,min:1,multiple:{multiple:1},name:1,pattern:1,placeholder:1,readonly:{readonly:1},required:{required:1},size:1,src:1,step:1,width:1,files:1,value:1},button:{autofocus:1,disabled:{disabled:1},form:1,formaction:1,formenctype:1,formmethod:1,formnovalidate:1,formtarget:1,name:1,value:1,type:{button:1,submit:1}},select:{autofocus:1,disabled:1,form:1,multiple:{multiple:1},name:1,size:1,readonly:{readonly:1}},datalist:{},optgroup:{disabled:1,label:1},option:{disabled:1,selected:1,label:1,value:1},textarea:{autofocus:{autofocus:1},disabled:{disabled:1},form:1,maxlength:1,name:1,placeholder:1,readonly:{readonly:1},required:{required:1},rows:1,cols:1,wrap:{on:1,off:1,hard:1,soft:1}},keygen:{autofocus:1,challenge:{challenge:1},disabled:{disabled:1},form:1,keytype:{rsa:1,dsa:1,ec:1},name:1},output:{\"for\":1,form:1,name:1},progress:{value:1,max:1},meter:{value:1,min:1,max:1,low:1,high:1,optimum:1},details:{open:1},summary:{},command:{type:1,label:1,icon:1,disabled:1,checked:1,radiogroup:1,command:1},menu:{type:1,label:1},dialog:{open:1}},a=Object.keys(u),h=function(){};(function(){this.getCompletions=function(e,t,n,r){var i=t.getTokenAt(n.row,n.column);if(!i)return[];if(f(i,\"tag-name\")||f(i,\"tag-open\")||f(i,\"end-tag-open\"))return this.getTagCompletions(e,t,n,r);if(f(i,\"tag-whitespace\")||f(i,\"attribute-name\"))return this.getAttributeCompletions(e,t,n,r);if(f(i,\"attribute-value\"))return this.getAttributeValueCompletions(e,t,n,r);var s=t.getLine(n.row).substr(0,n.column);return/&[a-z]*$/i.test(s)?this.getHTMLEntityCompletions(e,t,n,r):[]},this.getTagCompletions=function(e,t,n,r){return a.map(function(e){return{value:e,meta:\"tag\",score:Number.MAX_VALUE}})},this.getAttributeCompletions=function(e,t,n,r){var i=l(t,n);if(!i)return[];var s=o;return i in u&&(s=s.concat(Object.keys(u[i]))),s.map(function(e){return{caption:e,snippet:e+'=\"$0\"',meta:\"attribute\",score:Number.MAX_VALUE}})},this.getAttributeValueCompletions=function(e,t,n,r){var i=l(t,n),s=c(t,n);if(!i)return[];var o=[];return i in u&&s in u[i]&&typeof u[i][s]==\"object\"&&(o=Object.keys(u[i][s])),o.map(function(e){return{caption:e,snippet:e,meta:\"attribute value\",score:Number.MAX_VALUE}})},this.getHTMLEntityCompletions=function(e,t,n,r){var i=[\"Aacute;\",\"aacute;\",\"Acirc;\",\"acirc;\",\"acute;\",\"AElig;\",\"aelig;\",\"Agrave;\",\"agrave;\",\"alefsym;\",\"Alpha;\",\"alpha;\",\"amp;\",\"and;\",\"ang;\",\"Aring;\",\"aring;\",\"asymp;\",\"Atilde;\",\"atilde;\",\"Auml;\",\"auml;\",\"bdquo;\",\"Beta;\",\"beta;\",\"brvbar;\",\"bull;\",\"cap;\",\"Ccedil;\",\"ccedil;\",\"cedil;\",\"cent;\",\"Chi;\",\"chi;\",\"circ;\",\"clubs;\",\"cong;\",\"copy;\",\"crarr;\",\"cup;\",\"curren;\",\"Dagger;\",\"dagger;\",\"dArr;\",\"darr;\",\"deg;\",\"Delta;\",\"delta;\",\"diams;\",\"divide;\",\"Eacute;\",\"eacute;\",\"Ecirc;\",\"ecirc;\",\"Egrave;\",\"egrave;\",\"empty;\",\"emsp;\",\"ensp;\",\"Epsilon;\",\"epsilon;\",\"equiv;\",\"Eta;\",\"eta;\",\"ETH;\",\"eth;\",\"Euml;\",\"euml;\",\"euro;\",\"exist;\",\"fnof;\",\"forall;\",\"frac12;\",\"frac14;\",\"frac34;\",\"frasl;\",\"Gamma;\",\"gamma;\",\"ge;\",\"gt;\",\"hArr;\",\"harr;\",\"hearts;\",\"hellip;\",\"Iacute;\",\"iacute;\",\"Icirc;\",\"icirc;\",\"iexcl;\",\"Igrave;\",\"igrave;\",\"image;\",\"infin;\",\"int;\",\"Iota;\",\"iota;\",\"iquest;\",\"isin;\",\"Iuml;\",\"iuml;\",\"Kappa;\",\"kappa;\",\"Lambda;\",\"lambda;\",\"lang;\",\"laquo;\",\"lArr;\",\"larr;\",\"lceil;\",\"ldquo;\",\"le;\",\"lfloor;\",\"lowast;\",\"loz;\",\"lrm;\",\"lsaquo;\",\"lsquo;\",\"lt;\",\"macr;\",\"mdash;\",\"micro;\",\"middot;\",\"minus;\",\"Mu;\",\"mu;\",\"nabla;\",\"nbsp;\",\"ndash;\",\"ne;\",\"ni;\",\"not;\",\"notin;\",\"nsub;\",\"Ntilde;\",\"ntilde;\",\"Nu;\",\"nu;\",\"Oacute;\",\"oacute;\",\"Ocirc;\",\"ocirc;\",\"OElig;\",\"oelig;\",\"Ograve;\",\"ograve;\",\"oline;\",\"Omega;\",\"omega;\",\"Omicron;\",\"omicron;\",\"oplus;\",\"or;\",\"ordf;\",\"ordm;\",\"Oslash;\",\"oslash;\",\"Otilde;\",\"otilde;\",\"otimes;\",\"Ouml;\",\"ouml;\",\"para;\",\"part;\",\"permil;\",\"perp;\",\"Phi;\",\"phi;\",\"Pi;\",\"pi;\",\"piv;\",\"plusmn;\",\"pound;\",\"Prime;\",\"prime;\",\"prod;\",\"prop;\",\"Psi;\",\"psi;\",\"quot;\",\"radic;\",\"rang;\",\"raquo;\",\"rArr;\",\"rarr;\",\"rceil;\",\"rdquo;\",\"real;\",\"reg;\",\"rfloor;\",\"Rho;\",\"rho;\",\"rlm;\",\"rsaquo;\",\"rsquo;\",\"sbquo;\",\"Scaron;\",\"scaron;\",\"sdot;\",\"sect;\",\"shy;\",\"Sigma;\",\"sigma;\",\"sigmaf;\",\"sim;\",\"spades;\",\"sub;\",\"sube;\",\"sum;\",\"sup;\",\"sup1;\",\"sup2;\",\"sup3;\",\"supe;\",\"szlig;\",\"Tau;\",\"tau;\",\"there4;\",\"Theta;\",\"theta;\",\"thetasym;\",\"thinsp;\",\"THORN;\",\"thorn;\",\"tilde;\",\"times;\",\"trade;\",\"Uacute;\",\"uacute;\",\"uArr;\",\"uarr;\",\"Ucirc;\",\"ucirc;\",\"Ugrave;\",\"ugrave;\",\"uml;\",\"upsih;\",\"Upsilon;\",\"upsilon;\",\"Uuml;\",\"uuml;\",\"weierp;\",\"Xi;\",\"xi;\",\"Yacute;\",\"yacute;\",\"yen;\",\"Yuml;\",\"yuml;\",\"Zeta;\",\"zeta;\",\"zwj;\",\"zwnj;\"];return i.map(function(e){return{caption:e,snippet:e,meta:\"html entity\",score:Number.MAX_VALUE}})}}).call(h.prototype),t.HtmlCompletions=h}),define(\"ace/mode/html\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text\",\"ace/mode/javascript\",\"ace/mode/css\",\"ace/mode/html_highlight_rules\",\"ace/mode/behaviour/xml\",\"ace/mode/folding/html\",\"ace/mode/html_completions\",\"ace/worker/worker_client\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text\").Mode,o=e(\"./javascript\").Mode,u=e(\"./css\").Mode,a=e(\"./html_highlight_rules\").HtmlHighlightRules,f=e(\"./behaviour/xml\").XmlBehaviour,l=e(\"./folding/html\").FoldMode,c=e(\"./html_completions\").HtmlCompletions,h=e(\"../worker/worker_client\").WorkerClient,p=[\"area\",\"base\",\"br\",\"col\",\"embed\",\"hr\",\"img\",\"input\",\"keygen\",\"link\",\"meta\",\"menuitem\",\"param\",\"source\",\"track\",\"wbr\"],d=[\"li\",\"dt\",\"dd\",\"p\",\"rt\",\"rp\",\"optgroup\",\"option\",\"colgroup\",\"td\",\"th\"],v=function(e){this.fragmentContext=e&&e.fragmentContext,this.HighlightRules=a,this.$behaviour=new f,this.$completer=new c,this.createModeDelegates({\"js-\":o,\"css-\":u}),this.foldingRules=new l(this.voidElements,i.arrayToMap(d))};r.inherits(v,s),function(){this.blockComment={start:\"<!--\",end:\"-->\"},this.voidElements=i.arrayToMap(p),this.getNextLineIndent=function(e,t,n){return this.$getIndent(t)},this.checkOutdent=function(e,t,n){return!1},this.getCompletions=function(e,t,n,r){return this.$completer.getCompletions(e,t,n,r)},this.createWorker=function(e){if(this.constructor!=v)return;var t=new h([\"ace\"],\"ace/mode/html_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),this.fragmentContext&&t.call(\"setOptions\",[{context:this.fragmentContext}]),t.on(\"error\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/html\"}.call(v.prototype),t.Mode=v}),define(\"ace/mode/php\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/php_highlight_rules\",\"ace/mode/php_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/range\",\"ace/worker/worker_client\",\"ace/mode/php_completions\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/cstyle\",\"ace/unicode\",\"ace/mode/html\",\"ace/mode/javascript\",\"ace/mode/css\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./php_highlight_rules\").PhpHighlightRules,o=e(\"./php_highlight_rules\").PhpLangHighlightRules,u=e(\"./matching_brace_outdent\").MatchingBraceOutdent,a=e(\"../range\").Range,f=e(\"../worker/worker_client\").WorkerClient,l=e(\"./php_completions\").PhpCompletions,c=e(\"./behaviour/cstyle\").CstyleBehaviour,h=e(\"./folding/cstyle\").FoldMode,p=e(\"../unicode\"),d=e(\"./html\").Mode,v=e(\"./javascript\").Mode,m=e(\"./css\").Mode,g=function(e){this.HighlightRules=o,this.$outdent=new u,this.$behaviour=new c,this.$completer=new l,this.foldingRules=new h};r.inherits(g,i),function(){this.tokenRe=new RegExp(\"^[\"+p.packages.L+p.packages.Mn+p.packages.Mc+p.packages.Nd+p.packages.Pc+\"_]+\",\"g\"),this.nonTokenRe=new RegExp(\"^(?:[^\"+p.packages.L+p.packages.Mn+p.packages.Mc+p.packages.Nd+p.packages.Pc+\"_]|\\\\s])+\",\"g\"),this.lineCommentStart=[\"//\",\"#\"],this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens,o=i.state;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"){var u=t.match(/^.*[\\{\\(\\[:]\\s*$/);u&&(r+=n)}else if(e==\"doc-start\"){if(o!=\"doc-start\")return\"\";var u=t.match(/^\\s*(\\/?)\\*/);u&&(u[1]&&(r+=\" \"),r+=\"* \")}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.getCompletions=function(e,t,n,r){return this.$completer.getCompletions(e,t,n,r)},this.$id=\"ace/mode/php-inline\"}.call(g.prototype);var y=function(e){if(e&&e.inline){var t=new g;return t.createWorker=this.createWorker,t.inlinePhp=!0,t}d.call(this),this.HighlightRules=s,this.createModeDelegates({\"js-\":v,\"css-\":m,\"php-\":g}),this.foldingRules.subModes[\"php-\"]=new h};r.inherits(y,d),function(){this.createWorker=function(e){var t=new f([\"ace\"],\"ace/mode/php_worker\",\"PhpWorker\");return t.attachToDocument(e.getDocument()),this.inlinePhp&&t.call(\"setOptions\",[{inline:!0}]),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/php\"}.call(y.prototype),t.Mode=y})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-plain_text.js",
    "content": "define(\"ace/mode/plain_text\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/text_highlight_rules\",\"ace/mode/behaviour\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./text_highlight_rules\").TextHighlightRules,o=e(\"./behaviour\").Behaviour,u=function(){this.HighlightRules=s,this.$behaviour=new o};r.inherits(u,i),function(){this.type=\"text\",this.getNextLineIndent=function(e,t,n){return\"\"},this.$id=\"ace/mode/plain_text\"}.call(u.prototype),t.Mode=u})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-properties.js",
    "content": "define(\"ace/mode/properties_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){var e=/\\\\u[0-9a-fA-F]{4}|\\\\/;this.$rules={start:[{token:\"comment\",regex:/[!#].*$/},{token:\"keyword\",regex:/[=:]$/},{token:\"keyword\",regex:/[=:]/,next:\"value\"},{token:\"constant.language.escape\",regex:e},{defaultToken:\"variable\"}],value:[{regex:/\\\\$/,token:\"string\",next:\"value\"},{regex:/$/,token:\"string\",next:\"start\"},{token:\"constant.language.escape\",regex:e},{defaultToken:\"string\"}]}};r.inherits(s,i),t.PropertiesHighlightRules=s}),define(\"ace/mode/properties\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/properties_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./properties_highlight_rules\").PropertiesHighlightRules,o=function(){this.HighlightRules=s,this.$behaviour=this.$defaultBehaviour};r.inherits(o,i),function(){this.$id=\"ace/mode/properties\"}.call(o.prototype),t.Mode=o})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-python.js",
    "content": "define(\"ace/mode/python_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){var e=\"and|as|assert|break|class|continue|def|del|elif|else|except|exec|finally|for|from|global|if|import|in|is|lambda|not|or|pass|print|raise|return|try|while|with|yield\",t=\"True|False|None|NotImplemented|Ellipsis|__debug__\",n=\"abs|divmod|input|open|staticmethod|all|enumerate|int|ord|str|any|eval|isinstance|pow|sum|basestring|execfile|issubclass|print|super|binfile|iter|property|tuple|bool|filter|len|range|type|bytearray|float|list|raw_input|unichr|callable|format|locals|reduce|unicode|chr|frozenset|long|reload|vars|classmethod|getattr|map|repr|xrange|cmp|globals|max|reversed|zip|compile|hasattr|memoryview|round|__import__|complex|hash|min|set|apply|delattr|help|next|setattr|buffer|dict|hex|object|slice|coerce|dir|id|oct|sorted|intern\",r=this.createKeywordMapper({\"invalid.deprecated\":\"debugger\",\"support.function\":n,\"constant.language\":t,keyword:e},\"identifier\"),i=\"(?:r|u|ur|R|U|UR|Ur|uR)?\",s=\"(?:(?:[1-9]\\\\d*)|(?:0))\",o=\"(?:0[oO]?[0-7]+)\",u=\"(?:0[xX][\\\\dA-Fa-f]+)\",a=\"(?:0[bB][01]+)\",f=\"(?:\"+s+\"|\"+o+\"|\"+u+\"|\"+a+\")\",l=\"(?:[eE][+-]?\\\\d+)\",c=\"(?:\\\\.\\\\d+)\",h=\"(?:\\\\d+)\",p=\"(?:(?:\"+h+\"?\"+c+\")|(?:\"+h+\"\\\\.))\",d=\"(?:(?:\"+p+\"|\"+h+\")\"+l+\")\",v=\"(?:\"+d+\"|\"+p+\")\",m=\"\\\\\\\\(x[0-9A-Fa-f]{2}|[0-7]{3}|[\\\\\\\\abfnrtv'\\\"]|U[0-9A-Fa-f]{8}|u[0-9A-Fa-f]{4})\";this.$rules={start:[{token:\"comment\",regex:\"#.*$\"},{token:\"string\",regex:i+'\"{3}',next:\"qqstring3\"},{token:\"string\",regex:i+'\"(?=.)',next:\"qqstring\"},{token:\"string\",regex:i+\"'{3}\",next:\"qstring3\"},{token:\"string\",regex:i+\"'(?=.)\",next:\"qstring\"},{token:\"constant.numeric\",regex:\"(?:\"+v+\"|\\\\d+)[jJ]\\\\b\"},{token:\"constant.numeric\",regex:v},{token:\"constant.numeric\",regex:f+\"[lL]\\\\b\"},{token:\"constant.numeric\",regex:f+\"\\\\b\"},{token:r,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"keyword.operator\",regex:\"\\\\+|\\\\-|\\\\*|\\\\*\\\\*|\\\\/|\\\\/\\\\/|%|<<|>>|&|\\\\||\\\\^|~|<|>|<=|=>|==|!=|<>|=\"},{token:\"paren.lparen\",regex:\"[\\\\[\\\\(\\\\{]\"},{token:\"paren.rparen\",regex:\"[\\\\]\\\\)\\\\}]\"},{token:\"text\",regex:\"\\\\s+\"}],qqstring3:[{token:\"constant.language.escape\",regex:m},{token:\"string\",regex:'\"{3}',next:\"start\"},{defaultToken:\"string\"}],qstring3:[{token:\"constant.language.escape\",regex:m},{token:\"string\",regex:\"'{3}\",next:\"start\"},{defaultToken:\"string\"}],qqstring:[{token:\"constant.language.escape\",regex:m},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qqstring\"},{token:\"string\",regex:'\"|$',next:\"start\"},{defaultToken:\"string\"}],qstring:[{token:\"constant.language.escape\",regex:m},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qstring\"},{token:\"string\",regex:\"'|$\",next:\"start\"},{defaultToken:\"string\"}]}};r.inherits(s,i),t.PythonHighlightRules=s}),define(\"ace/mode/folding/pythonic\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=t.FoldMode=function(e){this.foldingStartMarker=new RegExp(\"([\\\\[{])(?:\\\\s*)$|(\"+e+\")(?:\\\\s*)(?:#.*)?$\")};r.inherits(s,i),function(){this.getFoldWidgetRange=function(e,t,n){var r=e.getLine(n),i=r.match(this.foldingStartMarker);if(i)return i[1]?this.openingBracketBlock(e,i[1],n,i.index):i[2]?this.indentationBlock(e,n,i.index+i[2].length):this.indentationBlock(e,n)}}.call(s.prototype)}),define(\"ace/mode/python\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/python_highlight_rules\",\"ace/mode/folding/pythonic\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./python_highlight_rules\").PythonHighlightRules,o=e(\"./folding/pythonic\").FoldMode,u=e(\"../range\").Range,a=function(){this.HighlightRules=s,this.foldingRules=new o(\"\\\\:\"),this.$behaviour=this.$defaultBehaviour};r.inherits(a,i),function(){this.lineCommentStart=\"#\",this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"){var o=t.match(/^.*[\\{\\(\\[:]\\s*$/);o&&(r+=n)}return r};var e={pass:1,\"return\":1,raise:1,\"break\":1,\"continue\":1};this.checkOutdent=function(t,n,r){if(r!==\"\\r\\n\"&&r!==\"\\r\"&&r!==\"\\n\")return!1;var i=this.getTokenizer().getLineTokens(n.trim(),t).tokens;if(!i)return!1;do var s=i.pop();while(s&&(s.type==\"comment\"||s.type==\"text\"&&s.value.match(/^\\s+$/)));return s?s.type==\"keyword\"&&e[s.value]:!1},this.autoOutdent=function(e,t,n){n+=1;var r=this.$getIndent(t.getLine(n)),i=t.getTabString();r.slice(-i.length)==i&&t.remove(new u(n,r.length-i.length,n,r.length))},this.$id=\"ace/mode/python\"}.call(a.prototype),t.Mode=a})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-ruby.js",
    "content": "define(\"ace/mode/ruby_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=t.constantOtherSymbol={token:\"constant.other.symbol.ruby\",regex:\"[:](?:[A-Za-z_]|[@$](?=[a-zA-Z0-9_]))[a-zA-Z0-9_]*[!=?]?\"},o=t.qString={token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},u=t.qqString={token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},a=t.tString={token:\"string\",regex:\"[`](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[`]\"},f=t.constantNumericHex={token:\"constant.numeric\",regex:\"0[xX][0-9a-fA-F](?:[0-9a-fA-F]|_(?=[0-9a-fA-F]))*\\\\b\"},l=t.constantNumericFloat={token:\"constant.numeric\",regex:\"[+-]?\\\\d(?:\\\\d|_(?=\\\\d))*(?:(?:\\\\.\\\\d(?:\\\\d|_(?=\\\\d))*)?(?:[eE][+-]?\\\\d+)?)?\\\\b\"},c=function(){var e=\"abort|Array|assert|assert_equal|assert_not_equal|assert_same|assert_not_same|assert_nil|assert_not_nil|assert_match|assert_no_match|assert_in_delta|assert_throws|assert_raise|assert_nothing_raised|assert_instance_of|assert_kind_of|assert_respond_to|assert_operator|assert_send|assert_difference|assert_no_difference|assert_recognizes|assert_generates|assert_response|assert_redirected_to|assert_template|assert_select|assert_select_email|assert_select_rjs|assert_select_encoded|css_select|at_exit|attr|attr_writer|attr_reader|attr_accessor|attr_accessible|autoload|binding|block_given?|callcc|caller|catch|chomp|chomp!|chop|chop!|defined?|delete_via_redirect|eval|exec|exit|exit!|fail|Float|flunk|follow_redirect!|fork|form_for|form_tag|format|gets|global_variables|gsub|gsub!|get_via_redirect|host!|https?|https!|include|Integer|lambda|link_to|link_to_unless_current|link_to_function|link_to_remote|load|local_variables|loop|open|open_session|p|print|printf|proc|putc|puts|post_via_redirect|put_via_redirect|raise|rand|raw|readline|readlines|redirect?|request_via_redirect|require|scan|select|set_trace_func|sleep|split|sprintf|srand|String|stylesheet_link_tag|syscall|system|sub|sub!|test|throw|trace_var|trap|untrace_var|atan2|cos|exp|frexp|ldexp|log|log10|sin|sqrt|tan|render|javascript_include_tag|csrf_meta_tag|label_tag|text_field_tag|submit_tag|check_box_tag|content_tag|radio_button_tag|text_area_tag|password_field_tag|hidden_field_tag|fields_for|select_tag|options_for_select|options_from_collection_for_select|collection_select|time_zone_select|select_date|select_time|select_datetime|date_select|time_select|datetime_select|select_year|select_month|select_day|select_hour|select_minute|select_second|file_field_tag|file_field|respond_to|skip_before_filter|around_filter|after_filter|verify|protect_from_forgery|rescue_from|helper_method|redirect_to|before_filter|send_data|send_file|validates_presence_of|validates_uniqueness_of|validates_length_of|validates_format_of|validates_acceptance_of|validates_associated|validates_exclusion_of|validates_inclusion_of|validates_numericality_of|validates_with|validates_each|authenticate_or_request_with_http_basic|authenticate_or_request_with_http_digest|filter_parameter_logging|match|get|post|resources|redirect|scope|assert_routing|translate|localize|extract_locale_from_tld|caches_page|expire_page|caches_action|expire_action|cache|expire_fragment|expire_cache_for|observe|cache_sweeper|has_many|has_one|belongs_to|has_and_belongs_to_many\",t=\"alias|and|BEGIN|begin|break|case|class|def|defined|do|else|elsif|END|end|ensure|__FILE__|finally|for|gem|if|in|__LINE__|module|next|not|or|private|protected|public|redo|rescue|retry|return|super|then|undef|unless|until|when|while|yield\",n=\"true|TRUE|false|FALSE|nil|NIL|ARGF|ARGV|DATA|ENV|RUBY_PLATFORM|RUBY_RELEASE_DATE|RUBY_VERSION|STDERR|STDIN|STDOUT|TOPLEVEL_BINDING\",r=\"$DEBUG|$defout|$FILENAME|$LOAD_PATH|$SAFE|$stdin|$stdout|$stderr|$VERBOSE|$!|root_url|flash|session|cookies|params|request|response|logger|self\",i=this.$keywords=this.createKeywordMapper({keyword:t,\"constant.language\":n,\"variable.language\":r,\"support.function\":e,\"invalid.deprecated\":\"debugger\"},\"identifier\");this.$rules={start:[{token:\"comment\",regex:\"#.*$\"},{token:\"comment\",regex:\"^=begin(?:$|\\\\s.*$)\",next:\"comment\"},{token:\"string.regexp\",regex:\"[/](?:(?:\\\\[(?:\\\\\\\\]|[^\\\\]])+\\\\])|(?:\\\\\\\\/|[^\\\\]/]))*[/]\\\\w*\\\\s*(?=[).,;]|$)\"},[{regex:\"[{}]\",onMatch:function(e,t,n){this.next=e==\"{\"?this.nextState:\"\";if(e==\"{\"&&n.length)return n.unshift(\"start\",t),\"paren.lparen\";if(e==\"}\"&&n.length){n.shift(),this.next=n.shift();if(this.next.indexOf(\"string\")!=-1)return\"paren.end\"}return e==\"{\"?\"paren.lparen\":\"paren.rparen\"},nextState:\"start\"},{token:\"string.start\",regex:/\"/,push:[{token:\"constant.language.escape\",regex:/\\\\(?:[nsrtvfbae'\"\\\\]|c.|C-.|M-.(?:\\\\C-.)?|[0-7]{3}|x[\\da-fA-F]{2}|u[\\da-fA-F]{4})/},{token:\"paren.start\",regex:/#{/,push:\"start\"},{token:\"string.end\",regex:/\"/,next:\"pop\"},{defaultToken:\"string\"}]},{token:\"string.start\",regex:/`/,push:[{token:\"constant.language.escape\",regex:/\\\\(?:[nsrtvfbae'\"\\\\]|c.|C-.|M-.(?:\\\\C-.)?|[0-7]{3}|x[\\da-fA-F]{2}|u[\\da-fA-F]{4})/},{token:\"paren.start\",regex:/#{/,push:\"start\"},{token:\"string.end\",regex:/`/,next:\"pop\"},{defaultToken:\"string\"}]},{token:\"string.start\",regex:/'/,push:[{token:\"constant.language.escape\",regex:/\\\\['\\\\]/},{token:\"string.end\",regex:/'/,next:\"pop\"},{defaultToken:\"string\"}]}],{token:\"text\",regex:\"::\"},{token:\"variable.instance\",regex:\"@{1,2}[a-zA-Z_\\\\d]+\"},{token:\"support.class\",regex:\"[A-Z][a-zA-Z_\\\\d]+\"},s,f,l,{token:\"constant.language.boolean\",regex:\"(?:true|false)\\\\b\"},{token:i,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"punctuation.separator.key-value\",regex:\"=>\"},{stateName:\"heredoc\",onMatch:function(e,t,n){var r=e[2]==\"-\"?\"indentedHeredoc\":\"heredoc\",i=e.split(this.splitRegex);return n.push(r,i[3]),[{type:\"constant\",value:i[1]},{type:\"string\",value:i[2]},{type:\"support.class\",value:i[3]},{type:\"string\",value:i[4]}]},regex:\"(<<-?)(['\\\"`]?)([\\\\w]+)(['\\\"`]?)\",rules:{heredoc:[{onMatch:function(e,t,n){return e===n[1]?(n.shift(),n.shift(),this.next=n[0]||\"start\",\"support.class\"):(this.next=\"\",\"string\")},regex:\".*$\",next:\"start\"}],indentedHeredoc:[{token:\"string\",regex:\"^ +\"},{onMatch:function(e,t,n){return e===n[1]?(n.shift(),n.shift(),this.next=n[0]||\"start\",\"support.class\"):(this.next=\"\",\"string\")},regex:\".*$\",next:\"start\"}]}},{regex:\"$\",token:\"empty\",next:function(e,t){return t[0]===\"heredoc\"||t[0]===\"indentedHeredoc\"?t[0]:e}},{token:\"string.character\",regex:\"\\\\B\\\\?.\"},{token:\"keyword.operator\",regex:\"!|\\\\$|%|&|\\\\*|\\\\-\\\\-|\\\\-|\\\\+\\\\+|\\\\+|~|===|==|=|!=|!==|<=|>=|<<=|>>=|>>>=|<>|<|>|!|&&|\\\\|\\\\||\\\\?\\\\:|\\\\*=|%=|\\\\+=|\\\\-=|&=|\\\\^=|\\\\b(?:in|instanceof|new|delete|typeof|void)\"},{token:\"paren.lparen\",regex:\"[[({]\"},{token:\"paren.rparen\",regex:\"[\\\\])}]\"},{token:\"text\",regex:\"\\\\s+\"}],comment:[{token:\"comment\",regex:\"^=end(?:$|\\\\s.*$)\",next:\"start\"},{token:\"comment\",regex:\".+\"}]},this.normalizeRules()};r.inherits(c,i),t.RubyHighlightRules=c}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/coffee\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=e(\"../../range\").Range,o=t.FoldMode=function(){};r.inherits(o,i),function(){this.getFoldWidgetRange=function(e,t,n){var r=this.indentationBlock(e,n);if(r)return r;var i=/\\S/,o=e.getLine(n),u=o.search(i);if(u==-1||o[u]!=\"#\")return;var a=o.length,f=e.getLength(),l=n,c=n;while(++n<f){o=e.getLine(n);var h=o.search(i);if(h==-1)continue;if(o[h]!=\"#\")break;c=n}if(c>l){var p=e.getLine(c).length;return new s(l,a,c,p)}},this.getFoldWidget=function(e,t,n){var r=e.getLine(n),i=r.search(/\\S/),s=e.getLine(n+1),o=e.getLine(n-1),u=o.search(/\\S/),a=s.search(/\\S/);if(i==-1)return e.foldWidgets[n-1]=u!=-1&&u<a?\"start\":\"\",\"\";if(u==-1){if(i==a&&r[i]==\"#\"&&s[i]==\"#\")return e.foldWidgets[n-1]=\"\",e.foldWidgets[n+1]=\"\",\"start\"}else if(u==i&&r[i]==\"#\"&&o[i]==\"#\"&&e.getLine(n-2).search(/\\S/)==-1)return e.foldWidgets[n-1]=\"start\",e.foldWidgets[n+1]=\"\",\"\";return u!=-1&&u<i?e.foldWidgets[n-1]=\"start\":e.foldWidgets[n-1]=\"\",i<a?\"start\":\"\"}}.call(o.prototype)}),define(\"ace/mode/ruby\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/ruby_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/range\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/coffee\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./ruby_highlight_rules\").RubyHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../range\").Range,a=e(\"./behaviour/cstyle\").CstyleBehaviour,f=e(\"./folding/coffee\").FoldMode,l=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new a,this.foldingRules=new f};r.inherits(l,i),function(){this.lineCommentStart=\"#\",this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"){var o=t.match(/^.*[\\{\\(\\[]\\s*$/),u=t.match(/^\\s*(class|def|module)\\s.*$/),a=t.match(/.*do(\\s*|\\s+\\|.*\\|\\s*)$/),f=t.match(/^\\s*(if|else|when)\\s*/);if(o||u||a||f)r+=n}return r},this.checkOutdent=function(e,t,n){return/^\\s+(end|else)$/.test(t+n)||this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){var r=t.getLine(n);if(/}/.test(r))return this.$outdent.autoOutdent(t,n);var i=this.$getIndent(r),s=t.getLine(n-1),o=this.$getIndent(s),a=t.getTabString();o.length<=i.length&&i.slice(-a.length)==a&&t.remove(new u(n,i.length-a.length,n,i.length))},this.$id=\"ace/mode/ruby\"}.call(l.prototype),t.Mode=l})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-rust.js",
    "content": "define(\"ace/mode/rust_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=/\\\\(?:[nrt0'\"\\\\]|x[\\da-fA-F]{2}|u\\{[\\da-fA-F]{6}\\})/.source,o=function(){this.$rules={start:[{token:\"variable.other.source.rust\",regex:\"'[a-zA-Z_][a-zA-Z0-9_]*(?![\\\\'])\"},{token:\"string.quoted.single.source.rust\",regex:\"'(?:[^'\\\\\\\\]|\"+s+\")'\"},{stateName:\"bracketedComment\",onMatch:function(e,t,n){return n.unshift(this.next,e.length-1,t),\"string.quoted.raw.source.rust\"},regex:/r#*\"/,next:[{onMatch:function(e,t,n){var r=\"string.quoted.raw.source.rust\";return e.length>=n[1]?(e.length>n[1]&&(r=\"invalid\"),n.shift(),n.shift(),this.next=n.shift()):this.next=\"\",r},regex:/\"#*/,next:\"start\"},{defaultToken:\"string.quoted.raw.source.rust\"}]},{token:\"string.quoted.double.source.rust\",regex:'\"',push:[{token:\"string.quoted.double.source.rust\",regex:'\"',next:\"pop\"},{token:\"constant.character.escape.source.rust\",regex:s},{defaultToken:\"string.quoted.double.source.rust\"}]},{token:[\"keyword.source.rust\",\"text\",\"entity.name.function.source.rust\"],regex:\"\\\\b(fn)(\\\\s+)([a-zA-Z_][a-zA-Z0-9_]*)\"},{token:\"support.constant\",regex:\"\\\\b[a-zA-Z_][\\\\w\\\\d]*::\"},{token:\"keyword.source.rust\",regex:\"\\\\b(?:abstract|alignof|as|box|break|continue|const|crate|do|else|enum|extern|for|final|if|impl|in|let|loop|macro|match|mod|move|mut|offsetof|override|priv|proc|pub|pure|ref|return|self|sizeof|static|struct|super|trait|type|typeof|unsafe|unsized|use|virtual|where|while|yield)\\\\b\"},{token:\"storage.type.source.rust\",regex:\"\\\\b(?:Self|isize|usize|char|bool|u8|u16|u32|u64|u128|f16|f32|f64|i8|i16|i32|i64|i128|str|option|either|c_float|c_double|c_void|FILE|fpos_t|DIR|dirent|c_char|c_schar|c_uchar|c_short|c_ushort|c_int|c_uint|c_long|c_ulong|size_t|ptrdiff_t|clock_t|time_t|c_longlong|c_ulonglong|intptr_t|uintptr_t|off_t|dev_t|ino_t|pid_t|mode_t|ssize_t)\\\\b\"},{token:\"variable.language.source.rust\",regex:\"\\\\bself\\\\b\"},{token:\"comment.line.doc.source.rust\",regex:\"//!.*$\"},{token:\"comment.line.double-dash.source.rust\",regex:\"//.*$\"},{token:\"comment.start.block.source.rust\",regex:\"/\\\\*\",stateName:\"comment\",push:[{token:\"comment.start.block.source.rust\",regex:\"/\\\\*\",push:\"comment\"},{token:\"comment.end.block.source.rust\",regex:\"\\\\*/\",next:\"pop\"},{defaultToken:\"comment.block.source.rust\"}]},{token:\"keyword.operator\",regex:/\\$|[-=]>|[-+%^=!&|<>]=?|[*/](?![*/])=?/},{token:\"punctuation.operator\",regex:/[?:,;.]/},{token:\"paren.lparen\",regex:/[\\[({]/},{token:\"paren.rparen\",regex:/[\\])}]/},{token:\"constant.language.source.rust\",regex:\"\\\\b(?:true|false|Some|None|Ok|Err)\\\\b\"},{token:\"support.constant.source.rust\",regex:\"\\\\b(?:EXIT_FAILURE|EXIT_SUCCESS|RAND_MAX|EOF|SEEK_SET|SEEK_CUR|SEEK_END|_IOFBF|_IONBF|_IOLBF|BUFSIZ|FOPEN_MAX|FILENAME_MAX|L_tmpnam|TMP_MAX|O_RDONLY|O_WRONLY|O_RDWR|O_APPEND|O_CREAT|O_EXCL|O_TRUNC|S_IFIFO|S_IFCHR|S_IFBLK|S_IFDIR|S_IFREG|S_IFMT|S_IEXEC|S_IWRITE|S_IREAD|S_IRWXU|S_IXUSR|S_IWUSR|S_IRUSR|F_OK|R_OK|W_OK|X_OK|STDIN_FILENO|STDOUT_FILENO|STDERR_FILENO)\\\\b\"},{token:\"meta.preprocessor.source.rust\",regex:\"\\\\b\\\\w\\\\(\\\\w\\\\)*!|#\\\\[[\\\\w=\\\\(\\\\)_]+\\\\]\\\\b\"},{token:\"constant.numeric.source.rust\",regex:/\\b(?:0x[a-fA-F0-9_]+|0o[0-7_]+|0b[01_]+|[0-9][0-9_]*(?!\\.))(?:[iu](?:size|8|16|32|64|128))?\\b/},{token:\"constant.numeric.source.rust\",regex:/\\b(?:[0-9][0-9_]*)(?:\\.[0-9][0-9_]*)?(?:[Ee][+-][0-9][0-9_]*)?(?:f32|f64)?\\b/}]},this.normalizeRules()};o.metaData={fileTypes:[\"rs\",\"rc\"],foldingStartMarker:\"^.*\\\\bfn\\\\s*(\\\\w+\\\\s*)?\\\\([^\\\\)]*\\\\)(\\\\s*\\\\{[^\\\\}]*)?\\\\s*$\",foldingStopMarker:\"^\\\\s*\\\\}\",name:\"Rust\",scopeName:\"source.rust\"},r.inherits(o,i),t.RustHighlightRules=o}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/rust\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/rust_highlight_rules\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./rust_highlight_rules\").RustHighlightRules,o=e(\"./folding/cstyle\").FoldMode,u=function(){this.HighlightRules=s,this.foldingRules=new o,this.$behaviour=this.$defaultBehaviour};r.inherits(u,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\",nestable:!0},this.$id=\"ace/mode/rust\"}.call(u.prototype),t.Mode=u})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-sh.js",
    "content": "define(\"ace/mode/sh_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=t.reservedKeywords=\"!|{|}|case|do|done|elif|else|esac|fi|for|if|in|then|until|while|&|;|export|local|read|typeset|unset|elif|select|set|function|declare|readonly\",o=t.languageConstructs=\"[|]|alias|bg|bind|break|builtin|cd|command|compgen|complete|continue|dirs|disown|echo|enable|eval|exec|exit|fc|fg|getopts|hash|help|history|jobs|kill|let|logout|popd|printf|pushd|pwd|return|set|shift|shopt|source|suspend|test|times|trap|type|ulimit|umask|unalias|wait\",u=function(){var e=this.createKeywordMapper({keyword:s,\"support.function.builtin\":o,\"invalid.deprecated\":\"debugger\"},\"identifier\"),t=\"(?:(?:[1-9]\\\\d*)|(?:0))\",n=\"(?:\\\\.\\\\d+)\",r=\"(?:\\\\d+)\",i=\"(?:(?:\"+r+\"?\"+n+\")|(?:\"+r+\"\\\\.))\",u=\"(?:(?:\"+i+\"|\"+r+\")\"+\")\",a=\"(?:\"+u+\"|\"+i+\")\",f=\"(?:&\"+r+\")\",l=\"[a-zA-Z_][a-zA-Z0-9_]*\",c=\"(?:\"+l+\"=)\",h=\"(?:\\\\$(?:SHLVL|\\\\$|\\\\!|\\\\?))\",p=\"(?:\"+l+\"\\\\s*\\\\(\\\\))\";this.$rules={start:[{token:\"constant\",regex:/\\\\./},{token:[\"text\",\"comment\"],regex:/(^|\\s)(#.*)$/},{token:\"string.start\",regex:'\"',push:[{token:\"constant.language.escape\",regex:/\\\\(?:[$`\"\\\\]|$)/},{include:\"variables\"},{token:\"keyword.operator\",regex:/`/},{token:\"string.end\",regex:'\"',next:\"pop\"},{defaultToken:\"string\"}]},{token:\"string\",regex:\"\\\\$'\",push:[{token:\"constant.language.escape\",regex:/\\\\(?:[abeEfnrtv\\\\'\"]|x[a-fA-F\\d]{1,2}|u[a-fA-F\\d]{4}([a-fA-F\\d]{4})?|c.|\\d{1,3})/},{token:\"string\",regex:\"'\",next:\"pop\"},{defaultToken:\"string\"}]},{regex:\"<<<\",token:\"keyword.operator\"},{stateName:\"heredoc\",regex:\"(<<-?)(\\\\s*)(['\\\"`]?)([\\\\w\\\\-]+)(['\\\"`]?)\",onMatch:function(e,t,n){var r=e[2]==\"-\"?\"indentedHeredoc\":\"heredoc\",i=e.split(this.splitRegex);return n.push(r,i[4]),[{type:\"constant\",value:i[1]},{type:\"text\",value:i[2]},{type:\"string\",value:i[3]},{type:\"support.class\",value:i[4]},{type:\"string\",value:i[5]}]},rules:{heredoc:[{onMatch:function(e,t,n){return e===n[1]?(n.shift(),n.shift(),this.next=n[0]||\"start\",\"support.class\"):(this.next=\"\",\"string\")},regex:\".*$\",next:\"start\"}],indentedHeredoc:[{token:\"string\",regex:\"^\t+\"},{onMatch:function(e,t,n){return e===n[1]?(n.shift(),n.shift(),this.next=n[0]||\"start\",\"support.class\"):(this.next=\"\",\"string\")},regex:\".*$\",next:\"start\"}]}},{regex:\"$\",token:\"empty\",next:function(e,t){return t[0]===\"heredoc\"||t[0]===\"indentedHeredoc\"?t[0]:e}},{token:[\"keyword\",\"text\",\"text\",\"text\",\"variable\"],regex:/(declare|local|readonly)(\\s+)(?:(-[fixar]+)(\\s+))?([a-zA-Z_][a-zA-Z0-9_]*\\b)/},{token:\"variable.language\",regex:h},{token:\"variable\",regex:c},{include:\"variables\"},{token:\"support.function\",regex:p},{token:\"support.function\",regex:f},{token:\"string\",start:\"'\",end:\"'\"},{token:\"constant.numeric\",regex:a},{token:\"constant.numeric\",regex:t+\"\\\\b\"},{token:e,regex:\"[a-zA-Z_][a-zA-Z0-9_]*\\\\b\"},{token:\"keyword.operator\",regex:\"\\\\+|\\\\-|\\\\*|\\\\*\\\\*|\\\\/|\\\\/\\\\/|~|<|>|<=|=>|=|!=|[%&|`]\"},{token:\"punctuation.operator\",regex:\";\"},{token:\"paren.lparen\",regex:\"[\\\\[\\\\(\\\\{]\"},{token:\"paren.rparen\",regex:\"[\\\\]]\"},{token:\"paren.rparen\",regex:\"[\\\\)\\\\}]\",next:\"pop\"}],variables:[{token:\"variable\",regex:/(\\$)(\\w+)/},{token:[\"variable\",\"paren.lparen\"],regex:/(\\$)(\\()/,push:\"start\"},{token:[\"variable\",\"paren.lparen\",\"keyword.operator\",\"variable\",\"keyword.operator\"],regex:/(\\$)(\\{)([#!]?)(\\w+|[*@#?\\-$!0_])(:[?+\\-=]?|##?|%%?|,,?\\/|\\^\\^?)?/,push:\"start\"},{token:\"variable\",regex:/\\$[*@#?\\-$!0_]/},{token:[\"variable\",\"paren.lparen\"],regex:/(\\$)(\\{)/,push:\"start\"}]},this.normalizeRules()};r.inherits(u,i),t.ShHighlightRules=u}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/sh\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/sh_highlight_rules\",\"ace/range\",\"ace/mode/folding/cstyle\",\"ace/mode/behaviour/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./sh_highlight_rules\").ShHighlightRules,o=e(\"../range\").Range,u=e(\"./folding/cstyle\").FoldMode,a=e(\"./behaviour/cstyle\").CstyleBehaviour,f=function(){this.HighlightRules=s,this.foldingRules=new u,this.$behaviour=new a};r.inherits(f,i),function(){this.lineCommentStart=\"#\",this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"){var o=t.match(/^.*[\\{\\(\\[:]\\s*$/);o&&(r+=n)}return r};var e={pass:1,\"return\":1,raise:1,\"break\":1,\"continue\":1};this.checkOutdent=function(t,n,r){if(r!==\"\\r\\n\"&&r!==\"\\r\"&&r!==\"\\n\")return!1;var i=this.getTokenizer().getLineTokens(n.trim(),t).tokens;if(!i)return!1;do var s=i.pop();while(s&&(s.type==\"comment\"||s.type==\"text\"&&s.value.match(/^\\s+$/)));return s?s.type==\"keyword\"&&e[s.value]:!1},this.autoOutdent=function(e,t,n){n+=1;var r=this.$getIndent(t.getLine(n)),i=t.getTabString();r.slice(-i.length)==i&&t.remove(new o(n,r.length-i.length,n,r.length))},this.$id=\"ace/mode/sh\"}.call(f.prototype),t.Mode=f})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-smarty.js",
    "content": "define(\"ace/mode/doc_comment_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment.doc.tag\",regex:\"@[\\\\w\\\\d_]+\"},s.getTagRule(),{defaultToken:\"comment.doc\",caseInsensitive:!0}]}};r.inherits(s,i),s.getTagRule=function(e){return{token:\"comment.doc.tag.storage.type\",regex:\"\\\\b(?:TODO|FIXME|XXX|HACK)\\\\b\"}},s.getStartRule=function(e){return{token:\"comment.doc\",regex:\"\\\\/\\\\*(?=\\\\*)\",next:e}},s.getEndRule=function(e){return{token:\"comment.doc\",regex:\"\\\\*\\\\/\",next:e}},t.DocCommentHighlightRules=s}),define(\"ace/mode/javascript_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/doc_comment_highlight_rules\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";function a(){var e=o.replace(\"\\\\d\",\"\\\\d\\\\-\"),t={onMatch:function(e,t,n){var r=e.charAt(1)==\"/\"?2:1;if(r==1)t!=this.nextState?n.unshift(this.next,this.nextState,0):n.unshift(this.next),n[2]++;else if(r==2&&t==this.nextState){n[1]--;if(!n[1]||n[1]<0)n.shift(),n.shift()}return[{type:\"meta.tag.punctuation.\"+(r==1?\"\":\"end-\")+\"tag-open.xml\",value:e.slice(0,r)},{type:\"meta.tag.tag-name.xml\",value:e.substr(r)}]},regex:\"</?\"+e+\"\",next:\"jsxAttributes\",nextState:\"jsx\"};this.$rules.start.unshift(t);var n={regex:\"{\",token:\"paren.quasi.start\",push:\"start\"};this.$rules.jsx=[n,t,{include:\"reference\"},{defaultToken:\"string\"}],this.$rules.jsxAttributes=[{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",onMatch:function(e,t,n){return t==n[0]&&n.shift(),e.length==2&&(n[0]==this.nextState&&n[1]--,(!n[1]||n[1]<0)&&n.splice(0,2)),this.next=n[0]||\"start\",[{type:this.token,value:e}]},nextState:\"jsx\"},n,f(\"jsxAttributes\"),{token:\"entity.other.attribute-name.xml\",regex:e},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"},{token:\"string.attribute-value.xml\",regex:\"'\",stateName:\"jsx_attr_q\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',stateName:\"jsx_attr_qq\",push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"reference\"},{defaultToken:\"string.attribute-value.xml\"}]},t],this.$rules.reference=[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}]}function f(e){return[{token:\"comment\",regex:/\\/\\*/,next:[i.getTagRule(),{token:\"comment\",regex:\"\\\\*\\\\/\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]},{token:\"comment\",regex:\"\\\\/\\\\/\",next:[i.getTagRule(),{token:\"comment\",regex:\"$|^\",next:e||\"pop\"},{defaultToken:\"comment\",caseInsensitive:!0}]}]}var r=e(\"../lib/oop\"),i=e(\"./doc_comment_highlight_rules\").DocCommentHighlightRules,s=e(\"./text_highlight_rules\").TextHighlightRules,o=\"[a-zA-Z\\\\$_\\u00a1-\\uffff][a-zA-Z\\\\d\\\\$_\\u00a1-\\uffff]*\",u=function(e){var t=this.createKeywordMapper({\"variable.language\":\"Array|Boolean|Date|Function|Iterator|Number|Object|RegExp|String|Proxy|Namespace|QName|XML|XMLList|ArrayBuffer|Float32Array|Float64Array|Int16Array|Int32Array|Int8Array|Uint16Array|Uint32Array|Uint8Array|Uint8ClampedArray|Error|EvalError|InternalError|RangeError|ReferenceError|StopIteration|SyntaxError|TypeError|URIError|decodeURI|decodeURIComponent|encodeURI|encodeURIComponent|eval|isFinite|isNaN|parseFloat|parseInt|JSON|Math|this|arguments|prototype|window|document\",keyword:\"const|yield|import|get|set|async|await|break|case|catch|continue|default|delete|do|else|finally|for|function|if|in|of|instanceof|new|return|switch|throw|try|typeof|let|var|while|with|debugger|__parent__|__count__|escape|unescape|with|__proto__|class|enum|extends|super|export|implements|private|public|interface|package|protected|static\",\"storage.type\":\"const|let|var|function\",\"constant.language\":\"null|Infinity|NaN|undefined\",\"support.function\":\"alert\",\"constant.language.boolean\":\"true|false\"},\"identifier\"),n=\"case|do|else|finally|in|instanceof|return|throw|try|typeof|yield|void\",r=\"\\\\\\\\(?:x[0-9a-fA-F]{2}|u[0-9a-fA-F]{4}|u{[0-9a-fA-F]{1,6}}|[0-2][0-7]{0,2}|3[0-7][0-7]?|[4-7][0-7]?|.)\";this.$rules={no_regex:[i.getStartRule(\"doc-start\"),f(\"no_regex\"),{token:\"string\",regex:\"'(?=.)\",next:\"qstring\"},{token:\"string\",regex:'\"(?=.)',next:\"qqstring\"},{token:\"constant.numeric\",regex:/0(?:[xX][0-9a-fA-F]+|[bB][01]+)\\b/},{token:\"constant.numeric\",regex:/[+-]?\\d[\\d_]*(?:(?:\\.\\d*)?(?:[eE][+-]?\\d+)?)?\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\"],regex:\"(\"+o+\")(\\\\.)(prototype)(\\\\.)(\"+o+\")(\\\\s*)(=)\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(\\\\s+)(\\\\w+)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(function)(\\\\s+)(\"+o+\")(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"entity.name.function\",\"text\",\"punctuation.operator\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\s*)(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:[\"text\",\"text\",\"storage.type\",\"text\",\"paren.lparen\"],regex:\"(:)(\\\\s*)(function)(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"keyword\",regex:\"(?:\"+n+\")\\\\b\",next:\"start\"},{token:[\"support.constant\"],regex:/that\\b/},{token:[\"storage.type\",\"punctuation.operator\",\"support.function.firebug\"],regex:/(console)(\\.)(warn|info|log|error|time|trace|timeEnd|assert)\\b/},{token:t,regex:o},{token:\"punctuation.operator\",regex:/[.](?![.])/,next:\"property\"},{token:\"keyword.operator\",regex:/--|\\+\\+|\\.{3}|===|==|=|!=|!==|<+=?|>+=?|!|&&|\\|\\||\\?:|[!$%&*+\\-~\\/^]=?/,next:\"start\"},{token:\"punctuation.operator\",regex:/[?:,;.]/,next:\"start\"},{token:\"paren.lparen\",regex:/[\\[({]/,next:\"start\"},{token:\"paren.rparen\",regex:/[\\])}]/},{token:\"comment\",regex:/^#!.*$/}],property:[{token:\"text\",regex:\"\\\\s+\"},{token:[\"storage.type\",\"punctuation.operator\",\"entity.name.function\",\"text\",\"keyword.operator\",\"text\",\"storage.type\",\"text\",\"entity.name.function\",\"text\",\"paren.lparen\"],regex:\"(\"+o+\")(\\\\.)(\"+o+\")(\\\\s*)(=)(\\\\s*)(function)(?:(\\\\s+)(\\\\w+))?(\\\\s*)(\\\\()\",next:\"function_arguments\"},{token:\"punctuation.operator\",regex:/[.](?![.])/},{token:\"support.function\",regex:/(s(?:h(?:ift|ow(?:Mod(?:elessDialog|alDialog)|Help))|croll(?:X|By(?:Pages|Lines)?|Y|To)?|t(?:op|rike)|i(?:n|zeToContent|debar|gnText)|ort|u(?:p|b(?:str(?:ing)?)?)|pli(?:ce|t)|e(?:nd|t(?:Re(?:sizable|questHeader)|M(?:i(?:nutes|lliseconds)|onth)|Seconds|Ho(?:tKeys|urs)|Year|Cursor|Time(?:out)?|Interval|ZOptions|Date|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Date|FullYear)|FullYear|Active)|arch)|qrt|lice|avePreferences|mall)|h(?:ome|andleEvent)|navigate|c(?:har(?:CodeAt|At)|o(?:s|n(?:cat|textual|firm)|mpile)|eil|lear(?:Timeout|Interval)?|a(?:ptureEvents|ll)|reate(?:StyleSheet|Popup|EventObject))|t(?:o(?:GMTString|S(?:tring|ource)|U(?:TCString|pperCase)|Lo(?:caleString|werCase))|est|a(?:n|int(?:Enabled)?))|i(?:s(?:NaN|Finite)|ndexOf|talics)|d(?:isableExternalCapture|ump|etachEvent)|u(?:n(?:shift|taint|escape|watch)|pdateCommands)|j(?:oin|avaEnabled)|p(?:o(?:p|w)|ush|lugins.refresh|a(?:ddings|rse(?:Int|Float)?)|r(?:int|ompt|eference))|e(?:scape|nableExternalCapture|val|lementFromPoint|x(?:p|ec(?:Script|Command)?))|valueOf|UTC|queryCommand(?:State|Indeterm|Enabled|Value)|f(?:i(?:nd|le(?:ModifiedDate|Size|CreatedDate|UpdatedDate)|xed)|o(?:nt(?:size|color)|rward)|loor|romCharCode)|watch|l(?:ink|o(?:ad|g)|astIndexOf)|a(?:sin|nchor|cos|t(?:tachEvent|ob|an(?:2)?)|pply|lert|b(?:s|ort))|r(?:ou(?:nd|teEvents)|e(?:size(?:By|To)|calc|turnValue|place|verse|l(?:oad|ease(?:Capture|Events)))|andom)|g(?:o|et(?:ResponseHeader|M(?:i(?:nutes|lliseconds)|onth)|Se(?:conds|lection)|Hours|Year|Time(?:zoneOffset)?|Da(?:y|te)|UTC(?:M(?:i(?:nutes|lliseconds)|onth)|Seconds|Hours|Da(?:y|te)|FullYear)|FullYear|A(?:ttention|llResponseHeaders)))|m(?:in|ove(?:B(?:y|elow)|To(?:Absolute)?|Above)|ergeAttributes|a(?:tch|rgins|x))|b(?:toa|ig|o(?:ld|rderWidths)|link|ack))\\b(?=\\()/},{token:\"support.function.dom\",regex:/(s(?:ub(?:stringData|mit)|plitText|e(?:t(?:NamedItem|Attribute(?:Node)?)|lect))|has(?:ChildNodes|Feature)|namedItem|c(?:l(?:ick|o(?:se|neNode))|reate(?:C(?:omment|DATASection|aption)|T(?:Head|extNode|Foot)|DocumentFragment|ProcessingInstruction|E(?:ntityReference|lement)|Attribute))|tabIndex|i(?:nsert(?:Row|Before|Cell|Data)|tem)|open|delete(?:Row|C(?:ell|aption)|T(?:Head|Foot)|Data)|focus|write(?:ln)?|a(?:dd|ppend(?:Child|Data))|re(?:set|place(?:Child|Data)|move(?:NamedItem|Child|Attribute(?:Node)?)?)|get(?:NamedItem|Element(?:sBy(?:Name|TagName|ClassName)|ById)|Attribute(?:Node)?)|blur)\\b(?=\\()/},{token:\"support.constant\",regex:/(s(?:ystemLanguage|cr(?:ipts|ollbars|een(?:X|Y|Top|Left))|t(?:yle(?:Sheets)?|atus(?:Text|bar)?)|ibling(?:Below|Above)|ource|uffixes|e(?:curity(?:Policy)?|l(?:ection|f)))|h(?:istory|ost(?:name)?|as(?:h|Focus))|y|X(?:MLDocument|SLDocument)|n(?:ext|ame(?:space(?:s|URI)|Prop))|M(?:IN_VALUE|AX_VALUE)|c(?:haracterSet|o(?:n(?:structor|trollers)|okieEnabled|lorDepth|mp(?:onents|lete))|urrent|puClass|l(?:i(?:p(?:boardData)?|entInformation)|osed|asses)|alle(?:e|r)|rypto)|t(?:o(?:olbar|p)|ext(?:Transform|Indent|Decoration|Align)|ags)|SQRT(?:1_2|2)|i(?:n(?:ner(?:Height|Width)|put)|ds|gnoreCase)|zIndex|o(?:scpu|n(?:readystatechange|Line)|uter(?:Height|Width)|p(?:sProfile|ener)|ffscreenBuffering)|NEGATIVE_INFINITY|d(?:i(?:splay|alog(?:Height|Top|Width|Left|Arguments)|rectories)|e(?:scription|fault(?:Status|Ch(?:ecked|arset)|View)))|u(?:ser(?:Profile|Language|Agent)|n(?:iqueID|defined)|pdateInterval)|_content|p(?:ixelDepth|ort|ersonalbar|kcs11|l(?:ugins|atform)|a(?:thname|dding(?:Right|Bottom|Top|Left)|rent(?:Window|Layer)?|ge(?:X(?:Offset)?|Y(?:Offset)?))|r(?:o(?:to(?:col|type)|duct(?:Sub)?|mpter)|e(?:vious|fix)))|e(?:n(?:coding|abledPlugin)|x(?:ternal|pando)|mbeds)|v(?:isibility|endor(?:Sub)?|Linkcolor)|URLUnencoded|P(?:I|OSITIVE_INFINITY)|f(?:ilename|o(?:nt(?:Size|Family|Weight)|rmName)|rame(?:s|Element)|gColor)|E|whiteSpace|l(?:i(?:stStyleType|n(?:eHeight|kColor))|o(?:ca(?:tion(?:bar)?|lName)|wsrc)|e(?:ngth|ft(?:Context)?)|a(?:st(?:M(?:odified|atch)|Index|Paren)|yer(?:s|X)|nguage))|a(?:pp(?:MinorVersion|Name|Co(?:deName|re)|Version)|vail(?:Height|Top|Width|Left)|ll|r(?:ity|guments)|Linkcolor|bove)|r(?:ight(?:Context)?|e(?:sponse(?:XML|Text)|adyState))|global|x|m(?:imeTypes|ultiline|enubar|argin(?:Right|Bottom|Top|Left))|L(?:N(?:10|2)|OG(?:10E|2E))|b(?:o(?:ttom|rder(?:Width|RightWidth|BottomWidth|Style|Color|TopWidth|LeftWidth))|ufferDepth|elow|ackground(?:Color|Image)))\\b/},{token:\"identifier\",regex:o},{regex:\"\",token:\"empty\",next:\"no_regex\"}],start:[i.getStartRule(\"doc-start\"),f(\"start\"),{token:\"string.regexp\",regex:\"\\\\/\",next:\"regex\"},{token:\"text\",regex:\"\\\\s+|^$\",next:\"start\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],regex:[{token:\"regexp.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"string.regexp\",regex:\"/[sxngimy]*\",next:\"no_regex\"},{token:\"invalid\",regex:/\\{\\d+\\b,?\\d*\\}[+*]|[+*$^?][+*]|[$^][?]|\\?{3,}/},{token:\"constant.language.escape\",regex:/\\(\\?[:=!]|\\)|\\{\\d+\\b,?\\d*\\}|[+*]\\?|[()$^+*?.]/},{token:\"constant.language.delimiter\",regex:/\\|/},{token:\"constant.language.escape\",regex:/\\[\\^?/,next:\"regex_character_class\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp\"}],regex_character_class:[{token:\"regexp.charclass.keyword.operator\",regex:\"\\\\\\\\(?:u[\\\\da-fA-F]{4}|x[\\\\da-fA-F]{2}|.)\"},{token:\"constant.language.escape\",regex:\"]\",next:\"regex\"},{token:\"constant.language.escape\",regex:\"-\"},{token:\"empty\",regex:\"$\",next:\"no_regex\"},{defaultToken:\"string.regexp.charachterclass\"}],function_arguments:[{token:\"variable.parameter\",regex:o},{token:\"punctuation.operator\",regex:\"[, ]+\"},{token:\"punctuation.operator\",regex:\"$\"},{token:\"empty\",regex:\"\",next:\"no_regex\"}],qqstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qqstring\"},{token:\"string\",regex:'\"|$',next:\"no_regex\"},{defaultToken:\"string\"}],qstring:[{token:\"constant.language.escape\",regex:r},{token:\"string\",regex:\"\\\\\\\\$\",next:\"qstring\"},{token:\"string\",regex:\"'|$\",next:\"no_regex\"},{defaultToken:\"string\"}]};if(!e||!e.noES6)this.$rules.no_regex.unshift({regex:\"[{}]\",onMatch:function(e,t,n){this.next=e==\"{\"?this.nextState:\"\";if(e==\"{\"&&n.length)n.unshift(\"start\",t);else if(e==\"}\"&&n.length){n.shift(),this.next=n.shift();if(this.next.indexOf(\"string\")!=-1||this.next.indexOf(\"jsx\")!=-1)return\"paren.quasi.end\"}return e==\"{\"?\"paren.lparen\":\"paren.rparen\"},nextState:\"start\"},{token:\"string.quasi.start\",regex:/`/,push:[{token:\"constant.language.escape\",regex:r},{token:\"paren.quasi.start\",regex:/\\${/,push:\"start\"},{token:\"string.quasi.end\",regex:/`/,next:\"pop\"},{defaultToken:\"string.quasi\"}]}),(!e||e.jsx!=0)&&a.call(this);this.embedRules(i,\"doc-\",[i.getEndRule(\"no_regex\")]),this.normalizeRules()};r.inherits(u,s),t.JavaScriptHighlightRules=u}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/cstyle\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/range\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../../range\").Range,s=e(\"./fold_mode\").FoldMode,o=t.FoldMode=function(e){e&&(this.foldingStartMarker=new RegExp(this.foldingStartMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.start)),this.foldingStopMarker=new RegExp(this.foldingStopMarker.source.replace(/\\|[^|]*?$/,\"|\"+e.end)))};r.inherits(o,s),function(){this.foldingStartMarker=/(\\{|\\[)[^\\}\\]]*$|^\\s*(\\/\\*)/,this.foldingStopMarker=/^[^\\[\\{]*(\\}|\\])|^[\\s\\*]*(\\*\\/)/,this.singleLineBlockCommentRe=/^\\s*(\\/\\*).*\\*\\/\\s*$/,this.tripleStarBlockCommentRe=/^\\s*(\\/\\*\\*\\*).*\\*\\/\\s*$/,this.startRegionRe=/^\\s*(\\/\\*|\\/\\/)#?region\\b/,this._getFoldWidgetBase=this.getFoldWidget,this.getFoldWidget=function(e,t,n){var r=e.getLine(n);if(this.singleLineBlockCommentRe.test(r)&&!this.startRegionRe.test(r)&&!this.tripleStarBlockCommentRe.test(r))return\"\";var i=this._getFoldWidgetBase(e,t,n);return!i&&this.startRegionRe.test(r)?\"start\":i},this.getFoldWidgetRange=function(e,t,n,r){var i=e.getLine(n);if(this.startRegionRe.test(i))return this.getCommentRegionBlock(e,i,n);var s=i.match(this.foldingStartMarker);if(s){var o=s.index;if(s[1])return this.openingBracketBlock(e,s[1],n,o);var u=e.getCommentFoldRange(n,o+s[0].length,1);return u&&!u.isMultiLine()&&(r?u=this.getSectionRange(e,n):t!=\"all\"&&(u=null)),u}if(t===\"markbegin\")return;var s=i.match(this.foldingStopMarker);if(s){var o=s.index+s[0].length;return s[1]?this.closingBracketBlock(e,s[1],n,o):e.getCommentFoldRange(n,o,-1)}},this.getSectionRange=function(e,t){var n=e.getLine(t),r=n.search(/\\S/),s=t,o=n.length;t+=1;var u=t,a=e.getLength();while(++t<a){n=e.getLine(t);var f=n.search(/\\S/);if(f===-1)continue;if(r>f)break;var l=this.getFoldWidgetRange(e,\"all\",t);if(l){if(l.start.row<=s)break;if(l.isMultiLine())t=l.end.row;else if(r==f)break}u=t}return new i(s,o,u,e.getLine(u).length)},this.getCommentRegionBlock=function(e,t,n){var r=t.search(/\\s*$/),s=e.getLength(),o=n,u=/^\\s*(?:\\/\\*|\\/\\/|--)#?(end)?region\\b/,a=1;while(++n<s){t=e.getLine(n);var f=u.exec(t);if(!f)continue;f[1]?a--:a++;if(!a)break}var l=n;if(l>o)return new i(o,r,l,t.length)}}.call(o.prototype)}),define(\"ace/mode/javascript\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/behaviour/cstyle\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./behaviour/cstyle\").CstyleBehaviour,f=e(\"./folding/cstyle\").FoldMode,l=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new a,this.foldingRules=new f};r.inherits(l,i),function(){this.lineCommentStart=\"//\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e),s=i.tokens,o=i.state;if(s.length&&s[s.length-1].type==\"comment\")return r;if(e==\"start\"||e==\"no_regex\"){var u=t.match(/^.*(?:\\bcase\\b.*:|[\\{\\(\\[])\\s*$/);u&&(r+=n)}else if(e==\"doc-start\"){if(o==\"start\"||o==\"no_regex\")return\"\";var u=t.match(/^\\s*(\\/?)\\*/);u&&(u[1]&&(r+=\" \"),r+=\"* \")}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/javascript_worker\",\"JavaScriptWorker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/javascript\"}.call(l.prototype),t.Mode=l}),define(\"ace/mode/css_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text_highlight_rules\").TextHighlightRules,o=t.supportType=\"align-content|align-items|align-self|all|animation|animation-delay|animation-direction|animation-duration|animation-fill-mode|animation-iteration-count|animation-name|animation-play-state|animation-timing-function|backface-visibility|background|background-attachment|background-blend-mode|background-clip|background-color|background-image|background-origin|background-position|background-repeat|background-size|border|border-bottom|border-bottom-color|border-bottom-left-radius|border-bottom-right-radius|border-bottom-style|border-bottom-width|border-collapse|border-color|border-image|border-image-outset|border-image-repeat|border-image-slice|border-image-source|border-image-width|border-left|border-left-color|border-left-style|border-left-width|border-radius|border-right|border-right-color|border-right-style|border-right-width|border-spacing|border-style|border-top|border-top-color|border-top-left-radius|border-top-right-radius|border-top-style|border-top-width|border-width|bottom|box-shadow|box-sizing|caption-side|clear|clip|color|column-count|column-fill|column-gap|column-rule|column-rule-color|column-rule-style|column-rule-width|column-span|column-width|columns|content|counter-increment|counter-reset|cursor|direction|display|empty-cells|filter|flex|flex-basis|flex-direction|flex-flow|flex-grow|flex-shrink|flex-wrap|float|font|font-family|font-size|font-size-adjust|font-stretch|font-style|font-variant|font-weight|hanging-punctuation|height|justify-content|left|letter-spacing|line-height|list-style|list-style-image|list-style-position|list-style-type|margin|margin-bottom|margin-left|margin-right|margin-top|max-height|max-width|min-height|min-width|nav-down|nav-index|nav-left|nav-right|nav-up|opacity|order|outline|outline-color|outline-offset|outline-style|outline-width|overflow|overflow-x|overflow-y|padding|padding-bottom|padding-left|padding-right|padding-top|page-break-after|page-break-before|page-break-inside|perspective|perspective-origin|position|quotes|resize|right|tab-size|table-layout|text-align|text-align-last|text-decoration|text-decoration-color|text-decoration-line|text-decoration-style|text-indent|text-justify|text-overflow|text-shadow|text-transform|top|transform|transform-origin|transform-style|transition|transition-delay|transition-duration|transition-property|transition-timing-function|unicode-bidi|vertical-align|visibility|white-space|width|word-break|word-spacing|word-wrap|z-index\",u=t.supportFunction=\"rgb|rgba|url|attr|counter|counters\",a=t.supportConstant=\"absolute|after-edge|after|all-scroll|all|alphabetic|always|antialiased|armenian|auto|avoid-column|avoid-page|avoid|balance|baseline|before-edge|before|below|bidi-override|block-line-height|block|bold|bolder|border-box|both|bottom|box|break-all|break-word|capitalize|caps-height|caption|center|central|char|circle|cjk-ideographic|clone|close-quote|col-resize|collapse|column|consider-shifts|contain|content-box|cover|crosshair|cubic-bezier|dashed|decimal-leading-zero|decimal|default|disabled|disc|disregard-shifts|distribute-all-lines|distribute-letter|distribute-space|distribute|dotted|double|e-resize|ease-in|ease-in-out|ease-out|ease|ellipsis|end|exclude-ruby|fill|fixed|georgian|glyphs|grid-height|groove|hand|hanging|hebrew|help|hidden|hiragana-iroha|hiragana|horizontal|icon|ideograph-alpha|ideograph-numeric|ideograph-parenthesis|ideograph-space|ideographic|inactive|include-ruby|inherit|initial|inline-block|inline-box|inline-line-height|inline-table|inline|inset|inside|inter-ideograph|inter-word|invert|italic|justify|katakana-iroha|katakana|keep-all|last|left|lighter|line-edge|line-through|line|linear|list-item|local|loose|lower-alpha|lower-greek|lower-latin|lower-roman|lowercase|lr-tb|ltr|mathematical|max-height|max-size|medium|menu|message-box|middle|move|n-resize|ne-resize|newspaper|no-change|no-close-quote|no-drop|no-open-quote|no-repeat|none|normal|not-allowed|nowrap|nw-resize|oblique|open-quote|outset|outside|overline|padding-box|page|pointer|pre-line|pre-wrap|pre|preserve-3d|progress|relative|repeat-x|repeat-y|repeat|replaced|reset-size|ridge|right|round|row-resize|rtl|s-resize|scroll|se-resize|separate|slice|small-caps|small-caption|solid|space|square|start|static|status-bar|step-end|step-start|steps|stretch|strict|sub|super|sw-resize|table-caption|table-cell|table-column-group|table-column|table-footer-group|table-header-group|table-row-group|table-row|table|tb-rl|text-after-edge|text-before-edge|text-bottom|text-size|text-top|text|thick|thin|transparent|underline|upper-alpha|upper-latin|upper-roman|uppercase|use-script|vertical-ideographic|vertical-text|visible|w-resize|wait|whitespace|z-index|zero\",f=t.supportConstantColor=\"aqua|black|blue|fuchsia|gray|green|lime|maroon|navy|olive|orange|purple|red|silver|teal|white|yellow\",l=t.supportConstantFonts=\"arial|century|comic|courier|cursive|fantasy|garamond|georgia|helvetica|impact|lucida|symbol|system|tahoma|times|trebuchet|utopia|verdana|webdings|sans-serif|serif|monospace\",c=t.numRe=\"\\\\-?(?:(?:[0-9]+)|(?:[0-9]*\\\\.[0-9]+))\",h=t.pseudoElements=\"(\\\\:+)\\\\b(after|before|first-letter|first-line|moz-selection|selection)\\\\b\",p=t.pseudoClasses=\"(:)\\\\b(active|checked|disabled|empty|enabled|first-child|first-of-type|focus|hover|indeterminate|invalid|last-child|last-of-type|link|not|nth-child|nth-last-child|nth-last-of-type|nth-of-type|only-child|only-of-type|required|root|target|valid|visited)\\\\b\",d=function(){var e=this.createKeywordMapper({\"support.function\":u,\"support.constant\":a,\"support.type\":o,\"support.constant.color\":f,\"support.constant.fonts\":l},\"text\",!0);this.$rules={start:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"@.*?{\",push:\"media\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],media:[{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"paren.lparen\",regex:\"\\\\{\",push:\"ruleset\"},{token:\"string\",regex:\"\\\\}\",next:\"pop\"},{token:\"keyword\",regex:\"#[a-z0-9-_]+\"},{token:\"variable\",regex:\"\\\\.[a-z0-9-_]+\"},{token:\"string\",regex:\":[a-z0-9-_]+\"},{token:\"constant\",regex:\"[a-z0-9-_]+\"},{caseInsensitive:!0}],comment:[{token:\"comment\",regex:\"\\\\*\\\\/\",next:\"pop\"},{defaultToken:\"comment\"}],ruleset:[{token:\"paren.rparen\",regex:\"\\\\}\",next:\"pop\"},{token:\"comment\",regex:\"\\\\/\\\\*\",push:\"comment\"},{token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},{token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},{token:[\"constant.numeric\",\"keyword\"],regex:\"(\"+c+\")(ch|cm|deg|em|ex|fr|gd|grad|Hz|in|kHz|mm|ms|pc|pt|px|rad|rem|s|turn|vh|vm|vw|%)\"},{token:\"constant.numeric\",regex:c},{token:\"constant.numeric\",regex:\"#[a-f0-9]{6}\"},{token:\"constant.numeric\",regex:\"#[a-f0-9]{3}\"},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-element.css\"],regex:h},{token:[\"punctuation\",\"entity.other.attribute-name.pseudo-class.css\"],regex:p},{token:[\"support.function\",\"string\",\"support.function\"],regex:\"(url\\\\()(.*)(\\\\))\"},{token:e,regex:\"\\\\-?[a-zA-Z_][a-zA-Z0-9_\\\\-]*\"},{caseInsensitive:!0}]},this.normalizeRules()};r.inherits(d,s),t.CssHighlightRules=d}),define(\"ace/mode/css_completions\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={background:{\"#$0\":1},\"background-color\":{\"#$0\":1,transparent:1,fixed:1},\"background-image\":{\"url('/$0')\":1},\"background-repeat\":{repeat:1,\"repeat-x\":1,\"repeat-y\":1,\"no-repeat\":1,inherit:1},\"background-position\":{bottom:2,center:2,left:2,right:2,top:2,inherit:2},\"background-attachment\":{scroll:1,fixed:1},\"background-size\":{cover:1,contain:1},\"background-clip\":{\"border-box\":1,\"padding-box\":1,\"content-box\":1},\"background-origin\":{\"border-box\":1,\"padding-box\":1,\"content-box\":1},border:{\"solid $0\":1,\"dashed $0\":1,\"dotted $0\":1,\"#$0\":1},\"border-color\":{\"#$0\":1},\"border-style\":{solid:2,dashed:2,dotted:2,\"double\":2,groove:2,hidden:2,inherit:2,inset:2,none:2,outset:2,ridged:2},\"border-collapse\":{collapse:1,separate:1},bottom:{px:1,em:1,\"%\":1},clear:{left:1,right:1,both:1,none:1},color:{\"#$0\":1,\"rgb(#$00,0,0)\":1},cursor:{\"default\":1,pointer:1,move:1,text:1,wait:1,help:1,progress:1,\"n-resize\":1,\"ne-resize\":1,\"e-resize\":1,\"se-resize\":1,\"s-resize\":1,\"sw-resize\":1,\"w-resize\":1,\"nw-resize\":1},display:{none:1,block:1,inline:1,\"inline-block\":1,\"table-cell\":1},\"empty-cells\":{show:1,hide:1},\"float\":{left:1,right:1,none:1},\"font-family\":{Arial:2,\"Comic Sans MS\":2,Consolas:2,\"Courier New\":2,Courier:2,Georgia:2,Monospace:2,\"Sans-Serif\":2,\"Segoe UI\":2,Tahoma:2,\"Times New Roman\":2,\"Trebuchet MS\":2,Verdana:1},\"font-size\":{px:1,em:1,\"%\":1},\"font-weight\":{bold:1,normal:1},\"font-style\":{italic:1,normal:1},\"font-variant\":{normal:1,\"small-caps\":1},height:{px:1,em:1,\"%\":1},left:{px:1,em:1,\"%\":1},\"letter-spacing\":{normal:1},\"line-height\":{normal:1},\"list-style-type\":{none:1,disc:1,circle:1,square:1,decimal:1,\"decimal-leading-zero\":1,\"lower-roman\":1,\"upper-roman\":1,\"lower-greek\":1,\"lower-latin\":1,\"upper-latin\":1,georgian:1,\"lower-alpha\":1,\"upper-alpha\":1},margin:{px:1,em:1,\"%\":1},\"margin-right\":{px:1,em:1,\"%\":1},\"margin-left\":{px:1,em:1,\"%\":1},\"margin-top\":{px:1,em:1,\"%\":1},\"margin-bottom\":{px:1,em:1,\"%\":1},\"max-height\":{px:1,em:1,\"%\":1},\"max-width\":{px:1,em:1,\"%\":1},\"min-height\":{px:1,em:1,\"%\":1},\"min-width\":{px:1,em:1,\"%\":1},overflow:{hidden:1,visible:1,auto:1,scroll:1},\"overflow-x\":{hidden:1,visible:1,auto:1,scroll:1},\"overflow-y\":{hidden:1,visible:1,auto:1,scroll:1},padding:{px:1,em:1,\"%\":1},\"padding-top\":{px:1,em:1,\"%\":1},\"padding-right\":{px:1,em:1,\"%\":1},\"padding-bottom\":{px:1,em:1,\"%\":1},\"padding-left\":{px:1,em:1,\"%\":1},\"page-break-after\":{auto:1,always:1,avoid:1,left:1,right:1},\"page-break-before\":{auto:1,always:1,avoid:1,left:1,right:1},position:{absolute:1,relative:1,fixed:1,\"static\":1},right:{px:1,em:1,\"%\":1},\"table-layout\":{fixed:1,auto:1},\"text-decoration\":{none:1,underline:1,\"line-through\":1,blink:1},\"text-align\":{left:1,right:1,center:1,justify:1},\"text-transform\":{capitalize:1,uppercase:1,lowercase:1,none:1},top:{px:1,em:1,\"%\":1},\"vertical-align\":{top:1,bottom:1},visibility:{hidden:1,visible:1},\"white-space\":{nowrap:1,normal:1,pre:1,\"pre-line\":1,\"pre-wrap\":1},width:{px:1,em:1,\"%\":1},\"word-spacing\":{normal:1},filter:{\"alpha(opacity=$0100)\":1},\"text-shadow\":{\"$02px 2px 2px #777\":1},\"text-overflow\":{\"ellipsis-word\":1,clip:1,ellipsis:1},\"-moz-border-radius\":1,\"-moz-border-radius-topright\":1,\"-moz-border-radius-bottomright\":1,\"-moz-border-radius-topleft\":1,\"-moz-border-radius-bottomleft\":1,\"-webkit-border-radius\":1,\"-webkit-border-top-right-radius\":1,\"-webkit-border-top-left-radius\":1,\"-webkit-border-bottom-right-radius\":1,\"-webkit-border-bottom-left-radius\":1,\"-moz-box-shadow\":1,\"-webkit-box-shadow\":1,transform:{\"rotate($00deg)\":1,\"skew($00deg)\":1},\"-moz-transform\":{\"rotate($00deg)\":1,\"skew($00deg)\":1},\"-webkit-transform\":{\"rotate($00deg)\":1,\"skew($00deg)\":1}},i=function(){};(function(){this.completionsDefined=!1,this.defineCompletions=function(){if(document){var e=document.createElement(\"c\").style;for(var t in e){if(typeof e[t]!=\"string\")continue;var n=t.replace(/[A-Z]/g,function(e){return\"-\"+e.toLowerCase()});r.hasOwnProperty(n)||(r[n]=1)}}this.completionsDefined=!0},this.getCompletions=function(e,t,n,r){this.completionsDefined||this.defineCompletions();var i=t.getTokenAt(n.row,n.column);if(!i)return[];if(e===\"ruleset\"){var s=t.getLine(n.row).substr(0,n.column);return/:[^;]+$/.test(s)?(/([\\w\\-]+):[^:]*$/.test(s),this.getPropertyValueCompletions(e,t,n,r)):this.getPropertyCompletions(e,t,n,r)}return[]},this.getPropertyCompletions=function(e,t,n,i){var s=Object.keys(r);return s.map(function(e){return{caption:e,snippet:e+\": $0\",meta:\"property\",score:Number.MAX_VALUE}})},this.getPropertyValueCompletions=function(e,t,n,i){var s=t.getLine(n.row).substr(0,n.column),o=(/([\\w\\-]+):[^:]*$/.exec(s)||{})[1];if(!o)return[];var u=[];return o in r&&typeof r[o]==\"object\"&&(u=Object.keys(r[o])),u.map(function(e){return{caption:e,snippet:e,meta:\"property value\",score:Number.MAX_VALUE}})}}).call(i.prototype),t.CssCompletions=i}),define(\"ace/mode/behaviour/css\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/mode/behaviour/cstyle\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"./cstyle\").CstyleBehaviour,o=e(\"../../token_iterator\").TokenIterator,u=function(){this.inherit(s),this.add(\"colon\",\"insertion\",function(e,t,n,r,i){if(i===\":\"){var s=n.getCursorPosition(),u=new o(r,s.row,s.column),a=u.getCurrentToken();a&&a.value.match(/\\s+/)&&(a=u.stepBackward());if(a&&a.type===\"support.type\"){var f=r.doc.getLine(s.row),l=f.substring(s.column,s.column+1);if(l===\":\")return{text:\"\",selection:[1,1]};if(!f.substring(s.column).match(/^\\s*;/))return{text:\":;\",selection:[1,1]}}}}),this.add(\"colon\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&s===\":\"){var u=n.getCursorPosition(),a=new o(r,u.row,u.column),f=a.getCurrentToken();f&&f.value.match(/\\s+/)&&(f=a.stepBackward());if(f&&f.type===\"support.type\"){var l=r.doc.getLine(i.start.row),c=l.substring(i.end.column,i.end.column+1);if(c===\";\")return i.end.column++,i}}}),this.add(\"semicolon\",\"insertion\",function(e,t,n,r,i){if(i===\";\"){var s=n.getCursorPosition(),o=r.doc.getLine(s.row),u=o.substring(s.column,s.column+1);if(u===\";\")return{text:\"\",selection:[1,1]}}})};r.inherits(u,s),t.CssBehaviour=u}),define(\"ace/mode/css\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/css_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/worker/worker_client\",\"ace/mode/css_completions\",\"ace/mode/behaviour/css\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./css_highlight_rules\").CssHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"../worker/worker_client\").WorkerClient,a=e(\"./css_completions\").CssCompletions,f=e(\"./behaviour/css\").CssBehaviour,l=e(\"./folding/cstyle\").FoldMode,c=function(){this.HighlightRules=s,this.$outdent=new o,this.$behaviour=new f,this.$completer=new a,this.foldingRules=new l};r.inherits(c,i),function(){this.foldingRules=\"cStyle\",this.blockComment={start:\"/*\",end:\"*/\"},this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t),i=this.getTokenizer().getLineTokens(t,e).tokens;if(i.length&&i[i.length-1].type==\"comment\")return r;var s=t.match(/^.*\\{\\s*$/);return s&&(r+=n),r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.getCompletions=function(e,t,n,r){return this.$completer.getCompletions(e,t,n,r)},this.createWorker=function(e){var t=new u([\"ace\"],\"ace/mode/css_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),t.on(\"annotate\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/css\"}.call(c.prototype),t.Mode=c}),define(\"ace/mode/xml_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(e){var t=\"[_:a-zA-Z\\u00c0-\\uffff][-_:.a-zA-Z0-9\\u00c0-\\uffff]*\";this.$rules={start:[{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\",next:\"cdata\"},{token:[\"punctuation.xml-decl.xml\",\"keyword.xml-decl.xml\"],regex:\"(<\\\\?)(xml)(?=[\\\\s])\",next:\"xml_decl\",caseInsensitive:!0},{token:[\"punctuation.instruction.xml\",\"keyword.instruction.xml\"],regex:\"(<\\\\?)(\"+t+\")\",next:\"processing_instruction\"},{token:\"comment.xml\",regex:\"<\\\\!--\",next:\"comment\"},{token:[\"xml-pe.doctype.xml\",\"xml-pe.doctype.xml\"],regex:\"(<\\\\!)(DOCTYPE)(?=[\\\\s])\",next:\"doctype\",caseInsensitive:!0},{include:\"tag\"},{token:\"text.end-tag-open.xml\",regex:\"</\"},{token:\"text.tag-open.xml\",regex:\"<\"},{include:\"reference\"},{defaultToken:\"text.xml\"}],xml_decl:[{token:\"entity.other.attribute-name.decl-attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.decl-attribute-equals.xml\",regex:\"=\"},{include:\"whitespace\"},{include:\"string\"},{token:\"punctuation.xml-decl.xml\",regex:\"\\\\?>\",next:\"start\"}],processing_instruction:[{token:\"punctuation.instruction.xml\",regex:\"\\\\?>\",next:\"start\"},{defaultToken:\"instruction.xml\"}],doctype:[{include:\"whitespace\"},{include:\"string\"},{token:\"xml-pe.doctype.xml\",regex:\">\",next:\"start\"},{token:\"xml-pe.xml\",regex:\"[-_a-zA-Z0-9:]+\"},{token:\"punctuation.int-subset\",regex:\"\\\\[\",push:\"int_subset\"}],int_subset:[{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"punctuation.int-subset.xml\",regex:\"]\",next:\"pop\"},{token:[\"punctuation.markup-decl.xml\",\"keyword.markup-decl.xml\"],regex:\"(<\\\\!)(\"+t+\")\",push:[{token:\"text\",regex:\"\\\\s+\"},{token:\"punctuation.markup-decl.xml\",regex:\">\",next:\"pop\"},{include:\"string\"}]}],cdata:[{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\",next:\"start\"},{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"text.xml\",regex:\"(?:[^\\\\]]|\\\\](?!\\\\]>))+\"}],comment:[{token:\"comment.xml\",regex:\"-->\",next:\"start\"},{defaultToken:\"comment.xml\"}],reference:[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],attr_reference:[{token:\"constant.language.escape.reference.attribute-value.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],tag:[{token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.tag-name.xml\"],regex:\"(?:(<)|(</))((?:\"+t+\":)?\"+t+\")\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}],tag_whitespace:[{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"}],whitespace:[{token:\"text.whitespace.xml\",regex:\"\\\\s+\"}],string:[{token:\"string.xml\",regex:\"'\",push:[{token:\"string.xml\",regex:\"'\",next:\"pop\"},{defaultToken:\"string.xml\"}]},{token:\"string.xml\",regex:'\"',push:[{token:\"string.xml\",regex:'\"',next:\"pop\"},{defaultToken:\"string.xml\"}]}],attributes:[{token:\"entity.other.attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{include:\"tag_whitespace\"},{include:\"attribute_value\"}],attribute_value:[{token:\"string.attribute-value.xml\",regex:\"'\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]}]},this.constructor===s&&this.normalizeRules()};(function(){this.embedTagRules=function(e,t,n){this.$rules.tag.unshift({token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(<)(\"+n+\"(?=\\\\s|>|$))\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:t+\"start\"}]}),this.$rules[n+\"-end\"]=[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\",onMatch:function(e,t,n){return n.splice(0),this.token}}],this.embedRules(e,t,[{token:[\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(</)(\"+n+\"(?=\\\\s|>|$))\",next:n+\"-end\"},{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\"},{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\"}])}}).call(i.prototype),r.inherits(s,i),t.XmlHighlightRules=s}),define(\"ace/mode/html_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/css_highlight_rules\",\"ace/mode/javascript_highlight_rules\",\"ace/mode/xml_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./css_highlight_rules\").CssHighlightRules,o=e(\"./javascript_highlight_rules\").JavaScriptHighlightRules,u=e(\"./xml_highlight_rules\").XmlHighlightRules,a=i.createMap({a:\"anchor\",button:\"form\",form:\"form\",img:\"image\",input:\"form\",label:\"form\",option:\"form\",script:\"script\",select:\"form\",textarea:\"form\",style:\"style\",table:\"table\",tbody:\"table\",td:\"table\",tfoot:\"table\",th:\"table\",tr:\"table\"}),f=function(){u.call(this),this.addRules({attributes:[{include:\"tag_whitespace\"},{token:\"entity.other.attribute-name.xml\",regex:\"[-_a-zA-Z0-9:.]+\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\",push:[{include:\"tag_whitespace\"},{token:\"string.unquoted.attribute-value.html\",regex:\"[^<>='\\\"`\\\\s]+\",next:\"pop\"},{token:\"empty\",regex:\"\",next:\"pop\"}]},{include:\"attribute_value\"}],tag:[{token:function(e,t){var n=a[t];return[\"meta.tag.punctuation.\"+(e==\"<\"?\"\":\"end-\")+\"tag-open.xml\",\"meta.tag\"+(n?\".\"+n:\"\")+\".tag-name.xml\"]},regex:\"(</?)([-_a-zA-Z0-9:.]+)\",next:\"tag_stuff\"}],tag_stuff:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}),this.embedTagRules(s,\"css-\",\"style\"),this.embedTagRules((new o({jsx:!1})).getRules(),\"js-\",\"script\"),this.constructor===f&&this.normalizeRules()};r.inherits(f,u),t.HtmlHighlightRules=f}),define(\"ace/mode/behaviour/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/token_iterator\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";function u(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"../../token_iterator\").TokenIterator,o=e(\"../../lib/lang\"),a=function(){this.add(\"string_dquotes\",\"insertion\",function(e,t,n,r,i){if(i=='\"'||i==\"'\"){var o=i,a=r.doc.getTextRange(n.getSelectionRange());if(a!==\"\"&&a!==\"'\"&&a!='\"'&&n.getWrapBehavioursEnabled())return{text:o+a+o,selection:!1};var f=n.getCursorPosition(),l=r.doc.getLine(f.row),c=l.substring(f.column,f.column+1),h=new s(r,f.row,f.column),p=h.getCurrentToken();if(c==o&&(u(p,\"attribute-value\")||u(p,\"string\")))return{text:\"\",selection:[1,1]};p||(p=h.stepBackward());if(!p)return;while(u(p,\"tag-whitespace\")||u(p,\"whitespace\"))p=h.stepBackward();var d=!c||c.match(/\\s/);if(u(p,\"attribute-equals\")&&(d||c==\">\")||u(p,\"decl-attribute-equals\")&&(d||c==\"?\"))return{text:o+o,selection:[1,1]}}}),this.add(\"string_dquotes\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&(s=='\"'||s==\"'\")){var o=r.doc.getLine(i.start.row),u=o.substring(i.start.column+1,i.start.column+2);if(u==s)return i.end.column++,i}}),this.add(\"autoclosing\",\"insertion\",function(e,t,n,r,i){if(i==\">\"){var o=n.getSelectionRange().start,a=new s(r,o.row,o.column),f=a.getCurrentToken()||a.stepBackward();if(!f||!(u(f,\"tag-name\")||u(f,\"tag-whitespace\")||u(f,\"attribute-name\")||u(f,\"attribute-equals\")||u(f,\"attribute-value\")))return;if(u(f,\"reference.attribute-value\"))return;if(u(f,\"attribute-value\")){var l=f.value.charAt(0);if(l=='\"'||l==\"'\"){var c=f.value.charAt(f.value.length-1),h=a.getCurrentTokenColumn()+f.value.length;if(h>o.column||h==o.column&&l!=c)return}}while(!u(f,\"tag-name\")){f=a.stepBackward();if(f.value==\"<\"){f=a.stepForward();break}}var p=a.getCurrentTokenRow(),d=a.getCurrentTokenColumn();if(u(a.stepBackward(),\"end-tag-open\"))return;var v=f.value;p==o.row&&(v=v.substring(0,o.column-d));if(this.voidElements.hasOwnProperty(v.toLowerCase()))return;return{text:\"></\"+v+\">\",selection:[1,1]}}}),this.add(\"autoindent\",\"insertion\",function(e,t,n,r,i){if(i==\"\\n\"){var o=n.getCursorPosition(),u=r.getLine(o.row),a=new s(r,o.row,o.column),f=a.getCurrentToken();if(f&&f.type.indexOf(\"tag-close\")!==-1){if(f.value==\"/>\")return;while(f&&f.type.indexOf(\"tag-name\")===-1)f=a.stepBackward();if(!f)return;var l=f.value,c=a.getCurrentTokenRow();f=a.stepBackward();if(!f||f.type.indexOf(\"end-tag\")!==-1)return;if(this.voidElements&&!this.voidElements[l]){var h=r.getTokenAt(o.row,o.column+1),u=r.getLine(c),p=this.$getIndent(u),d=p+r.getTabString();return h&&h.value===\"</\"?{text:\"\\n\"+d+\"\\n\"+p,selection:[1,d.length,1,d.length]}:{text:\"\\n\"+d}}}}})};r.inherits(a,i),t.XmlBehaviour=a}),define(\"ace/mode/folding/mixed\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=t.FoldMode=function(e,t){this.defaultMode=e,this.subModes=t};r.inherits(s,i),function(){this.$getMode=function(e){typeof e!=\"string\"&&(e=e[0]);for(var t in this.subModes)if(e.indexOf(t)===0)return this.subModes[t];return null},this.$tryMode=function(e,t,n,r){var i=this.$getMode(e);return i?i.getFoldWidget(t,n,r):\"\"},this.getFoldWidget=function(e,t,n){return this.$tryMode(e.getState(n-1),e,t,n)||this.$tryMode(e.getState(n),e,t,n)||this.defaultMode.getFoldWidget(e,t,n)},this.getFoldWidgetRange=function(e,t,n){var r=this.$getMode(e.getState(n-1));if(!r||!r.getFoldWidget(e,t,n))r=this.$getMode(e.getState(n));if(!r||!r.getFoldWidget(e,t,n))r=this.defaultMode;return r.getFoldWidgetRange(e,t,n)}}.call(s.prototype)}),define(\"ace/mode/folding/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/range\",\"ace/mode/folding/fold_mode\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";function l(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}var r=e(\"../../lib/oop\"),i=e(\"../../lib/lang\"),s=e(\"../../range\").Range,o=e(\"./fold_mode\").FoldMode,u=e(\"../../token_iterator\").TokenIterator,a=t.FoldMode=function(e,t){o.call(this),this.voidElements=e||{},this.optionalEndTags=r.mixin({},this.voidElements),t&&r.mixin(this.optionalEndTags,t)};r.inherits(a,o);var f=function(){this.tagName=\"\",this.closing=!1,this.selfClosing=!1,this.start={row:0,column:0},this.end={row:0,column:0}};(function(){this.getFoldWidget=function(e,t,n){var r=this._getFirstTagInLine(e,n);return r?r.closing||!r.tagName&&r.selfClosing?t==\"markbeginend\"?\"end\":\"\":!r.tagName||r.selfClosing||this.voidElements.hasOwnProperty(r.tagName.toLowerCase())?\"\":this._findEndTagInLine(e,n,r.tagName,r.end.column)?\"\":\"start\":\"\"},this._getFirstTagInLine=function(e,t){var n=e.getTokens(t),r=new f;for(var i=0;i<n.length;i++){var s=n[i];if(l(s,\"tag-open\")){r.end.column=r.start.column+s.value.length,r.closing=l(s,\"end-tag-open\"),s=n[++i];if(!s)return null;r.tagName=s.value,r.end.column+=s.value.length;for(i++;i<n.length;i++){s=n[i],r.end.column+=s.value.length;if(l(s,\"tag-close\")){r.selfClosing=s.value==\"/>\";break}}return r}if(l(s,\"tag-close\"))return r.selfClosing=s.value==\"/>\",r;r.start.column+=s.value.length}return null},this._findEndTagInLine=function(e,t,n,r){var i=e.getTokens(t),s=0;for(var o=0;o<i.length;o++){var u=i[o];s+=u.value.length;if(s<r)continue;if(l(u,\"end-tag-open\")){u=i[o+1];if(u&&u.value==n)return!0}}return!1},this._readTagForward=function(e){var t=e.getCurrentToken();if(!t)return null;var n=new f;do if(l(t,\"tag-open\"))n.closing=l(t,\"end-tag-open\"),n.start.row=e.getCurrentTokenRow(),n.start.column=e.getCurrentTokenColumn();else if(l(t,\"tag-name\"))n.tagName=t.value;else if(l(t,\"tag-close\"))return n.selfClosing=t.value==\"/>\",n.end.row=e.getCurrentTokenRow(),n.end.column=e.getCurrentTokenColumn()+t.value.length,e.stepForward(),n;while(t=e.stepForward());return null},this._readTagBackward=function(e){var t=e.getCurrentToken();if(!t)return null;var n=new f;do{if(l(t,\"tag-open\"))return n.closing=l(t,\"end-tag-open\"),n.start.row=e.getCurrentTokenRow(),n.start.column=e.getCurrentTokenColumn(),e.stepBackward(),n;l(t,\"tag-name\")?n.tagName=t.value:l(t,\"tag-close\")&&(n.selfClosing=t.value==\"/>\",n.end.row=e.getCurrentTokenRow(),n.end.column=e.getCurrentTokenColumn()+t.value.length)}while(t=e.stepBackward());return null},this._pop=function(e,t){while(e.length){var n=e[e.length-1];if(!t||n.tagName==t.tagName)return e.pop();if(this.optionalEndTags.hasOwnProperty(n.tagName)){e.pop();continue}return null}},this.getFoldWidgetRange=function(e,t,n){var r=this._getFirstTagInLine(e,n);if(!r)return null;var i=r.closing||r.selfClosing,o=[],a;if(!i){var f=new u(e,n,r.start.column),l={row:n,column:r.start.column+r.tagName.length+2};r.start.row==r.end.row&&(l.column=r.end.column);while(a=this._readTagForward(f)){if(a.selfClosing){if(!o.length)return a.start.column+=a.tagName.length+2,a.end.column-=2,s.fromPoints(a.start,a.end);continue}if(a.closing){this._pop(o,a);if(o.length==0)return s.fromPoints(l,a.start)}else o.push(a)}}else{var f=new u(e,n,r.end.column),c={row:n,column:r.start.column};while(a=this._readTagBackward(f)){if(a.selfClosing){if(!o.length)return a.start.column+=a.tagName.length+2,a.end.column-=2,s.fromPoints(a.start,a.end);continue}if(!a.closing){this._pop(o,a);if(o.length==0)return a.start.column+=a.tagName.length+2,a.start.row==a.end.row&&a.start.column<a.end.column&&(a.start.column=a.end.column),s.fromPoints(a.start,c)}else o.push(a)}}}}).call(a.prototype)}),define(\"ace/mode/folding/html\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/mixed\",\"ace/mode/folding/xml\",\"ace/mode/folding/cstyle\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./mixed\").FoldMode,s=e(\"./xml\").FoldMode,o=e(\"./cstyle\").FoldMode,u=t.FoldMode=function(e,t){i.call(this,new s(e,t),{\"js-\":new o,\"css-\":new o})};r.inherits(u,i)}),define(\"ace/mode/html_completions\",[\"require\",\"exports\",\"module\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";function f(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}function l(e,t){var n=new r(e,t.row,t.column),i=n.getCurrentToken();while(i&&!f(i,\"tag-name\"))i=n.stepBackward();if(i)return i.value}function c(e,t){var n=new r(e,t.row,t.column),i=n.getCurrentToken();while(i&&!f(i,\"attribute-name\"))i=n.stepBackward();if(i)return i.value}var r=e(\"../token_iterator\").TokenIterator,i=[\"accesskey\",\"class\",\"contenteditable\",\"contextmenu\",\"dir\",\"draggable\",\"dropzone\",\"hidden\",\"id\",\"inert\",\"itemid\",\"itemprop\",\"itemref\",\"itemscope\",\"itemtype\",\"lang\",\"spellcheck\",\"style\",\"tabindex\",\"title\",\"translate\"],s=[\"onabort\",\"onblur\",\"oncancel\",\"oncanplay\",\"oncanplaythrough\",\"onchange\",\"onclick\",\"onclose\",\"oncontextmenu\",\"oncuechange\",\"ondblclick\",\"ondrag\",\"ondragend\",\"ondragenter\",\"ondragleave\",\"ondragover\",\"ondragstart\",\"ondrop\",\"ondurationchange\",\"onemptied\",\"onended\",\"onerror\",\"onfocus\",\"oninput\",\"oninvalid\",\"onkeydown\",\"onkeypress\",\"onkeyup\",\"onload\",\"onloadeddata\",\"onloadedmetadata\",\"onloadstart\",\"onmousedown\",\"onmousemove\",\"onmouseout\",\"onmouseover\",\"onmouseup\",\"onmousewheel\",\"onpause\",\"onplay\",\"onplaying\",\"onprogress\",\"onratechange\",\"onreset\",\"onscroll\",\"onseeked\",\"onseeking\",\"onselect\",\"onshow\",\"onstalled\",\"onsubmit\",\"onsuspend\",\"ontimeupdate\",\"onvolumechange\",\"onwaiting\"],o=i.concat(s),u={html:{manifest:1},head:{},title:{},base:{href:1,target:1},link:{href:1,hreflang:1,rel:{stylesheet:1,icon:1},media:{all:1,screen:1,print:1},type:{\"text/css\":1,\"image/png\":1,\"image/jpeg\":1,\"image/gif\":1},sizes:1},meta:{\"http-equiv\":{\"content-type\":1},name:{description:1,keywords:1},content:{\"text/html; charset=UTF-8\":1},charset:1},style:{type:1,media:{all:1,screen:1,print:1},scoped:1},script:{charset:1,type:{\"text/javascript\":1},src:1,defer:1,async:1},noscript:{href:1},body:{onafterprint:1,onbeforeprint:1,onbeforeunload:1,onhashchange:1,onmessage:1,onoffline:1,onpopstate:1,onredo:1,onresize:1,onstorage:1,onundo:1,onunload:1},section:{},nav:{},article:{pubdate:1},aside:{},h1:{},h2:{},h3:{},h4:{},h5:{},h6:{},header:{},footer:{},address:{},main:{},p:{},hr:{},pre:{},blockquote:{cite:1},ol:{start:1,reversed:1},ul:{},li:{value:1},dl:{},dt:{},dd:{},figure:{},figcaption:{},div:{},a:{href:1,target:{_blank:1,top:1},ping:1,rel:{nofollow:1,alternate:1,author:1,bookmark:1,help:1,license:1,next:1,noreferrer:1,prefetch:1,prev:1,search:1,tag:1},media:1,hreflang:1,type:1},em:{},strong:{},small:{},s:{},cite:{},q:{cite:1},dfn:{},abbr:{},data:{},time:{datetime:1},code:{},\"var\":{},samp:{},kbd:{},sub:{},sup:{},i:{},b:{},u:{},mark:{},ruby:{},rt:{},rp:{},bdi:{},bdo:{},span:{},br:{},wbr:{},ins:{cite:1,datetime:1},del:{cite:1,datetime:1},img:{alt:1,src:1,height:1,width:1,usemap:1,ismap:1},iframe:{name:1,src:1,height:1,width:1,sandbox:{\"allow-same-origin\":1,\"allow-top-navigation\":1,\"allow-forms\":1,\"allow-scripts\":1},seamless:{seamless:1}},embed:{src:1,height:1,width:1,type:1},object:{param:1,data:1,type:1,height:1,width:1,usemap:1,name:1,form:1,classid:1},param:{name:1,value:1},video:{src:1,autobuffer:1,autoplay:{autoplay:1},loop:{loop:1},controls:{controls:1},width:1,height:1,poster:1,muted:{muted:1},preload:{auto:1,metadata:1,none:1}},audio:{src:1,autobuffer:1,autoplay:{autoplay:1},loop:{loop:1},controls:{controls:1},muted:{muted:1},preload:{auto:1,metadata:1,none:1}},source:{src:1,type:1,media:1},track:{kind:1,src:1,srclang:1,label:1,\"default\":1},canvas:{width:1,height:1},map:{name:1},area:{shape:1,coords:1,href:1,hreflang:1,alt:1,target:1,media:1,rel:1,ping:1,type:1},svg:{},math:{},table:{summary:1},caption:{},colgroup:{span:1},col:{span:1},tbody:{},thead:{},tfoot:{},tr:{},td:{headers:1,rowspan:1,colspan:1},th:{headers:1,rowspan:1,colspan:1,scope:1},form:{\"accept-charset\":1,action:1,autocomplete:1,enctype:{\"multipart/form-data\":1,\"application/x-www-form-urlencoded\":1},method:{get:1,post:1},name:1,novalidate:1,target:{_blank:1,top:1}},fieldset:{disabled:1,form:1,name:1},legend:{},label:{form:1,\"for\":1},input:{type:{text:1,password:1,hidden:1,checkbox:1,submit:1,radio:1,file:1,button:1,reset:1,image:31,color:1,date:1,datetime:1,\"datetime-local\":1,email:1,month:1,number:1,range:1,search:1,tel:1,time:1,url:1,week:1},accept:1,alt:1,autocomplete:{on:1,off:1},autofocus:{autofocus:1},checked:{checked:1},disabled:{disabled:1},form:1,formaction:1,formenctype:{\"application/x-www-form-urlencoded\":1,\"multipart/form-data\":1,\"text/plain\":1},formmethod:{get:1,post:1},formnovalidate:{formnovalidate:1},formtarget:{_blank:1,_self:1,_parent:1,_top:1},height:1,list:1,max:1,maxlength:1,min:1,multiple:{multiple:1},name:1,pattern:1,placeholder:1,readonly:{readonly:1},required:{required:1},size:1,src:1,step:1,width:1,files:1,value:1},button:{autofocus:1,disabled:{disabled:1},form:1,formaction:1,formenctype:1,formmethod:1,formnovalidate:1,formtarget:1,name:1,value:1,type:{button:1,submit:1}},select:{autofocus:1,disabled:1,form:1,multiple:{multiple:1},name:1,size:1,readonly:{readonly:1}},datalist:{},optgroup:{disabled:1,label:1},option:{disabled:1,selected:1,label:1,value:1},textarea:{autofocus:{autofocus:1},disabled:{disabled:1},form:1,maxlength:1,name:1,placeholder:1,readonly:{readonly:1},required:{required:1},rows:1,cols:1,wrap:{on:1,off:1,hard:1,soft:1}},keygen:{autofocus:1,challenge:{challenge:1},disabled:{disabled:1},form:1,keytype:{rsa:1,dsa:1,ec:1},name:1},output:{\"for\":1,form:1,name:1},progress:{value:1,max:1},meter:{value:1,min:1,max:1,low:1,high:1,optimum:1},details:{open:1},summary:{},command:{type:1,label:1,icon:1,disabled:1,checked:1,radiogroup:1,command:1},menu:{type:1,label:1},dialog:{open:1}},a=Object.keys(u),h=function(){};(function(){this.getCompletions=function(e,t,n,r){var i=t.getTokenAt(n.row,n.column);if(!i)return[];if(f(i,\"tag-name\")||f(i,\"tag-open\")||f(i,\"end-tag-open\"))return this.getTagCompletions(e,t,n,r);if(f(i,\"tag-whitespace\")||f(i,\"attribute-name\"))return this.getAttributeCompletions(e,t,n,r);if(f(i,\"attribute-value\"))return this.getAttributeValueCompletions(e,t,n,r);var s=t.getLine(n.row).substr(0,n.column);return/&[a-z]*$/i.test(s)?this.getHTMLEntityCompletions(e,t,n,r):[]},this.getTagCompletions=function(e,t,n,r){return a.map(function(e){return{value:e,meta:\"tag\",score:Number.MAX_VALUE}})},this.getAttributeCompletions=function(e,t,n,r){var i=l(t,n);if(!i)return[];var s=o;return i in u&&(s=s.concat(Object.keys(u[i]))),s.map(function(e){return{caption:e,snippet:e+'=\"$0\"',meta:\"attribute\",score:Number.MAX_VALUE}})},this.getAttributeValueCompletions=function(e,t,n,r){var i=l(t,n),s=c(t,n);if(!i)return[];var o=[];return i in u&&s in u[i]&&typeof u[i][s]==\"object\"&&(o=Object.keys(u[i][s])),o.map(function(e){return{caption:e,snippet:e,meta:\"attribute value\",score:Number.MAX_VALUE}})},this.getHTMLEntityCompletions=function(e,t,n,r){var i=[\"Aacute;\",\"aacute;\",\"Acirc;\",\"acirc;\",\"acute;\",\"AElig;\",\"aelig;\",\"Agrave;\",\"agrave;\",\"alefsym;\",\"Alpha;\",\"alpha;\",\"amp;\",\"and;\",\"ang;\",\"Aring;\",\"aring;\",\"asymp;\",\"Atilde;\",\"atilde;\",\"Auml;\",\"auml;\",\"bdquo;\",\"Beta;\",\"beta;\",\"brvbar;\",\"bull;\",\"cap;\",\"Ccedil;\",\"ccedil;\",\"cedil;\",\"cent;\",\"Chi;\",\"chi;\",\"circ;\",\"clubs;\",\"cong;\",\"copy;\",\"crarr;\",\"cup;\",\"curren;\",\"Dagger;\",\"dagger;\",\"dArr;\",\"darr;\",\"deg;\",\"Delta;\",\"delta;\",\"diams;\",\"divide;\",\"Eacute;\",\"eacute;\",\"Ecirc;\",\"ecirc;\",\"Egrave;\",\"egrave;\",\"empty;\",\"emsp;\",\"ensp;\",\"Epsilon;\",\"epsilon;\",\"equiv;\",\"Eta;\",\"eta;\",\"ETH;\",\"eth;\",\"Euml;\",\"euml;\",\"euro;\",\"exist;\",\"fnof;\",\"forall;\",\"frac12;\",\"frac14;\",\"frac34;\",\"frasl;\",\"Gamma;\",\"gamma;\",\"ge;\",\"gt;\",\"hArr;\",\"harr;\",\"hearts;\",\"hellip;\",\"Iacute;\",\"iacute;\",\"Icirc;\",\"icirc;\",\"iexcl;\",\"Igrave;\",\"igrave;\",\"image;\",\"infin;\",\"int;\",\"Iota;\",\"iota;\",\"iquest;\",\"isin;\",\"Iuml;\",\"iuml;\",\"Kappa;\",\"kappa;\",\"Lambda;\",\"lambda;\",\"lang;\",\"laquo;\",\"lArr;\",\"larr;\",\"lceil;\",\"ldquo;\",\"le;\",\"lfloor;\",\"lowast;\",\"loz;\",\"lrm;\",\"lsaquo;\",\"lsquo;\",\"lt;\",\"macr;\",\"mdash;\",\"micro;\",\"middot;\",\"minus;\",\"Mu;\",\"mu;\",\"nabla;\",\"nbsp;\",\"ndash;\",\"ne;\",\"ni;\",\"not;\",\"notin;\",\"nsub;\",\"Ntilde;\",\"ntilde;\",\"Nu;\",\"nu;\",\"Oacute;\",\"oacute;\",\"Ocirc;\",\"ocirc;\",\"OElig;\",\"oelig;\",\"Ograve;\",\"ograve;\",\"oline;\",\"Omega;\",\"omega;\",\"Omicron;\",\"omicron;\",\"oplus;\",\"or;\",\"ordf;\",\"ordm;\",\"Oslash;\",\"oslash;\",\"Otilde;\",\"otilde;\",\"otimes;\",\"Ouml;\",\"ouml;\",\"para;\",\"part;\",\"permil;\",\"perp;\",\"Phi;\",\"phi;\",\"Pi;\",\"pi;\",\"piv;\",\"plusmn;\",\"pound;\",\"Prime;\",\"prime;\",\"prod;\",\"prop;\",\"Psi;\",\"psi;\",\"quot;\",\"radic;\",\"rang;\",\"raquo;\",\"rArr;\",\"rarr;\",\"rceil;\",\"rdquo;\",\"real;\",\"reg;\",\"rfloor;\",\"Rho;\",\"rho;\",\"rlm;\",\"rsaquo;\",\"rsquo;\",\"sbquo;\",\"Scaron;\",\"scaron;\",\"sdot;\",\"sect;\",\"shy;\",\"Sigma;\",\"sigma;\",\"sigmaf;\",\"sim;\",\"spades;\",\"sub;\",\"sube;\",\"sum;\",\"sup;\",\"sup1;\",\"sup2;\",\"sup3;\",\"supe;\",\"szlig;\",\"Tau;\",\"tau;\",\"there4;\",\"Theta;\",\"theta;\",\"thetasym;\",\"thinsp;\",\"THORN;\",\"thorn;\",\"tilde;\",\"times;\",\"trade;\",\"Uacute;\",\"uacute;\",\"uArr;\",\"uarr;\",\"Ucirc;\",\"ucirc;\",\"Ugrave;\",\"ugrave;\",\"uml;\",\"upsih;\",\"Upsilon;\",\"upsilon;\",\"Uuml;\",\"uuml;\",\"weierp;\",\"Xi;\",\"xi;\",\"Yacute;\",\"yacute;\",\"yen;\",\"Yuml;\",\"yuml;\",\"Zeta;\",\"zeta;\",\"zwj;\",\"zwnj;\"];return i.map(function(e){return{caption:e,snippet:e,meta:\"html entity\",score:Number.MAX_VALUE}})}}).call(h.prototype),t.HtmlCompletions=h}),define(\"ace/mode/html\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text\",\"ace/mode/javascript\",\"ace/mode/css\",\"ace/mode/html_highlight_rules\",\"ace/mode/behaviour/xml\",\"ace/mode/folding/html\",\"ace/mode/html_completions\",\"ace/worker/worker_client\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text\").Mode,o=e(\"./javascript\").Mode,u=e(\"./css\").Mode,a=e(\"./html_highlight_rules\").HtmlHighlightRules,f=e(\"./behaviour/xml\").XmlBehaviour,l=e(\"./folding/html\").FoldMode,c=e(\"./html_completions\").HtmlCompletions,h=e(\"../worker/worker_client\").WorkerClient,p=[\"area\",\"base\",\"br\",\"col\",\"embed\",\"hr\",\"img\",\"input\",\"keygen\",\"link\",\"meta\",\"menuitem\",\"param\",\"source\",\"track\",\"wbr\"],d=[\"li\",\"dt\",\"dd\",\"p\",\"rt\",\"rp\",\"optgroup\",\"option\",\"colgroup\",\"td\",\"th\"],v=function(e){this.fragmentContext=e&&e.fragmentContext,this.HighlightRules=a,this.$behaviour=new f,this.$completer=new c,this.createModeDelegates({\"js-\":o,\"css-\":u}),this.foldingRules=new l(this.voidElements,i.arrayToMap(d))};r.inherits(v,s),function(){this.blockComment={start:\"<!--\",end:\"-->\"},this.voidElements=i.arrayToMap(p),this.getNextLineIndent=function(e,t,n){return this.$getIndent(t)},this.checkOutdent=function(e,t,n){return!1},this.getCompletions=function(e,t,n,r){return this.$completer.getCompletions(e,t,n,r)},this.createWorker=function(e){if(this.constructor!=v)return;var t=new h([\"ace\"],\"ace/mode/html_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),this.fragmentContext&&t.call(\"setOptions\",[{context:this.fragmentContext}]),t.on(\"error\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/html\"}.call(v.prototype),t.Mode=v}),define(\"ace/mode/smarty_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/html_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./html_highlight_rules\").HtmlHighlightRules,s=function(){i.call(this);var e={start:[{include:\"#comments\"},{include:\"#blocks\"}],\"#blocks\":[{token:\"punctuation.section.embedded.begin.smarty\",regex:\"\\\\{%?\",push:[{token:\"punctuation.section.embedded.end.smarty\",regex:\"%?\\\\}\",next:\"pop\"},{include:\"#strings\"},{include:\"#variables\"},{include:\"#lang\"},{defaultToken:\"source.smarty\"}]}],\"#comments\":[{token:[\"punctuation.definition.comment.smarty\",\"comment.block.smarty\"],regex:\"(\\\\{%?)(\\\\*)\",push:[{token:\"comment.block.smarty\",regex:\"\\\\*%?\\\\}\",next:\"pop\"},{defaultToken:\"comment.block.smarty\"}]}],\"#lang\":[{token:\"keyword.operator.smarty\",regex:\"(?:!=|!|<=|>=|<|>|===|==|%|&&|\\\\|\\\\|)|\\\\b(?:and|or|eq|neq|ne|gte|gt|ge|lte|lt|le|not|mod)\\\\b\"},{token:\"constant.language.smarty\",regex:\"\\\\b(?:TRUE|FALSE|true|false)\\\\b\"},{token:\"keyword.control.smarty\",regex:\"\\\\b(?:if|else|elseif|foreach|foreachelse|section|switch|case|break|default)\\\\b\"},{token:\"variable.parameter.smarty\",regex:\"\\\\b[a-zA-Z]+=\"},{token:\"support.function.built-in.smarty\",regex:\"\\\\b(?:capture|config_load|counter|cycle|debug|eval|fetch|include_php|include|insert|literal|math|strip|rdelim|ldelim|assign|constant|block|html_[a-z_]*)\\\\b\"},{token:\"support.function.variable-modifier.smarty\",regex:\"\\\\|(?:capitalize|cat|count_characters|count_paragraphs|count_sentences|count_words|date_format|default|escape|indent|lower|nl2br|regex_replace|replace|spacify|string_format|strip_tags|strip|truncate|upper|wordwrap)\"}],\"#strings\":[{token:\"punctuation.definition.string.begin.smarty\",regex:\"'\",push:[{token:\"punctuation.definition.string.end.smarty\",regex:\"'\",next:\"pop\"},{token:\"constant.character.escape.smarty\",regex:\"\\\\\\\\.\"},{defaultToken:\"string.quoted.single.smarty\"}]},{token:\"punctuation.definition.string.begin.smarty\",regex:'\"',push:[{token:\"punctuation.definition.string.end.smarty\",regex:'\"',next:\"pop\"},{token:\"constant.character.escape.smarty\",regex:\"\\\\\\\\.\"},{defaultToken:\"string.quoted.double.smarty\"}]}],\"#variables\":[{token:[\"punctuation.definition.variable.smarty\",\"variable.other.global.smarty\"],regex:\"\\\\b(\\\\$)(Smarty\\\\.)\"},{token:[\"punctuation.definition.variable.smarty\",\"variable.other.smarty\"],regex:\"(\\\\$)([a-zA-Z_][a-zA-Z0-9_]*)\\\\b\"},{token:[\"keyword.operator.smarty\",\"variable.other.property.smarty\"],regex:\"(->)([a-zA-Z_][a-zA-Z0-9_]*)\\\\b\"},{token:[\"keyword.operator.smarty\",\"meta.function-call.object.smarty\",\"punctuation.definition.variable.smarty\",\"variable.other.smarty\",\"punctuation.definition.variable.smarty\"],regex:\"(->)([a-zA-Z_][a-zA-Z0-9_]*)(\\\\()(.*?)(\\\\))\"}]},t=e.start;for(var n in this.$rules)this.$rules[n].unshift.apply(this.$rules[n],t);Object.keys(e).forEach(function(t){this.$rules[t]||(this.$rules[t]=e[t])},this),this.normalizeRules()};s.metaData={fileTypes:[\"tpl\"],foldingStartMarker:\"\\\\{%?\",foldingStopMarker:\"%?\\\\}\",name:\"Smarty\",scopeName:\"text.html.smarty\"},r.inherits(s,i),t.SmartyHighlightRules=s}),define(\"ace/mode/smarty\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/html\",\"ace/mode/smarty_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./html\").Mode,s=e(\"./smarty_highlight_rules\").SmartyHighlightRules,o=function(){i.call(this),this.HighlightRules=s};r.inherits(o,i),function(){this.$id=\"ace/mode/smarty\"}.call(o.prototype),t.Mode=o})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-sql.js",
    "content": "define(\"ace/mode/sql_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){var e=\"select|insert|update|delete|from|where|and|or|group|by|order|limit|offset|having|as|case|when|else|end|type|left|right|join|on|outer|desc|asc|union|create|table|primary|key|if|foreign|not|references|default|null|inner|cross|natural|database|drop|grant\",t=\"true|false\",n=\"avg|count|first|last|max|min|sum|ucase|lcase|mid|len|round|rank|now|format|coalesce|ifnull|isnull|nvl\",r=\"int|numeric|decimal|date|varchar|char|bigint|float|double|bit|binary|text|set|timestamp|money|real|number|integer\",i=this.createKeywordMapper({\"support.function\":n,keyword:e,\"constant.language\":t,\"storage.type\":r},\"identifier\",!0);this.$rules={start:[{token:\"comment\",regex:\"--.*$\"},{token:\"comment\",start:\"/\\\\*\",end:\"\\\\*/\"},{token:\"string\",regex:'\".*?\"'},{token:\"string\",regex:\"'.*?'\"},{token:\"constant.numeric\",regex:\"[+-]?\\\\d+(?:(?:\\\\.\\\\d*)?(?:[eE][+-]?\\\\d+)?)?\\\\b\"},{token:i,regex:\"[a-zA-Z_$][a-zA-Z0-9_$]*\\\\b\"},{token:\"keyword.operator\",regex:\"\\\\+|\\\\-|\\\\/|\\\\/\\\\/|%|<@>|@>|<@|&|\\\\^|~|<|>|<=|=>|==|!=|<>|=\"},{token:\"paren.lparen\",regex:\"[\\\\(]\"},{token:\"paren.rparen\",regex:\"[\\\\)]\"},{token:\"text\",regex:\"\\\\s+\"}]},this.normalizeRules()};r.inherits(s,i),t.SqlHighlightRules=s}),define(\"ace/mode/sql\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/sql_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./sql_highlight_rules\").SqlHighlightRules,o=function(){this.HighlightRules=s,this.$behaviour=this.$defaultBehaviour};r.inherits(o,i),function(){this.lineCommentStart=\"--\",this.$id=\"ace/mode/sql\"}.call(o.prototype),t.Mode=o})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-xml.js",
    "content": "define(\"ace/mode/xml_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(e){var t=\"[_:a-zA-Z\\u00c0-\\uffff][-_:.a-zA-Z0-9\\u00c0-\\uffff]*\";this.$rules={start:[{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\",next:\"cdata\"},{token:[\"punctuation.xml-decl.xml\",\"keyword.xml-decl.xml\"],regex:\"(<\\\\?)(xml)(?=[\\\\s])\",next:\"xml_decl\",caseInsensitive:!0},{token:[\"punctuation.instruction.xml\",\"keyword.instruction.xml\"],regex:\"(<\\\\?)(\"+t+\")\",next:\"processing_instruction\"},{token:\"comment.xml\",regex:\"<\\\\!--\",next:\"comment\"},{token:[\"xml-pe.doctype.xml\",\"xml-pe.doctype.xml\"],regex:\"(<\\\\!)(DOCTYPE)(?=[\\\\s])\",next:\"doctype\",caseInsensitive:!0},{include:\"tag\"},{token:\"text.end-tag-open.xml\",regex:\"</\"},{token:\"text.tag-open.xml\",regex:\"<\"},{include:\"reference\"},{defaultToken:\"text.xml\"}],xml_decl:[{token:\"entity.other.attribute-name.decl-attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.decl-attribute-equals.xml\",regex:\"=\"},{include:\"whitespace\"},{include:\"string\"},{token:\"punctuation.xml-decl.xml\",regex:\"\\\\?>\",next:\"start\"}],processing_instruction:[{token:\"punctuation.instruction.xml\",regex:\"\\\\?>\",next:\"start\"},{defaultToken:\"instruction.xml\"}],doctype:[{include:\"whitespace\"},{include:\"string\"},{token:\"xml-pe.doctype.xml\",regex:\">\",next:\"start\"},{token:\"xml-pe.xml\",regex:\"[-_a-zA-Z0-9:]+\"},{token:\"punctuation.int-subset\",regex:\"\\\\[\",push:\"int_subset\"}],int_subset:[{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"punctuation.int-subset.xml\",regex:\"]\",next:\"pop\"},{token:[\"punctuation.markup-decl.xml\",\"keyword.markup-decl.xml\"],regex:\"(<\\\\!)(\"+t+\")\",push:[{token:\"text\",regex:\"\\\\s+\"},{token:\"punctuation.markup-decl.xml\",regex:\">\",next:\"pop\"},{include:\"string\"}]}],cdata:[{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\",next:\"start\"},{token:\"text.xml\",regex:\"\\\\s+\"},{token:\"text.xml\",regex:\"(?:[^\\\\]]|\\\\](?!\\\\]>))+\"}],comment:[{token:\"comment.xml\",regex:\"-->\",next:\"start\"},{defaultToken:\"comment.xml\"}],reference:[{token:\"constant.language.escape.reference.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],attr_reference:[{token:\"constant.language.escape.reference.attribute-value.xml\",regex:\"(?:&#[0-9]+;)|(?:&#x[0-9a-fA-F]+;)|(?:&[a-zA-Z0-9_:\\\\.-]+;)\"}],tag:[{token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.tag-name.xml\"],regex:\"(?:(<)|(</))((?:\"+t+\":)?\"+t+\")\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\"}]}],tag_whitespace:[{token:\"text.tag-whitespace.xml\",regex:\"\\\\s+\"}],whitespace:[{token:\"text.whitespace.xml\",regex:\"\\\\s+\"}],string:[{token:\"string.xml\",regex:\"'\",push:[{token:\"string.xml\",regex:\"'\",next:\"pop\"},{defaultToken:\"string.xml\"}]},{token:\"string.xml\",regex:'\"',push:[{token:\"string.xml\",regex:'\"',next:\"pop\"},{defaultToken:\"string.xml\"}]}],attributes:[{token:\"entity.other.attribute-name.xml\",regex:\"(?:\"+t+\":)?\"+t+\"\"},{token:\"keyword.operator.attribute-equals.xml\",regex:\"=\"},{include:\"tag_whitespace\"},{include:\"attribute_value\"}],attribute_value:[{token:\"string.attribute-value.xml\",regex:\"'\",push:[{token:\"string.attribute-value.xml\",regex:\"'\",next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]},{token:\"string.attribute-value.xml\",regex:'\"',push:[{token:\"string.attribute-value.xml\",regex:'\"',next:\"pop\"},{include:\"attr_reference\"},{defaultToken:\"string.attribute-value.xml\"}]}]},this.constructor===s&&this.normalizeRules()};(function(){this.embedTagRules=function(e,t,n){this.$rules.tag.unshift({token:[\"meta.tag.punctuation.tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(<)(\"+n+\"(?=\\\\s|>|$))\",next:[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:t+\"start\"}]}),this.$rules[n+\"-end\"]=[{include:\"attributes\"},{token:\"meta.tag.punctuation.tag-close.xml\",regex:\"/?>\",next:\"start\",onMatch:function(e,t,n){return n.splice(0),this.token}}],this.embedRules(e,t,[{token:[\"meta.tag.punctuation.end-tag-open.xml\",\"meta.tag.\"+n+\".tag-name.xml\"],regex:\"(</)(\"+n+\"(?=\\\\s|>|$))\",next:n+\"-end\"},{token:\"string.cdata.xml\",regex:\"<\\\\!\\\\[CDATA\\\\[\"},{token:\"string.cdata.xml\",regex:\"\\\\]\\\\]>\"}])}}).call(i.prototype),r.inherits(s,i),t.XmlHighlightRules=s}),define(\"ace/mode/behaviour/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/behaviour\",\"ace/token_iterator\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";function u(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}var r=e(\"../../lib/oop\"),i=e(\"../behaviour\").Behaviour,s=e(\"../../token_iterator\").TokenIterator,o=e(\"../../lib/lang\"),a=function(){this.add(\"string_dquotes\",\"insertion\",function(e,t,n,r,i){if(i=='\"'||i==\"'\"){var o=i,a=r.doc.getTextRange(n.getSelectionRange());if(a!==\"\"&&a!==\"'\"&&a!='\"'&&n.getWrapBehavioursEnabled())return{text:o+a+o,selection:!1};var f=n.getCursorPosition(),l=r.doc.getLine(f.row),c=l.substring(f.column,f.column+1),h=new s(r,f.row,f.column),p=h.getCurrentToken();if(c==o&&(u(p,\"attribute-value\")||u(p,\"string\")))return{text:\"\",selection:[1,1]};p||(p=h.stepBackward());if(!p)return;while(u(p,\"tag-whitespace\")||u(p,\"whitespace\"))p=h.stepBackward();var d=!c||c.match(/\\s/);if(u(p,\"attribute-equals\")&&(d||c==\">\")||u(p,\"decl-attribute-equals\")&&(d||c==\"?\"))return{text:o+o,selection:[1,1]}}}),this.add(\"string_dquotes\",\"deletion\",function(e,t,n,r,i){var s=r.doc.getTextRange(i);if(!i.isMultiLine()&&(s=='\"'||s==\"'\")){var o=r.doc.getLine(i.start.row),u=o.substring(i.start.column+1,i.start.column+2);if(u==s)return i.end.column++,i}}),this.add(\"autoclosing\",\"insertion\",function(e,t,n,r,i){if(i==\">\"){var o=n.getSelectionRange().start,a=new s(r,o.row,o.column),f=a.getCurrentToken()||a.stepBackward();if(!f||!(u(f,\"tag-name\")||u(f,\"tag-whitespace\")||u(f,\"attribute-name\")||u(f,\"attribute-equals\")||u(f,\"attribute-value\")))return;if(u(f,\"reference.attribute-value\"))return;if(u(f,\"attribute-value\")){var l=f.value.charAt(0);if(l=='\"'||l==\"'\"){var c=f.value.charAt(f.value.length-1),h=a.getCurrentTokenColumn()+f.value.length;if(h>o.column||h==o.column&&l!=c)return}}while(!u(f,\"tag-name\")){f=a.stepBackward();if(f.value==\"<\"){f=a.stepForward();break}}var p=a.getCurrentTokenRow(),d=a.getCurrentTokenColumn();if(u(a.stepBackward(),\"end-tag-open\"))return;var v=f.value;p==o.row&&(v=v.substring(0,o.column-d));if(this.voidElements.hasOwnProperty(v.toLowerCase()))return;return{text:\"></\"+v+\">\",selection:[1,1]}}}),this.add(\"autoindent\",\"insertion\",function(e,t,n,r,i){if(i==\"\\n\"){var o=n.getCursorPosition(),u=r.getLine(o.row),a=new s(r,o.row,o.column),f=a.getCurrentToken();if(f&&f.type.indexOf(\"tag-close\")!==-1){if(f.value==\"/>\")return;while(f&&f.type.indexOf(\"tag-name\")===-1)f=a.stepBackward();if(!f)return;var l=f.value,c=a.getCurrentTokenRow();f=a.stepBackward();if(!f||f.type.indexOf(\"end-tag\")!==-1)return;if(this.voidElements&&!this.voidElements[l]){var h=r.getTokenAt(o.row,o.column+1),u=r.getLine(c),p=this.$getIndent(u),d=p+r.getTabString();return h&&h.value===\"</\"?{text:\"\\n\"+d+\"\\n\"+p,selection:[1,d.length,1,d.length]}:{text:\"\\n\"+d}}}}})};r.inherits(a,i),t.XmlBehaviour=a}),define(\"ace/mode/folding/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/range\",\"ace/mode/folding/fold_mode\",\"ace/token_iterator\"],function(e,t,n){\"use strict\";function l(e,t){return e.type.lastIndexOf(t+\".xml\")>-1}var r=e(\"../../lib/oop\"),i=e(\"../../lib/lang\"),s=e(\"../../range\").Range,o=e(\"./fold_mode\").FoldMode,u=e(\"../../token_iterator\").TokenIterator,a=t.FoldMode=function(e,t){o.call(this),this.voidElements=e||{},this.optionalEndTags=r.mixin({},this.voidElements),t&&r.mixin(this.optionalEndTags,t)};r.inherits(a,o);var f=function(){this.tagName=\"\",this.closing=!1,this.selfClosing=!1,this.start={row:0,column:0},this.end={row:0,column:0}};(function(){this.getFoldWidget=function(e,t,n){var r=this._getFirstTagInLine(e,n);return r?r.closing||!r.tagName&&r.selfClosing?t==\"markbeginend\"?\"end\":\"\":!r.tagName||r.selfClosing||this.voidElements.hasOwnProperty(r.tagName.toLowerCase())?\"\":this._findEndTagInLine(e,n,r.tagName,r.end.column)?\"\":\"start\":\"\"},this._getFirstTagInLine=function(e,t){var n=e.getTokens(t),r=new f;for(var i=0;i<n.length;i++){var s=n[i];if(l(s,\"tag-open\")){r.end.column=r.start.column+s.value.length,r.closing=l(s,\"end-tag-open\"),s=n[++i];if(!s)return null;r.tagName=s.value,r.end.column+=s.value.length;for(i++;i<n.length;i++){s=n[i],r.end.column+=s.value.length;if(l(s,\"tag-close\")){r.selfClosing=s.value==\"/>\";break}}return r}if(l(s,\"tag-close\"))return r.selfClosing=s.value==\"/>\",r;r.start.column+=s.value.length}return null},this._findEndTagInLine=function(e,t,n,r){var i=e.getTokens(t),s=0;for(var o=0;o<i.length;o++){var u=i[o];s+=u.value.length;if(s<r)continue;if(l(u,\"end-tag-open\")){u=i[o+1];if(u&&u.value==n)return!0}}return!1},this._readTagForward=function(e){var t=e.getCurrentToken();if(!t)return null;var n=new f;do if(l(t,\"tag-open\"))n.closing=l(t,\"end-tag-open\"),n.start.row=e.getCurrentTokenRow(),n.start.column=e.getCurrentTokenColumn();else if(l(t,\"tag-name\"))n.tagName=t.value;else if(l(t,\"tag-close\"))return n.selfClosing=t.value==\"/>\",n.end.row=e.getCurrentTokenRow(),n.end.column=e.getCurrentTokenColumn()+t.value.length,e.stepForward(),n;while(t=e.stepForward());return null},this._readTagBackward=function(e){var t=e.getCurrentToken();if(!t)return null;var n=new f;do{if(l(t,\"tag-open\"))return n.closing=l(t,\"end-tag-open\"),n.start.row=e.getCurrentTokenRow(),n.start.column=e.getCurrentTokenColumn(),e.stepBackward(),n;l(t,\"tag-name\")?n.tagName=t.value:l(t,\"tag-close\")&&(n.selfClosing=t.value==\"/>\",n.end.row=e.getCurrentTokenRow(),n.end.column=e.getCurrentTokenColumn()+t.value.length)}while(t=e.stepBackward());return null},this._pop=function(e,t){while(e.length){var n=e[e.length-1];if(!t||n.tagName==t.tagName)return e.pop();if(this.optionalEndTags.hasOwnProperty(n.tagName)){e.pop();continue}return null}},this.getFoldWidgetRange=function(e,t,n){var r=this._getFirstTagInLine(e,n);if(!r)return null;var i=r.closing||r.selfClosing,o=[],a;if(!i){var f=new u(e,n,r.start.column),l={row:n,column:r.start.column+r.tagName.length+2};r.start.row==r.end.row&&(l.column=r.end.column);while(a=this._readTagForward(f)){if(a.selfClosing){if(!o.length)return a.start.column+=a.tagName.length+2,a.end.column-=2,s.fromPoints(a.start,a.end);continue}if(a.closing){this._pop(o,a);if(o.length==0)return s.fromPoints(l,a.start)}else o.push(a)}}else{var f=new u(e,n,r.end.column),c={row:n,column:r.start.column};while(a=this._readTagBackward(f)){if(a.selfClosing){if(!o.length)return a.start.column+=a.tagName.length+2,a.end.column-=2,s.fromPoints(a.start,a.end);continue}if(!a.closing){this._pop(o,a);if(o.length==0)return a.start.column+=a.tagName.length+2,a.start.row==a.end.row&&a.start.column<a.end.column&&(a.start.column=a.end.column),s.fromPoints(a.start,c)}else o.push(a)}}}}).call(a.prototype)}),define(\"ace/mode/xml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/mode/text\",\"ace/mode/xml_highlight_rules\",\"ace/mode/behaviour/xml\",\"ace/mode/folding/xml\",\"ace/worker/worker_client\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"./text\").Mode,o=e(\"./xml_highlight_rules\").XmlHighlightRules,u=e(\"./behaviour/xml\").XmlBehaviour,a=e(\"./folding/xml\").FoldMode,f=e(\"../worker/worker_client\").WorkerClient,l=function(){this.HighlightRules=o,this.$behaviour=new u,this.foldingRules=new a};r.inherits(l,s),function(){this.voidElements=i.arrayToMap([]),this.blockComment={start:\"<!--\",end:\"-->\"},this.createWorker=function(e){var t=new f([\"ace\"],\"ace/mode/xml_worker\",\"Worker\");return t.attachToDocument(e.getDocument()),t.on(\"error\",function(t){e.setAnnotations(t.data)}),t.on(\"terminate\",function(){e.clearAnnotations()}),t},this.$id=\"ace/mode/xml\"}.call(l.prototype),t.Mode=l})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/mode-yaml.js",
    "content": "define(\"ace/mode/yaml_highlight_rules\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text_highlight_rules\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text_highlight_rules\").TextHighlightRules,s=function(){this.$rules={start:[{token:\"comment\",regex:\"#.*$\"},{token:\"list.markup\",regex:/^(?:-{3}|\\.{3})\\s*(?=#|$)/},{token:\"list.markup\",regex:/^\\s*[\\-?](?:$|\\s)/},{token:\"constant\",regex:\"!![\\\\w//]+\"},{token:\"constant.language\",regex:\"[&\\\\*][a-zA-Z0-9-_]+\"},{token:[\"meta.tag\",\"keyword\"],regex:/^(\\s*\\w.*?)(:(?:\\s+|$))/},{token:[\"meta.tag\",\"keyword\"],regex:/(\\w+?)(\\s*:(?:\\s+|$))/},{token:\"keyword.operator\",regex:\"<<\\\\w*:\\\\w*\"},{token:\"keyword.operator\",regex:\"-\\\\s*(?=[{])\"},{token:\"string\",regex:'[\"](?:(?:\\\\\\\\.)|(?:[^\"\\\\\\\\]))*?[\"]'},{token:\"string\",regex:\"[|>][-+\\\\d\\\\s]*$\",next:\"qqstring\"},{token:\"string\",regex:\"['](?:(?:\\\\\\\\.)|(?:[^'\\\\\\\\]))*?[']\"},{token:\"constant.numeric\",regex:/(\\b|[+\\-\\.])[\\d_]+(?:(?:\\.[\\d_]*)?(?:[eE][+\\-]?[\\d_]+)?)/},{token:\"constant.numeric\",regex:/[+\\-]?\\.inf\\b|NaN\\b|0x[\\dA-Fa-f_]+|0b[10_]+/},{token:\"constant.language.boolean\",regex:\"\\\\b(?:true|false|TRUE|FALSE|True|False|yes|no)\\\\b\"},{token:\"paren.lparen\",regex:\"[[({]\"},{token:\"paren.rparen\",regex:\"[\\\\])}]\"}],qqstring:[{token:\"string\",regex:\"(?=(?:(?:\\\\\\\\.)|(?:[^:]))*?:)\",next:\"start\"},{token:\"string\",regex:\".+\"}]}};r.inherits(s,i),t.YamlHighlightRules=s}),define(\"ace/mode/matching_brace_outdent\",[\"require\",\"exports\",\"module\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=function(){};(function(){this.checkOutdent=function(e,t){return/^\\s+$/.test(e)?/^\\s*\\}/.test(t):!1},this.autoOutdent=function(e,t){var n=e.getLine(t),i=n.match(/^(\\s*\\})/);if(!i)return 0;var s=i[1].length,o=e.findMatchingBracket({row:t,column:s});if(!o||o.row==t)return 0;var u=this.$getIndent(e.getLine(o.row));e.replace(new r(t,0,t,s-1),u)},this.$getIndent=function(e){return e.match(/^\\s*/)[0]}}).call(i.prototype),t.MatchingBraceOutdent=i}),define(\"ace/mode/folding/coffee\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/folding/fold_mode\",\"ace/range\"],function(e,t,n){\"use strict\";var r=e(\"../../lib/oop\"),i=e(\"./fold_mode\").FoldMode,s=e(\"../../range\").Range,o=t.FoldMode=function(){};r.inherits(o,i),function(){this.getFoldWidgetRange=function(e,t,n){var r=this.indentationBlock(e,n);if(r)return r;var i=/\\S/,o=e.getLine(n),u=o.search(i);if(u==-1||o[u]!=\"#\")return;var a=o.length,f=e.getLength(),l=n,c=n;while(++n<f){o=e.getLine(n);var h=o.search(i);if(h==-1)continue;if(o[h]!=\"#\")break;c=n}if(c>l){var p=e.getLine(c).length;return new s(l,a,c,p)}},this.getFoldWidget=function(e,t,n){var r=e.getLine(n),i=r.search(/\\S/),s=e.getLine(n+1),o=e.getLine(n-1),u=o.search(/\\S/),a=s.search(/\\S/);if(i==-1)return e.foldWidgets[n-1]=u!=-1&&u<a?\"start\":\"\",\"\";if(u==-1){if(i==a&&r[i]==\"#\"&&s[i]==\"#\")return e.foldWidgets[n-1]=\"\",e.foldWidgets[n+1]=\"\",\"start\"}else if(u==i&&r[i]==\"#\"&&o[i]==\"#\"&&e.getLine(n-2).search(/\\S/)==-1)return e.foldWidgets[n-1]=\"start\",e.foldWidgets[n+1]=\"\",\"\";return u!=-1&&u<i?e.foldWidgets[n-1]=\"start\":e.foldWidgets[n-1]=\"\",i<a?\"start\":\"\"}}.call(o.prototype)}),define(\"ace/mode/yaml\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/mode/text\",\"ace/mode/yaml_highlight_rules\",\"ace/mode/matching_brace_outdent\",\"ace/mode/folding/coffee\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"./text\").Mode,s=e(\"./yaml_highlight_rules\").YamlHighlightRules,o=e(\"./matching_brace_outdent\").MatchingBraceOutdent,u=e(\"./folding/coffee\").FoldMode,a=function(){this.HighlightRules=s,this.$outdent=new o,this.foldingRules=new u,this.$behaviour=this.$defaultBehaviour};r.inherits(a,i),function(){this.lineCommentStart=\"#\",this.getNextLineIndent=function(e,t,n){var r=this.$getIndent(t);if(e==\"start\"){var i=t.match(/^.*[\\{\\(\\[]\\s*$/);i&&(r+=n)}return r},this.checkOutdent=function(e,t,n){return this.$outdent.checkOutdent(t,n)},this.autoOutdent=function(e,t,n){this.$outdent.autoOutdent(t,n)},this.$id=\"ace/mode/yaml\"}.call(a.prototype),t.Mode=a})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/theme-chrome.js",
    "content": "define(\"ace/theme/chrome\",[\"require\",\"exports\",\"module\",\"ace/lib/dom\"],function(e,t,n){t.isDark=!1,t.cssClass=\"ace-chrome\",t.cssText='.ace-chrome .ace_gutter {background: #ebebeb;color: #333;overflow : hidden;}.ace-chrome .ace_print-margin {width: 1px;background: #e8e8e8;}.ace-chrome {background-color: #FFFFFF;color: black;}.ace-chrome .ace_cursor {color: black;}.ace-chrome .ace_invisible {color: rgb(191, 191, 191);}.ace-chrome .ace_constant.ace_buildin {color: rgb(88, 72, 246);}.ace-chrome .ace_constant.ace_language {color: rgb(88, 92, 246);}.ace-chrome .ace_constant.ace_library {color: rgb(6, 150, 14);}.ace-chrome .ace_invalid {background-color: rgb(153, 0, 0);color: white;}.ace-chrome .ace_fold {}.ace-chrome .ace_support.ace_function {color: rgb(60, 76, 114);}.ace-chrome .ace_support.ace_constant {color: rgb(6, 150, 14);}.ace-chrome .ace_support.ace_type,.ace-chrome .ace_support.ace_class.ace-chrome .ace_support.ace_other {color: rgb(109, 121, 222);}.ace-chrome .ace_variable.ace_parameter {font-style:italic;color:#FD971F;}.ace-chrome .ace_keyword.ace_operator {color: rgb(104, 118, 135);}.ace-chrome .ace_comment {color: #236e24;}.ace-chrome .ace_comment.ace_doc {color: #236e24;}.ace-chrome .ace_comment.ace_doc.ace_tag {color: #236e24;}.ace-chrome .ace_constant.ace_numeric {color: rgb(0, 0, 205);}.ace-chrome .ace_variable {color: rgb(49, 132, 149);}.ace-chrome .ace_xml-pe {color: rgb(104, 104, 91);}.ace-chrome .ace_entity.ace_name.ace_function {color: #0000A2;}.ace-chrome .ace_heading {color: rgb(12, 7, 255);}.ace-chrome .ace_list {color:rgb(185, 6, 144);}.ace-chrome .ace_marker-layer .ace_selection {background: rgb(181, 213, 255);}.ace-chrome .ace_marker-layer .ace_step {background: rgb(252, 255, 0);}.ace-chrome .ace_marker-layer .ace_stack {background: rgb(164, 229, 101);}.ace-chrome .ace_marker-layer .ace_bracket {margin: -1px 0 0 -1px;border: 1px solid rgb(192, 192, 192);}.ace-chrome .ace_marker-layer .ace_active-line {background: rgba(0, 0, 0, 0.07);}.ace-chrome .ace_gutter-active-line {background-color : #dcdcdc;}.ace-chrome .ace_marker-layer .ace_selected-word {background: rgb(250, 250, 255);border: 1px solid rgb(200, 200, 250);}.ace-chrome .ace_storage,.ace-chrome .ace_keyword,.ace-chrome .ace_meta.ace_tag {color: rgb(147, 15, 128);}.ace-chrome .ace_string.ace_regex {color: rgb(255, 0, 0)}.ace-chrome .ace_string {color: #1A1AA6;}.ace-chrome .ace_entity.ace_other.ace_attribute-name {color: #994409;}.ace-chrome .ace_indent-guide {background: url(\"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAACCAYAAACZgbYnAAAAE0lEQVQImWP4////f4bLly//BwAmVgd1/w11/gAAAABJRU5ErkJggg==\") right repeat-y;}';var r=e(\"../lib/dom\");r.importCssString(t.cssText,t.cssClass)})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/worker-css.js",
    "content": "\"no use strict\";(function(e){function t(e,t){var n=e,r=\"\";while(n){var i=t[n];if(typeof i==\"string\")return i+r;if(i)return i.location.replace(/\\/*$/,\"/\")+(r||i.main||i.name);if(i===!1)return\"\";var s=n.lastIndexOf(\"/\");if(s===-1)break;r=n.substr(s)+r,n=n.slice(0,s)}return e}if(typeof e.window!=\"undefined\"&&e.document)return;if(e.require&&e.define)return;e.console||(e.console=function(){var e=Array.prototype.slice.call(arguments,0);postMessage({type:\"log\",data:e})},e.console.error=e.console.warn=e.console.log=e.console.trace=e.console),e.window=e,e.ace=e,e.onerror=function(e,t,n,r,i){postMessage({type:\"error\",data:{message:e,data:i.data,file:t,line:n,col:r,stack:i.stack}})},e.normalizeModule=function(t,n){if(n.indexOf(\"!\")!==-1){var r=n.split(\"!\");return e.normalizeModule(t,r[0])+\"!\"+e.normalizeModule(t,r[1])}if(n.charAt(0)==\".\"){var i=t.split(\"/\").slice(0,-1).join(\"/\");n=(i?i+\"/\":\"\")+n;while(n.indexOf(\".\")!==-1&&s!=n){var s=n;n=n.replace(/^\\.\\//,\"\").replace(/\\/\\.\\//,\"/\").replace(/[^\\/]+\\/\\.\\.\\//,\"\")}}return n},e.require=function(r,i){i||(i=r,r=null);if(!i.charAt)throw new Error(\"worker.js require() accepts only (parentId, id) as arguments\");i=e.normalizeModule(r,i);var s=e.require.modules[i];if(s)return s.initialized||(s.initialized=!0,s.exports=s.factory().exports),s.exports;if(!e.require.tlns)return console.log(\"unable to load \"+i);var o=t(i,e.require.tlns);return o.slice(-3)!=\".js\"&&(o+=\".js\"),e.require.id=i,e.require.modules[i]={},importScripts(o),e.require(r,i)},e.require.modules={},e.require.tlns={},e.define=function(t,n,r){arguments.length==2?(r=n,typeof t!=\"string\"&&(n=t,t=e.require.id)):arguments.length==1&&(r=t,n=[],t=e.require.id);if(typeof r!=\"function\"){e.require.modules[t]={exports:r,initialized:!0};return}n.length||(n=[\"require\",\"exports\",\"module\"]);var i=function(n){return e.require(t,n)};e.require.modules[t]={exports:{},factory:function(){var e=this,t=r.apply(this,n.map(function(t){switch(t){case\"require\":return i;case\"exports\":return e.exports;case\"module\":return e;default:return i(t)}}));return t&&(e.exports=t),e}}},e.define.amd={},require.tlns={},e.initBaseUrls=function(t){for(var n in t)require.tlns[n]=t[n]},e.initSender=function(){var n=e.require(\"ace/lib/event_emitter\").EventEmitter,r=e.require(\"ace/lib/oop\"),i=function(){};return function(){r.implement(this,n),this.callback=function(e,t){postMessage({type:\"call\",id:t,data:e})},this.emit=function(e,t){postMessage({type:\"event\",name:e,data:t})}}.call(i.prototype),new i};var n=e.main=null,r=e.sender=null;e.onmessage=function(t){var i=t.data;if(i.event&&r)r._signal(i.event,i.data);else if(i.command)if(n[i.command])n[i.command].apply(n,i.args);else{if(!e[i.command])throw new Error(\"Unknown command:\"+i.command);e[i.command].apply(e,i.args)}else if(i.init){e.initBaseUrls(i.tlns),require(\"ace/lib/es5-shim\"),r=e.sender=e.initSender();var s=require(i.module)[i.classname];n=e.main=new s(r)}}})(this),define(\"ace/lib/oop\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.inherits=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})},t.mixin=function(e,t){for(var n in t)e[n]=t[n];return e},t.implement=function(e,n){t.mixin(e,n)}}),define(\"ace/lib/lang\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.last=function(e){return e[e.length-1]},t.stringReverse=function(e){return e.split(\"\").reverse().join(\"\")},t.stringRepeat=function(e,t){var n=\"\";while(t>0){t&1&&(n+=e);if(t>>=1)e+=e}return n};var r=/^\\s\\s*/,i=/\\s\\s*$/;t.stringTrimLeft=function(e){return e.replace(r,\"\")},t.stringTrimRight=function(e){return e.replace(i,\"\")},t.copyObject=function(e){var t={};for(var n in e)t[n]=e[n];return t},t.copyArray=function(e){var t=[];for(var n=0,r=e.length;n<r;n++)e[n]&&typeof e[n]==\"object\"?t[n]=this.copyObject(e[n]):t[n]=e[n];return t},t.deepCopy=function s(e){if(typeof e!=\"object\"||!e)return e;var t;if(Array.isArray(e)){t=[];for(var n=0;n<e.length;n++)t[n]=s(e[n]);return t}if(Object.prototype.toString.call(e)!==\"[object Object]\")return e;t={};for(var n in e)t[n]=s(e[n]);return t},t.arrayToMap=function(e){var t={};for(var n=0;n<e.length;n++)t[e[n]]=1;return t},t.createMap=function(e){var t=Object.create(null);for(var n in e)t[n]=e[n];return t},t.arrayRemove=function(e,t){for(var n=0;n<=e.length;n++)t===e[n]&&e.splice(n,1)},t.escapeRegExp=function(e){return e.replace(/([.*+?^${}()|[\\]\\/\\\\])/g,\"\\\\$1\")},t.escapeHTML=function(e){return e.replace(/&/g,\"&#38;\").replace(/\"/g,\"&#34;\").replace(/'/g,\"&#39;\").replace(/</g,\"&#60;\")},t.getMatchOffsets=function(e,t){var n=[];return e.replace(t,function(e){n.push({offset:arguments[arguments.length-2],length:e.length})}),n},t.deferredCall=function(e){var t=null,n=function(){t=null,e()},r=function(e){return r.cancel(),t=setTimeout(n,e||0),r};return r.schedule=r,r.call=function(){return this.cancel(),e(),r},r.cancel=function(){return clearTimeout(t),t=null,r},r.isPending=function(){return t},r},t.delayedCall=function(e,t){var n=null,r=function(){n=null,e()},i=function(e){n==null&&(n=setTimeout(r,e||t))};return i.delay=function(e){n&&clearTimeout(n),n=setTimeout(r,e||t)},i.schedule=i,i.call=function(){this.cancel(),e()},i.cancel=function(){n&&clearTimeout(n),n=null},i.isPending=function(){return n},i}}),define(\"ace/range\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(e,t){return e.row-t.row||e.column-t.column},i=function(e,t,n,r){this.start={row:e,column:t},this.end={row:n,column:r}};(function(){this.isEqual=function(e){return this.start.row===e.start.row&&this.end.row===e.end.row&&this.start.column===e.start.column&&this.end.column===e.end.column},this.toString=function(){return\"Range: [\"+this.start.row+\"/\"+this.start.column+\"] -> [\"+this.end.row+\"/\"+this.end.column+\"]\"},this.contains=function(e,t){return this.compare(e,t)==0},this.compareRange=function(e){var t,n=e.end,r=e.start;return t=this.compare(n.row,n.column),t==1?(t=this.compare(r.row,r.column),t==1?2:t==0?1:0):t==-1?-2:(t=this.compare(r.row,r.column),t==-1?-1:t==1?42:0)},this.comparePoint=function(e){return this.compare(e.row,e.column)},this.containsRange=function(e){return this.comparePoint(e.start)==0&&this.comparePoint(e.end)==0},this.intersects=function(e){var t=this.compareRange(e);return t==-1||t==0||t==1},this.isEnd=function(e,t){return this.end.row==e&&this.end.column==t},this.isStart=function(e,t){return this.start.row==e&&this.start.column==t},this.setStart=function(e,t){typeof e==\"object\"?(this.start.column=e.column,this.start.row=e.row):(this.start.row=e,this.start.column=t)},this.setEnd=function(e,t){typeof e==\"object\"?(this.end.column=e.column,this.end.row=e.row):(this.end.row=e,this.end.column=t)},this.inside=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)||this.isStart(e,t)?!1:!0:!1},this.insideStart=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)?!1:!0:!1},this.insideEnd=function(e,t){return this.compare(e,t)==0?this.isStart(e,t)?!1:!0:!1},this.compare=function(e,t){return!this.isMultiLine()&&e===this.start.row?t<this.start.column?-1:t>this.end.column?1:0:e<this.start.row?-1:e>this.end.row?1:this.start.row===e?t>=this.start.column?0:-1:this.end.row===e?t<=this.end.column?0:1:0},this.compareStart=function(e,t){return this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.compareEnd=function(e,t){return this.end.row==e&&this.end.column==t?1:this.compare(e,t)},this.compareInside=function(e,t){return this.end.row==e&&this.end.column==t?1:this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.clipRows=function(e,t){if(this.end.row>t)var n={row:t+1,column:0};else if(this.end.row<e)var n={row:e,column:0};if(this.start.row>t)var r={row:t+1,column:0};else if(this.start.row<e)var r={row:e,column:0};return i.fromPoints(r||this.start,n||this.end)},this.extend=function(e,t){var n=this.compare(e,t);if(n==0)return this;if(n==-1)var r={row:e,column:t};else var s={row:e,column:t};return i.fromPoints(r||this.start,s||this.end)},this.isEmpty=function(){return this.start.row===this.end.row&&this.start.column===this.end.column},this.isMultiLine=function(){return this.start.row!==this.end.row},this.clone=function(){return i.fromPoints(this.start,this.end)},this.collapseRows=function(){return this.end.column==0?new i(this.start.row,0,Math.max(this.start.row,this.end.row-1),0):new i(this.start.row,0,this.end.row,0)},this.toScreenRange=function(e){var t=e.documentToScreenPosition(this.start),n=e.documentToScreenPosition(this.end);return new i(t.row,t.column,n.row,n.column)},this.moveBy=function(e,t){this.start.row+=e,this.start.column+=t,this.end.row+=e,this.end.column+=t}}).call(i.prototype),i.fromPoints=function(e,t){return new i(e.row,e.column,t.row,t.column)},i.comparePoints=r,i.comparePoints=function(e,t){return e.row-t.row||e.column-t.column},t.Range=i}),define(\"ace/apply_delta\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function r(e,t){throw console.log(\"Invalid Delta:\",e),\"Invalid Delta: \"+t}function i(e,t){return t.row>=0&&t.row<e.length&&t.column>=0&&t.column<=e[t.row].length}function s(e,t){t.action!=\"insert\"&&t.action!=\"remove\"&&r(t,\"delta.action must be 'insert' or 'remove'\"),t.lines instanceof Array||r(t,\"delta.lines must be an Array\"),(!t.start||!t.end)&&r(t,\"delta.start/end must be an present\");var n=t.start;i(e,t.start)||r(t,\"delta.start must be contained in document\");var s=t.end;t.action==\"remove\"&&!i(e,s)&&r(t,\"delta.end must contained in document for 'remove' actions\");var o=s.row-n.row,u=s.column-(o==0?n.column:0);(o!=t.lines.length-1||t.lines[o].length!=u)&&r(t,\"delta.range must match delta lines\")}t.applyDelta=function(e,t,n){var r=t.start.row,i=t.start.column,s=e[r]||\"\";switch(t.action){case\"insert\":var o=t.lines;if(o.length===1)e[r]=s.substring(0,i)+t.lines[0]+s.substring(i);else{var u=[r,1].concat(t.lines);e.splice.apply(e,u),e[r]=s.substring(0,i)+e[r],e[r+t.lines.length-1]+=s.substring(i)}break;case\"remove\":var a=t.end.column,f=t.end.row;r===f?e[r]=s.substring(0,i)+s.substring(a):e.splice(r,f-r+1,s.substring(0,i)+e[f].substring(a))}}}),define(\"ace/lib/event_emitter\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={},i=function(){this.propagationStopped=!0},s=function(){this.defaultPrevented=!0};r._emit=r._dispatchEvent=function(e,t){this._eventRegistry||(this._eventRegistry={}),this._defaultHandlers||(this._defaultHandlers={});var n=this._eventRegistry[e]||[],r=this._defaultHandlers[e];if(!n.length&&!r)return;if(typeof t!=\"object\"||!t)t={};t.type||(t.type=e),t.stopPropagation||(t.stopPropagation=i),t.preventDefault||(t.preventDefault=s),n=n.slice();for(var o=0;o<n.length;o++){n[o](t,this);if(t.propagationStopped)break}if(r&&!t.defaultPrevented)return r(t,this)},r._signal=function(e,t){var n=(this._eventRegistry||{})[e];if(!n)return;n=n.slice();for(var r=0;r<n.length;r++)n[r](t,this)},r.once=function(e,t){var n=this;t&&this.addEventListener(e,function r(){n.removeEventListener(e,r),t.apply(null,arguments)})},r.setDefaultHandler=function(e,t){var n=this._defaultHandlers;n||(n=this._defaultHandlers={_disabled_:{}});if(n[e]){var r=n[e],i=n._disabled_[e];i||(n._disabled_[e]=i=[]),i.push(r);var s=i.indexOf(t);s!=-1&&i.splice(s,1)}n[e]=t},r.removeDefaultHandler=function(e,t){var n=this._defaultHandlers;if(!n)return;var r=n._disabled_[e];if(n[e]==t){var i=n[e];r&&this.setDefaultHandler(e,r.pop())}else if(r){var s=r.indexOf(t);s!=-1&&r.splice(s,1)}},r.on=r.addEventListener=function(e,t,n){this._eventRegistry=this._eventRegistry||{};var r=this._eventRegistry[e];return r||(r=this._eventRegistry[e]=[]),r.indexOf(t)==-1&&r[n?\"unshift\":\"push\"](t),t},r.off=r.removeListener=r.removeEventListener=function(e,t){this._eventRegistry=this._eventRegistry||{};var n=this._eventRegistry[e];if(!n)return;var r=n.indexOf(t);r!==-1&&n.splice(r,1)},r.removeAllListeners=function(e){this._eventRegistry&&(this._eventRegistry[e]=[])},t.EventEmitter=r}),define(\"ace/anchor\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/event_emitter\").EventEmitter,s=t.Anchor=function(e,t,n){this.$onChange=this.onChange.bind(this),this.attach(e),typeof n==\"undefined\"?this.setPosition(t.row,t.column):this.setPosition(t,n)};(function(){function e(e,t,n){var r=n?e.column<=t.column:e.column<t.column;return e.row<t.row||e.row==t.row&&r}function t(t,n,r){var i=t.action==\"insert\",s=(i?1:-1)*(t.end.row-t.start.row),o=(i?1:-1)*(t.end.column-t.start.column),u=t.start,a=i?u:t.end;return e(n,u,r)?{row:n.row,column:n.column}:e(a,n,!r)?{row:n.row+s,column:n.column+(n.row==a.row?o:0)}:{row:u.row,column:u.column}}r.implement(this,i),this.getPosition=function(){return this.$clipPositionToDocument(this.row,this.column)},this.getDocument=function(){return this.document},this.$insertRight=!1,this.onChange=function(e){if(e.start.row==e.end.row&&e.start.row!=this.row)return;if(e.start.row>this.row)return;var n=t(e,{row:this.row,column:this.column},this.$insertRight);this.setPosition(n.row,n.column,!0)},this.setPosition=function(e,t,n){var r;n?r={row:e,column:t}:r=this.$clipPositionToDocument(e,t);if(this.row==r.row&&this.column==r.column)return;var i={row:this.row,column:this.column};this.row=r.row,this.column=r.column,this._signal(\"change\",{old:i,value:r})},this.detach=function(){this.document.removeEventListener(\"change\",this.$onChange)},this.attach=function(e){this.document=e||this.document,this.document.on(\"change\",this.$onChange)},this.$clipPositionToDocument=function(e,t){var n={};return e>=this.document.getLength()?(n.row=Math.max(0,this.document.getLength()-1),n.column=this.document.getLine(n.row).length):e<0?(n.row=0,n.column=0):(n.row=e,n.column=Math.min(this.document.getLine(n.row).length,Math.max(0,t))),t<0&&(n.column=0),n}}).call(s.prototype)}),define(\"ace/document\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/apply_delta\",\"ace/lib/event_emitter\",\"ace/range\",\"ace/anchor\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./apply_delta\").applyDelta,s=e(\"./lib/event_emitter\").EventEmitter,o=e(\"./range\").Range,u=e(\"./anchor\").Anchor,a=function(e){this.$lines=[\"\"],e.length===0?this.$lines=[\"\"]:Array.isArray(e)?this.insertMergedLines({row:0,column:0},e):this.insert({row:0,column:0},e)};(function(){r.implement(this,s),this.setValue=function(e){var t=this.getLength()-1;this.remove(new o(0,0,t,this.getLine(t).length)),this.insert({row:0,column:0},e)},this.getValue=function(){return this.getAllLines().join(this.getNewLineCharacter())},this.createAnchor=function(e,t){return new u(this,e,t)},\"aaa\".split(/a/).length===0?this.$split=function(e){return e.replace(/\\r\\n|\\r/g,\"\\n\").split(\"\\n\")}:this.$split=function(e){return e.split(/\\r\\n|\\r|\\n/)},this.$detectNewLine=function(e){var t=e.match(/^.*?(\\r\\n|\\r|\\n)/m);this.$autoNewLine=t?t[1]:\"\\n\",this._signal(\"changeNewLineMode\")},this.getNewLineCharacter=function(){switch(this.$newLineMode){case\"windows\":return\"\\r\\n\";case\"unix\":return\"\\n\";default:return this.$autoNewLine||\"\\n\"}},this.$autoNewLine=\"\",this.$newLineMode=\"auto\",this.setNewLineMode=function(e){if(this.$newLineMode===e)return;this.$newLineMode=e,this._signal(\"changeNewLineMode\")},this.getNewLineMode=function(){return this.$newLineMode},this.isNewLine=function(e){return e==\"\\r\\n\"||e==\"\\r\"||e==\"\\n\"},this.getLine=function(e){return this.$lines[e]||\"\"},this.getLines=function(e,t){return this.$lines.slice(e,t+1)},this.getAllLines=function(){return this.getLines(0,this.getLength())},this.getLength=function(){return this.$lines.length},this.getTextRange=function(e){return this.getLinesForRange(e).join(this.getNewLineCharacter())},this.getLinesForRange=function(e){var t;if(e.start.row===e.end.row)t=[this.getLine(e.start.row).substring(e.start.column,e.end.column)];else{t=this.getLines(e.start.row,e.end.row),t[0]=(t[0]||\"\").substring(e.start.column);var n=t.length-1;e.end.row-e.start.row==n&&(t[n]=t[n].substring(0,e.end.column))}return t},this.insertLines=function(e,t){return console.warn(\"Use of document.insertLines is deprecated. Use the insertFullLines method instead.\"),this.insertFullLines(e,t)},this.removeLines=function(e,t){return console.warn(\"Use of document.removeLines is deprecated. Use the removeFullLines method instead.\"),this.removeFullLines(e,t)},this.insertNewLine=function(e){return console.warn(\"Use of document.insertNewLine is deprecated. Use insertMergedLines(position, ['', '']) instead.\"),this.insertMergedLines(e,[\"\",\"\"])},this.insert=function(e,t){return this.getLength()<=1&&this.$detectNewLine(t),this.insertMergedLines(e,this.$split(t))},this.insertInLine=function(e,t){var n=this.clippedPos(e.row,e.column),r=this.pos(e.row,e.column+t.length);return this.applyDelta({start:n,end:r,action:\"insert\",lines:[t]},!0),this.clonePos(r)},this.clippedPos=function(e,t){var n=this.getLength();e===undefined?e=n:e<0?e=0:e>=n&&(e=n-1,t=undefined);var r=this.getLine(e);return t==undefined&&(t=r.length),t=Math.min(Math.max(t,0),r.length),{row:e,column:t}},this.clonePos=function(e){return{row:e.row,column:e.column}},this.pos=function(e,t){return{row:e,column:t}},this.$clipPosition=function(e){var t=this.getLength();return e.row>=t?(e.row=Math.max(0,t-1),e.column=this.getLine(t-1).length):(e.row=Math.max(0,e.row),e.column=Math.min(Math.max(e.column,0),this.getLine(e.row).length)),e},this.insertFullLines=function(e,t){e=Math.min(Math.max(e,0),this.getLength());var n=0;e<this.getLength()?(t=t.concat([\"\"]),n=0):(t=[\"\"].concat(t),e--,n=this.$lines[e].length),this.insertMergedLines({row:e,column:n},t)},this.insertMergedLines=function(e,t){var n=this.clippedPos(e.row,e.column),r={row:n.row+t.length-1,column:(t.length==1?n.column:0)+t[t.length-1].length};return this.applyDelta({start:n,end:r,action:\"insert\",lines:t}),this.clonePos(r)},this.remove=function(e){var t=this.clippedPos(e.start.row,e.start.column),n=this.clippedPos(e.end.row,e.end.column);return this.applyDelta({start:t,end:n,action:\"remove\",lines:this.getLinesForRange({start:t,end:n})}),this.clonePos(t)},this.removeInLine=function(e,t,n){var r=this.clippedPos(e,t),i=this.clippedPos(e,n);return this.applyDelta({start:r,end:i,action:\"remove\",lines:this.getLinesForRange({start:r,end:i})},!0),this.clonePos(r)},this.removeFullLines=function(e,t){e=Math.min(Math.max(0,e),this.getLength()-1),t=Math.min(Math.max(0,t),this.getLength()-1);var n=t==this.getLength()-1&&e>0,r=t<this.getLength()-1,i=n?e-1:e,s=n?this.getLine(i).length:0,u=r?t+1:t,a=r?0:this.getLine(u).length,f=new o(i,s,u,a),l=this.$lines.slice(e,t+1);return this.applyDelta({start:f.start,end:f.end,action:\"remove\",lines:this.getLinesForRange(f)}),l},this.removeNewLine=function(e){e<this.getLength()-1&&e>=0&&this.applyDelta({start:this.pos(e,this.getLine(e).length),end:this.pos(e+1,0),action:\"remove\",lines:[\"\",\"\"]})},this.replace=function(e,t){e instanceof o||(e=o.fromPoints(e.start,e.end));if(t.length===0&&e.isEmpty())return e.start;if(t==this.getTextRange(e))return e.end;this.remove(e);var n;return t?n=this.insert(e.start,t):n=e.start,n},this.applyDeltas=function(e){for(var t=0;t<e.length;t++)this.applyDelta(e[t])},this.revertDeltas=function(e){for(var t=e.length-1;t>=0;t--)this.revertDelta(e[t])},this.applyDelta=function(e,t){var n=e.action==\"insert\";if(n?e.lines.length<=1&&!e.lines[0]:!o.comparePoints(e.start,e.end))return;n&&e.lines.length>2e4&&this.$splitAndapplyLargeDelta(e,2e4),i(this.$lines,e,t),this._signal(\"change\",e)},this.$splitAndapplyLargeDelta=function(e,t){var n=e.lines,r=n.length,i=e.start.row,s=e.start.column,o=0,u=0;do{o=u,u+=t-1;var a=n.slice(o,u);if(u>r){e.lines=a,e.start.row=i+o,e.start.column=s;break}a.push(\"\"),this.applyDelta({start:this.pos(i+o,s),end:this.pos(i+u,s=0),action:e.action,lines:a},!0)}while(!0)},this.revertDelta=function(e){this.applyDelta({start:this.clonePos(e.start),end:this.clonePos(e.end),action:e.action==\"insert\"?\"remove\":\"insert\",lines:e.lines.slice()})},this.indexToPosition=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length;for(var i=t||0,s=n.length;i<s;i++){e-=n[i].length+r;if(e<0)return{row:i,column:e+n[i].length+r}}return{row:s-1,column:n[s-1].length}},this.positionToIndex=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length,i=0,s=Math.min(e.row,n.length);for(var o=t||0;o<s;++o)i+=n[o].length+r;return i+e.column}}).call(a.prototype),t.Document=a}),define(\"ace/worker/mirror\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/document\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=e(\"../document\").Document,s=e(\"../lib/lang\"),o=t.Mirror=function(e){this.sender=e;var t=this.doc=new i(\"\"),n=this.deferredUpdate=s.delayedCall(this.onUpdate.bind(this)),r=this;e.on(\"change\",function(e){var i=e.data;if(i[0].start)t.applyDeltas(i);else for(var s=0;s<i.length;s+=2){if(Array.isArray(i[s+1]))var o={action:\"insert\",start:i[s],lines:i[s+1]};else var o={action:\"remove\",start:i[s],end:i[s+1]};t.applyDelta(o,!0)}if(r.$timeout)return n.schedule(r.$timeout);r.onUpdate()})};(function(){this.$timeout=500,this.setTimeout=function(e){this.$timeout=e},this.setValue=function(e){this.doc.setValue(e),this.deferredUpdate.schedule(this.$timeout)},this.getValue=function(e){this.sender.callback(this.doc.getValue(),e)},this.onUpdate=function(){},this.isPending=function(){return this.deferredUpdate.isPending()}}).call(o.prototype)}),define(\"ace/mode/css/csslint\",[\"require\",\"exports\",\"module\"],function(require,exports,module){function objectToString(e){return Object.prototype.toString.call(e)}function clone(e,t,n,r){function u(e,n){if(e===null)return null;if(n==0)return e;var a;if(typeof e!=\"object\")return e;if(util.isArray(e))a=[];else if(util.isRegExp(e))a=new RegExp(e.source,util.getRegExpFlags(e)),e.lastIndex&&(a.lastIndex=e.lastIndex);else if(util.isDate(e))a=new Date(e.getTime());else{if(o&&Buffer.isBuffer(e))return a=new Buffer(e.length),e.copy(a),a;typeof r==\"undefined\"?a=Object.create(Object.getPrototypeOf(e)):a=Object.create(r)}if(t){var f=i.indexOf(e);if(f!=-1)return s[f];i.push(e),s.push(a)}for(var l in e)a[l]=u(e[l],n-1);return a}var i=[],s=[],o=typeof Buffer!=\"undefined\";return typeof t==\"undefined\"&&(t=!0),typeof n==\"undefined\"&&(n=Infinity),u(e,n)}function Reporter(e,t){this.messages=[],this.stats=[],this.lines=e,this.ruleset=t}var parserlib={};(function(){function e(){this._listeners={}}function t(e){this._input=e.replace(/\\n\\r?/g,\"\\n\"),this._line=1,this._col=1,this._cursor=0}function n(e,t,n){this.col=n,this.line=t,this.message=e}function r(e,t,n,r){this.col=n,this.line=t,this.text=e,this.type=r}function i(e,n){this._reader=e?new t(e.toString()):null,this._token=null,this._tokenData=n,this._lt=[],this._ltIndex=0,this._ltIndexCache=[]}e.prototype={constructor:e,addListener:function(e,t){this._listeners[e]||(this._listeners[e]=[]),this._listeners[e].push(t)},fire:function(e){typeof e==\"string\"&&(e={type:e}),typeof e.target!=\"undefined\"&&(e.target=this);if(typeof e.type==\"undefined\")throw new Error(\"Event object missing 'type' property.\");if(this._listeners[e.type]){var t=this._listeners[e.type].concat();for(var n=0,r=t.length;n<r;n++)t[n].call(this,e)}},removeListener:function(e,t){if(this._listeners[e]){var n=this._listeners[e];for(var r=0,i=n.length;r<i;r++)if(n[r]===t){n.splice(r,1);break}}}},t.prototype={constructor:t,getCol:function(){return this._col},getLine:function(){return this._line},eof:function(){return this._cursor==this._input.length},peek:function(e){var t=null;return e=typeof e==\"undefined\"?1:e,this._cursor<this._input.length&&(t=this._input.charAt(this._cursor+e-1)),t},read:function(){var e=null;return this._cursor<this._input.length&&(this._input.charAt(this._cursor)==\"\\n\"?(this._line++,this._col=1):this._col++,e=this._input.charAt(this._cursor++)),e},mark:function(){this._bookmark={cursor:this._cursor,line:this._line,col:this._col}},reset:function(){this._bookmark&&(this._cursor=this._bookmark.cursor,this._line=this._bookmark.line,this._col=this._bookmark.col,delete this._bookmark)},readTo:function(e){var t=\"\",n;while(t.length<e.length||t.lastIndexOf(e)!=t.length-e.length){n=this.read();if(!n)throw new Error('Expected \"'+e+'\" at line '+this._line+\", col \"+this._col+\".\");t+=n}return t},readWhile:function(e){var t=\"\",n=this.read();while(n!==null&&e(n))t+=n,n=this.read();return t},readMatch:function(e){var t=this._input.substring(this._cursor),n=null;return typeof e==\"string\"?t.indexOf(e)===0&&(n=this.readCount(e.length)):e instanceof RegExp&&e.test(t)&&(n=this.readCount(RegExp.lastMatch.length)),n},readCount:function(e){var t=\"\";while(e--)t+=this.read();return t}},n.prototype=new Error,r.fromToken=function(e){return new r(e.value,e.startLine,e.startCol)},r.prototype={constructor:r,valueOf:function(){return this.text},toString:function(){return this.text}},i.createTokenData=function(e){var t=[],n={},r=e.concat([]),i=0,s=r.length+1;r.UNKNOWN=-1,r.unshift({name:\"EOF\"});for(;i<s;i++)t.push(r[i].name),r[r[i].name]=i,r[i].text&&(n[r[i].text]=i);return r.name=function(e){return t[e]},r.type=function(e){return n[e]},r},i.prototype={constructor:i,match:function(e,t){e instanceof Array||(e=[e]);var n=this.get(t),r=0,i=e.length;while(r<i)if(n==e[r++])return!0;return this.unget(),!1},mustMatch:function(e,t){var r;e instanceof Array||(e=[e]);if(!this.match.apply(this,arguments))throw r=this.LT(1),new n(\"Expected \"+this._tokenData[e[0]].name+\" at line \"+r.startLine+\", col \"+r.startCol+\".\",r.startLine,r.startCol)},advance:function(e,t){while(this.LA(0)!==0&&!this.match(e,t))this.get();return this.LA(0)},get:function(e){var t=this._tokenData,n=this._reader,r,i=0,s=t.length,o=!1,u,a;if(this._lt.length&&this._ltIndex>=0&&this._ltIndex<this._lt.length){i++,this._token=this._lt[this._ltIndex++],a=t[this._token.type];while(a.channel!==undefined&&e!==a.channel&&this._ltIndex<this._lt.length)this._token=this._lt[this._ltIndex++],a=t[this._token.type],i++;if((a.channel===undefined||e===a.channel)&&this._ltIndex<=this._lt.length)return this._ltIndexCache.push(i),this._token.type}return u=this._getToken(),u.type>-1&&!t[u.type].hide&&(u.channel=t[u.type].channel,this._token=u,this._lt.push(u),this._ltIndexCache.push(this._lt.length-this._ltIndex+i),this._lt.length>5&&this._lt.shift(),this._ltIndexCache.length>5&&this._ltIndexCache.shift(),this._ltIndex=this._lt.length),a=t[u.type],a&&(a.hide||a.channel!==undefined&&e!==a.channel)?this.get(e):u.type},LA:function(e){var t=e,n;if(e>0){if(e>5)throw new Error(\"Too much lookahead.\");while(t)n=this.get(),t--;while(t<e)this.unget(),t++}else if(e<0){if(!this._lt[this._ltIndex+e])throw new Error(\"Too much lookbehind.\");n=this._lt[this._ltIndex+e].type}else n=this._token.type;return n},LT:function(e){return this.LA(e),this._lt[this._ltIndex+e-1]},peek:function(){return this.LA(1)},token:function(){return this._token},tokenName:function(e){return e<0||e>this._tokenData.length?\"UNKNOWN_TOKEN\":this._tokenData[e].name},tokenType:function(e){return this._tokenData[e]||-1},unget:function(){if(!this._ltIndexCache.length)throw new Error(\"Too much lookahead.\");this._ltIndex-=this._ltIndexCache.pop(),this._token=this._lt[this._ltIndex-1]}},parserlib.util={StringReader:t,SyntaxError:n,SyntaxUnit:r,EventTarget:e,TokenStreamBase:i}})(),function(){function Combinator(e,t,n){SyntaxUnit.call(this,e,t,n,Parser.COMBINATOR_TYPE),this.type=\"unknown\",/^\\s+$/.test(e)?this.type=\"descendant\":e==\">\"?this.type=\"child\":e==\"+\"?this.type=\"adjacent-sibling\":e==\"~\"&&(this.type=\"sibling\")}function MediaFeature(e,t){SyntaxUnit.call(this,\"(\"+e+(t!==null?\":\"+t:\"\")+\")\",e.startLine,e.startCol,Parser.MEDIA_FEATURE_TYPE),this.name=e,this.value=t}function MediaQuery(e,t,n,r,i){SyntaxUnit.call(this,(e?e+\" \":\"\")+(t?t:\"\")+(t&&n.length>0?\" and \":\"\")+n.join(\" and \"),r,i,Parser.MEDIA_QUERY_TYPE),this.modifier=e,this.mediaType=t,this.features=n}function Parser(e){EventTarget.call(this),this.options=e||{},this._tokenStream=null}function PropertyName(e,t,n,r){SyntaxUnit.call(this,e,n,r,Parser.PROPERTY_NAME_TYPE),this.hack=t}function PropertyValue(e,t,n){SyntaxUnit.call(this,e.join(\" \"),t,n,Parser.PROPERTY_VALUE_TYPE),this.parts=e}function PropertyValueIterator(e){this._i=0,this._parts=e.parts,this._marks=[],this.value=e}function PropertyValuePart(text,line,col){SyntaxUnit.call(this,text,line,col,Parser.PROPERTY_VALUE_PART_TYPE),this.type=\"unknown\";var temp;if(/^([+\\-]?[\\d\\.]+)([a-z]+)$/i.test(text)){this.type=\"dimension\",this.value=+RegExp.$1,this.units=RegExp.$2;switch(this.units.toLowerCase()){case\"em\":case\"rem\":case\"ex\":case\"px\":case\"cm\":case\"mm\":case\"in\":case\"pt\":case\"pc\":case\"ch\":case\"vh\":case\"vw\":case\"vmax\":case\"vmin\":this.type=\"length\";break;case\"deg\":case\"rad\":case\"grad\":this.type=\"angle\";break;case\"ms\":case\"s\":this.type=\"time\";break;case\"hz\":case\"khz\":this.type=\"frequency\";break;case\"dpi\":case\"dpcm\":this.type=\"resolution\"}}else/^([+\\-]?[\\d\\.]+)%$/i.test(text)?(this.type=\"percentage\",this.value=+RegExp.$1):/^([+\\-]?\\d+)$/i.test(text)?(this.type=\"integer\",this.value=+RegExp.$1):/^([+\\-]?[\\d\\.]+)$/i.test(text)?(this.type=\"number\",this.value=+RegExp.$1):/^#([a-f0-9]{3,6})/i.test(text)?(this.type=\"color\",temp=RegExp.$1,temp.length==3?(this.red=parseInt(temp.charAt(0)+temp.charAt(0),16),this.green=parseInt(temp.charAt(1)+temp.charAt(1),16),this.blue=parseInt(temp.charAt(2)+temp.charAt(2),16)):(this.red=parseInt(temp.substring(0,2),16),this.green=parseInt(temp.substring(2,4),16),this.blue=parseInt(temp.substring(4,6),16))):/^rgb\\(\\s*(\\d+)\\s*,\\s*(\\d+)\\s*,\\s*(\\d+)\\s*\\)/i.test(text)?(this.type=\"color\",this.red=+RegExp.$1,this.green=+RegExp.$2,this.blue=+RegExp.$3):/^rgb\\(\\s*(\\d+)%\\s*,\\s*(\\d+)%\\s*,\\s*(\\d+)%\\s*\\)/i.test(text)?(this.type=\"color\",this.red=+RegExp.$1*255/100,this.green=+RegExp.$2*255/100,this.blue=+RegExp.$3*255/100):/^rgba\\(\\s*(\\d+)\\s*,\\s*(\\d+)\\s*,\\s*(\\d+)\\s*,\\s*([\\d\\.]+)\\s*\\)/i.test(text)?(this.type=\"color\",this.red=+RegExp.$1,this.green=+RegExp.$2,this.blue=+RegExp.$3,this.alpha=+RegExp.$4):/^rgba\\(\\s*(\\d+)%\\s*,\\s*(\\d+)%\\s*,\\s*(\\d+)%\\s*,\\s*([\\d\\.]+)\\s*\\)/i.test(text)?(this.type=\"color\",this.red=+RegExp.$1*255/100,this.green=+RegExp.$2*255/100,this.blue=+RegExp.$3*255/100,this.alpha=+RegExp.$4):/^hsl\\(\\s*(\\d+)\\s*,\\s*(\\d+)%\\s*,\\s*(\\d+)%\\s*\\)/i.test(text)?(this.type=\"color\",this.hue=+RegExp.$1,this.saturation=+RegExp.$2/100,this.lightness=+RegExp.$3/100):/^hsla\\(\\s*(\\d+)\\s*,\\s*(\\d+)%\\s*,\\s*(\\d+)%\\s*,\\s*([\\d\\.]+)\\s*\\)/i.test(text)?(this.type=\"color\",this.hue=+RegExp.$1,this.saturation=+RegExp.$2/100,this.lightness=+RegExp.$3/100,this.alpha=+RegExp.$4):/^url\\([\"']?([^\\)\"']+)[\"']?\\)/i.test(text)?(this.type=\"uri\",this.uri=RegExp.$1):/^([^\\(]+)\\(/i.test(text)?(this.type=\"function\",this.name=RegExp.$1,this.value=text):/^[\"'][^\"']*[\"']/.test(text)?(this.type=\"string\",this.value=eval(text)):Colors[text.toLowerCase()]?(this.type=\"color\",temp=Colors[text.toLowerCase()].substring(1),this.red=parseInt(temp.substring(0,2),16),this.green=parseInt(temp.substring(2,4),16),this.blue=parseInt(temp.substring(4,6),16)):/^[\\,\\/]$/.test(text)?(this.type=\"operator\",this.value=text):/^[a-z\\-_\\u0080-\\uFFFF][a-z0-9\\-_\\u0080-\\uFFFF]*$/i.test(text)&&(this.type=\"identifier\",this.value=text)}function Selector(e,t,n){SyntaxUnit.call(this,e.join(\" \"),t,n,Parser.SELECTOR_TYPE),this.parts=e,this.specificity=Specificity.calculate(this)}function SelectorPart(e,t,n,r,i){SyntaxUnit.call(this,n,r,i,Parser.SELECTOR_PART_TYPE),this.elementName=e,this.modifiers=t}function SelectorSubPart(e,t,n,r){SyntaxUnit.call(this,e,n,r,Parser.SELECTOR_SUB_PART_TYPE),this.type=t,this.args=[]}function Specificity(e,t,n,r){this.a=e,this.b=t,this.c=n,this.d=r}function isHexDigit(e){return e!==null&&h.test(e)}function isDigit(e){return e!==null&&/\\d/.test(e)}function isWhitespace(e){return e!==null&&/\\s/.test(e)}function isNewLine(e){return e!==null&&nl.test(e)}function isNameStart(e){return e!==null&&/[a-z_\\u0080-\\uFFFF\\\\]/i.test(e)}function isNameChar(e){return e!==null&&(isNameStart(e)||/[0-9\\-\\\\]/.test(e))}function isIdentStart(e){return e!==null&&(isNameStart(e)||/\\-\\\\/.test(e))}function mix(e,t){for(var n in t)t.hasOwnProperty(n)&&(e[n]=t[n]);return e}function TokenStream(e){TokenStreamBase.call(this,e,Tokens)}function ValidationError(e,t,n){this.col=n,this.line=t,this.message=e}var EventTarget=parserlib.util.EventTarget,TokenStreamBase=parserlib.util.TokenStreamBase,StringReader=parserlib.util.StringReader,SyntaxError=parserlib.util.SyntaxError,SyntaxUnit=parserlib.util.SyntaxUnit,Colors={aliceblue:\"#f0f8ff\",antiquewhite:\"#faebd7\",aqua:\"#00ffff\",aquamarine:\"#7fffd4\",azure:\"#f0ffff\",beige:\"#f5f5dc\",bisque:\"#ffe4c4\",black:\"#000000\",blanchedalmond:\"#ffebcd\",blue:\"#0000ff\",blueviolet:\"#8a2be2\",brown:\"#a52a2a\",burlywood:\"#deb887\",cadetblue:\"#5f9ea0\",chartreuse:\"#7fff00\",chocolate:\"#d2691e\",coral:\"#ff7f50\",cornflowerblue:\"#6495ed\",cornsilk:\"#fff8dc\",crimson:\"#dc143c\",cyan:\"#00ffff\",darkblue:\"#00008b\",darkcyan:\"#008b8b\",darkgoldenrod:\"#b8860b\",darkgray:\"#a9a9a9\",darkgrey:\"#a9a9a9\",darkgreen:\"#006400\",darkkhaki:\"#bdb76b\",darkmagenta:\"#8b008b\",darkolivegreen:\"#556b2f\",darkorange:\"#ff8c00\",darkorchid:\"#9932cc\",darkred:\"#8b0000\",darksalmon:\"#e9967a\",darkseagreen:\"#8fbc8f\",darkslateblue:\"#483d8b\",darkslategray:\"#2f4f4f\",darkslategrey:\"#2f4f4f\",darkturquoise:\"#00ced1\",darkviolet:\"#9400d3\",deeppink:\"#ff1493\",deepskyblue:\"#00bfff\",dimgray:\"#696969\",dimgrey:\"#696969\",dodgerblue:\"#1e90ff\",firebrick:\"#b22222\",floralwhite:\"#fffaf0\",forestgreen:\"#228b22\",fuchsia:\"#ff00ff\",gainsboro:\"#dcdcdc\",ghostwhite:\"#f8f8ff\",gold:\"#ffd700\",goldenrod:\"#daa520\",gray:\"#808080\",grey:\"#808080\",green:\"#008000\",greenyellow:\"#adff2f\",honeydew:\"#f0fff0\",hotpink:\"#ff69b4\",indianred:\"#cd5c5c\",indigo:\"#4b0082\",ivory:\"#fffff0\",khaki:\"#f0e68c\",lavender:\"#e6e6fa\",lavenderblush:\"#fff0f5\",lawngreen:\"#7cfc00\",lemonchiffon:\"#fffacd\",lightblue:\"#add8e6\",lightcoral:\"#f08080\",lightcyan:\"#e0ffff\",lightgoldenrodyellow:\"#fafad2\",lightgray:\"#d3d3d3\",lightgrey:\"#d3d3d3\",lightgreen:\"#90ee90\",lightpink:\"#ffb6c1\",lightsalmon:\"#ffa07a\",lightseagreen:\"#20b2aa\",lightskyblue:\"#87cefa\",lightslategray:\"#778899\",lightslategrey:\"#778899\",lightsteelblue:\"#b0c4de\",lightyellow:\"#ffffe0\",lime:\"#00ff00\",limegreen:\"#32cd32\",linen:\"#faf0e6\",magenta:\"#ff00ff\",maroon:\"#800000\",mediumaquamarine:\"#66cdaa\",mediumblue:\"#0000cd\",mediumorchid:\"#ba55d3\",mediumpurple:\"#9370d8\",mediumseagreen:\"#3cb371\",mediumslateblue:\"#7b68ee\",mediumspringgreen:\"#00fa9a\",mediumturquoise:\"#48d1cc\",mediumvioletred:\"#c71585\",midnightblue:\"#191970\",mintcream:\"#f5fffa\",mistyrose:\"#ffe4e1\",moccasin:\"#ffe4b5\",navajowhite:\"#ffdead\",navy:\"#000080\",oldlace:\"#fdf5e6\",olive:\"#808000\",olivedrab:\"#6b8e23\",orange:\"#ffa500\",orangered:\"#ff4500\",orchid:\"#da70d6\",palegoldenrod:\"#eee8aa\",palegreen:\"#98fb98\",paleturquoise:\"#afeeee\",palevioletred:\"#d87093\",papayawhip:\"#ffefd5\",peachpuff:\"#ffdab9\",peru:\"#cd853f\",pink:\"#ffc0cb\",plum:\"#dda0dd\",powderblue:\"#b0e0e6\",purple:\"#800080\",red:\"#ff0000\",rosybrown:\"#bc8f8f\",royalblue:\"#4169e1\",saddlebrown:\"#8b4513\",salmon:\"#fa8072\",sandybrown:\"#f4a460\",seagreen:\"#2e8b57\",seashell:\"#fff5ee\",sienna:\"#a0522d\",silver:\"#c0c0c0\",skyblue:\"#87ceeb\",slateblue:\"#6a5acd\",slategray:\"#708090\",slategrey:\"#708090\",snow:\"#fffafa\",springgreen:\"#00ff7f\",steelblue:\"#4682b4\",tan:\"#d2b48c\",teal:\"#008080\",thistle:\"#d8bfd8\",tomato:\"#ff6347\",turquoise:\"#40e0d0\",violet:\"#ee82ee\",wheat:\"#f5deb3\",white:\"#ffffff\",whitesmoke:\"#f5f5f5\",yellow:\"#ffff00\",yellowgreen:\"#9acd32\",activeBorder:\"Active window border.\",activecaption:\"Active window caption.\",appworkspace:\"Background color of multiple document interface.\",background:\"Desktop background.\",buttonface:\"The face background color for 3-D elements that appear 3-D due to one layer of surrounding border.\",buttonhighlight:\"The color of the border facing the light source for 3-D elements that appear 3-D due to one layer of surrounding border.\",buttonshadow:\"The color of the border away from the light source for 3-D elements that appear 3-D due to one layer of surrounding border.\",buttontext:\"Text on push buttons.\",captiontext:\"Text in caption, size box, and scrollbar arrow box.\",graytext:\"Grayed (disabled) text. This color is set to #000 if the current display driver does not support a solid gray color.\",greytext:\"Greyed (disabled) text. This color is set to #000 if the current display driver does not support a solid grey color.\",highlight:\"Item(s) selected in a control.\",highlighttext:\"Text of item(s) selected in a control.\",inactiveborder:\"Inactive window border.\",inactivecaption:\"Inactive window caption.\",inactivecaptiontext:\"Color of text in an inactive caption.\",infobackground:\"Background color for tooltip controls.\",infotext:\"Text color for tooltip controls.\",menu:\"Menu background.\",menutext:\"Text in menus.\",scrollbar:\"Scroll bar gray area.\",threeddarkshadow:\"The color of the darker (generally outer) of the two borders away from the light source for 3-D elements that appear 3-D due to two concentric layers of surrounding border.\",threedface:\"The face background color for 3-D elements that appear 3-D due to two concentric layers of surrounding border.\",threedhighlight:\"The color of the lighter (generally outer) of the two borders facing the light source for 3-D elements that appear 3-D due to two concentric layers of surrounding border.\",threedlightshadow:\"The color of the darker (generally inner) of the two borders facing the light source for 3-D elements that appear 3-D due to two concentric layers of surrounding border.\",threedshadow:\"The color of the lighter (generally inner) of the two borders away from the light source for 3-D elements that appear 3-D due to two concentric layers of surrounding border.\",window:\"Window background.\",windowframe:\"Window frame.\",windowtext:\"Text in windows.\"};Combinator.prototype=new SyntaxUnit,Combinator.prototype.constructor=Combinator,MediaFeature.prototype=new SyntaxUnit,MediaFeature.prototype.constructor=MediaFeature,MediaQuery.prototype=new SyntaxUnit,MediaQuery.prototype.constructor=MediaQuery,Parser.DEFAULT_TYPE=0,Parser.COMBINATOR_TYPE=1,Parser.MEDIA_FEATURE_TYPE=2,Parser.MEDIA_QUERY_TYPE=3,Parser.PROPERTY_NAME_TYPE=4,Parser.PROPERTY_VALUE_TYPE=5,Parser.PROPERTY_VALUE_PART_TYPE=6,Parser.SELECTOR_TYPE=7,Parser.SELECTOR_PART_TYPE=8,Parser.SELECTOR_SUB_PART_TYPE=9,Parser.prototype=function(){var e=new EventTarget,t,n={constructor:Parser,DEFAULT_TYPE:0,COMBINATOR_TYPE:1,MEDIA_FEATURE_TYPE:2,MEDIA_QUERY_TYPE:3,PROPERTY_NAME_TYPE:4,PROPERTY_VALUE_TYPE:5,PROPERTY_VALUE_PART_TYPE:6,SELECTOR_TYPE:7,SELECTOR_PART_TYPE:8,SELECTOR_SUB_PART_TYPE:9,_stylesheet:function(){var e=this._tokenStream,t=null,n,r,i;this.fire(\"startstylesheet\"),this._charset(),this._skipCruft();while(e.peek()==Tokens.IMPORT_SYM)this._import(),this._skipCruft();while(e.peek()==Tokens.NAMESPACE_SYM)this._namespace(),this._skipCruft();i=e.peek();while(i>Tokens.EOF){try{switch(i){case Tokens.MEDIA_SYM:this._media(),this._skipCruft();break;case Tokens.PAGE_SYM:this._page(),this._skipCruft();break;case Tokens.FONT_FACE_SYM:this._font_face(),this._skipCruft();break;case Tokens.KEYFRAMES_SYM:this._keyframes(),this._skipCruft();break;case Tokens.VIEWPORT_SYM:this._viewport(),this._skipCruft();break;case Tokens.UNKNOWN_SYM:e.get();if(!!this.options.strict)throw new SyntaxError(\"Unknown @ rule.\",e.LT(0).startLine,e.LT(0).startCol);this.fire({type:\"error\",error:null,message:\"Unknown @ rule: \"+e.LT(0).value+\".\",line:e.LT(0).startLine,col:e.LT(0).startCol}),n=0;while(e.advance([Tokens.LBRACE,Tokens.RBRACE])==Tokens.LBRACE)n++;while(n)e.advance([Tokens.RBRACE]),n--;break;case Tokens.S:this._readWhitespace();break;default:if(!this._ruleset())switch(i){case Tokens.CHARSET_SYM:throw r=e.LT(1),this._charset(!1),new SyntaxError(\"@charset not allowed here.\",r.startLine,r.startCol);case Tokens.IMPORT_SYM:throw r=e.LT(1),this._import(!1),new SyntaxError(\"@import not allowed here.\",r.startLine,r.startCol);case Tokens.NAMESPACE_SYM:throw r=e.LT(1),this._namespace(!1),new SyntaxError(\"@namespace not allowed here.\",r.startLine,r.startCol);default:e.get(),this._unexpectedToken(e.token())}}}catch(s){if(!(s instanceof SyntaxError&&!this.options.strict))throw s;this.fire({type:\"error\",error:s,message:s.message,line:s.line,col:s.col})}i=e.peek()}i!=Tokens.EOF&&this._unexpectedToken(e.token()),this.fire(\"endstylesheet\")},_charset:function(e){var t=this._tokenStream,n,r,i,s;t.match(Tokens.CHARSET_SYM)&&(i=t.token().startLine,s=t.token().startCol,this._readWhitespace(),t.mustMatch(Tokens.STRING),r=t.token(),n=r.value,this._readWhitespace(),t.mustMatch(Tokens.SEMICOLON),e!==!1&&this.fire({type:\"charset\",charset:n,line:i,col:s}))},_import:function(e){var t=this._tokenStream,n,r,i,s=[];t.mustMatch(Tokens.IMPORT_SYM),i=t.token(),this._readWhitespace(),t.mustMatch([Tokens.STRING,Tokens.URI]),r=t.token().value.replace(/^(?:url\\()?[\"']?([^\"']+?)[\"']?\\)?$/,\"$1\"),this._readWhitespace(),s=this._media_query_list(),t.mustMatch(Tokens.SEMICOLON),this._readWhitespace(),e!==!1&&this.fire({type:\"import\",uri:r,media:s,line:i.startLine,col:i.startCol})},_namespace:function(e){var t=this._tokenStream,n,r,i,s;t.mustMatch(Tokens.NAMESPACE_SYM),n=t.token().startLine,r=t.token().startCol,this._readWhitespace(),t.match(Tokens.IDENT)&&(i=t.token().value,this._readWhitespace()),t.mustMatch([Tokens.STRING,Tokens.URI]),s=t.token().value.replace(/(?:url\\()?[\"']([^\"']+)[\"']\\)?/,\"$1\"),this._readWhitespace(),t.mustMatch(Tokens.SEMICOLON),this._readWhitespace(),e!==!1&&this.fire({type:\"namespace\",prefix:i,uri:s,line:n,col:r})},_media:function(){var e=this._tokenStream,t,n,r;e.mustMatch(Tokens.MEDIA_SYM),t=e.token().startLine,n=e.token().startCol,this._readWhitespace(),r=this._media_query_list(),e.mustMatch(Tokens.LBRACE),this._readWhitespace(),this.fire({type:\"startmedia\",media:r,line:t,col:n});for(;;)if(e.peek()==Tokens.PAGE_SYM)this._page();else if(e.peek()==Tokens.FONT_FACE_SYM)this._font_face();else if(e.peek()==Tokens.VIEWPORT_SYM)this._viewport();else if(!this._ruleset())break;e.mustMatch(Tokens.RBRACE),this._readWhitespace(),this.fire({type:\"endmedia\",media:r,line:t,col:n})},_media_query_list:function(){var e=this._tokenStream,t=[];this._readWhitespace(),(e.peek()==Tokens.IDENT||e.peek()==Tokens.LPAREN)&&t.push(this._media_query());while(e.match(Tokens.COMMA))this._readWhitespace(),t.push(this._media_query());return t},_media_query:function(){var e=this._tokenStream,t=null,n=null,r=null,i=[];e.match(Tokens.IDENT)&&(n=e.token().value.toLowerCase(),n!=\"only\"&&n!=\"not\"?(e.unget(),n=null):r=e.token()),this._readWhitespace(),e.peek()==Tokens.IDENT?(t=this._media_type(),r===null&&(r=e.token())):e.peek()==Tokens.LPAREN&&(r===null&&(r=e.LT(1)),i.push(this._media_expression()));if(t===null&&i.length===0)return null;this._readWhitespace();while(e.match(Tokens.IDENT))e.token().value.toLowerCase()!=\"and\"&&this._unexpectedToken(e.token()),this._readWhitespace(),i.push(this._media_expression());return new MediaQuery(n,t,i,r.startLine,r.startCol)},_media_type:function(){return this._media_feature()},_media_expression:function(){var e=this._tokenStream,t=null,n,r=null;return e.mustMatch(Tokens.LPAREN),t=this._media_feature(),this._readWhitespace(),e.match(Tokens.COLON)&&(this._readWhitespace(),n=e.LT(1),r=this._expression()),e.mustMatch(Tokens.RPAREN),this._readWhitespace(),new MediaFeature(t,r?new SyntaxUnit(r,n.startLine,n.startCol):null)},_media_feature:function(){var e=this._tokenStream;return e.mustMatch(Tokens.IDENT),SyntaxUnit.fromToken(e.token())},_page:function(){var e=this._tokenStream,t,n,r=null,i=null;e.mustMatch(Tokens.PAGE_SYM),t=e.token().startLine,n=e.token().startCol,this._readWhitespace(),e.match(Tokens.IDENT)&&(r=e.token().value,r.toLowerCase()===\"auto\"&&this._unexpectedToken(e.token())),e.peek()==Tokens.COLON&&(i=this._pseudo_page()),this._readWhitespace(),this.fire({type:\"startpage\",id:r,pseudo:i,line:t,col:n}),this._readDeclarations(!0,!0),this.fire({type:\"endpage\",id:r,pseudo:i,line:t,col:n})},_margin:function(){var e=this._tokenStream,t,n,r=this._margin_sym();return r?(t=e.token().startLine,n=e.token().startCol,this.fire({type:\"startpagemargin\",margin:r,line:t,col:n}),this._readDeclarations(!0),this.fire({type:\"endpagemargin\",margin:r,line:t,col:n}),!0):!1},_margin_sym:function(){var e=this._tokenStream;return e.match([Tokens.TOPLEFTCORNER_SYM,Tokens.TOPLEFT_SYM,Tokens.TOPCENTER_SYM,Tokens.TOPRIGHT_SYM,Tokens.TOPRIGHTCORNER_SYM,Tokens.BOTTOMLEFTCORNER_SYM,Tokens.BOTTOMLEFT_SYM,Tokens.BOTTOMCENTER_SYM,Tokens.BOTTOMRIGHT_SYM,Tokens.BOTTOMRIGHTCORNER_SYM,Tokens.LEFTTOP_SYM,Tokens.LEFTMIDDLE_SYM,Tokens.LEFTBOTTOM_SYM,Tokens.RIGHTTOP_SYM,Tokens.RIGHTMIDDLE_SYM,Tokens.RIGHTBOTTOM_SYM])?SyntaxUnit.fromToken(e.token()):null},_pseudo_page:function(){var e=this._tokenStream;return e.mustMatch(Tokens.COLON),e.mustMatch(Tokens.IDENT),e.token().value},_font_face:function(){var e=this._tokenStream,t,n;e.mustMatch(Tokens.FONT_FACE_SYM),t=e.token().startLine,n=e.token().startCol,this._readWhitespace(),this.fire({type:\"startfontface\",line:t,col:n}),this._readDeclarations(!0),this.fire({type:\"endfontface\",line:t,col:n})},_viewport:function(){var e=this._tokenStream,t,n;e.mustMatch(Tokens.VIEWPORT_SYM),t=e.token().startLine,n=e.token().startCol,this._readWhitespace(),this.fire({type:\"startviewport\",line:t,col:n}),this._readDeclarations(!0),this.fire({type:\"endviewport\",line:t,col:n})},_operator:function(e){var t=this._tokenStream,n=null;if(t.match([Tokens.SLASH,Tokens.COMMA])||e&&t.match([Tokens.PLUS,Tokens.STAR,Tokens.MINUS]))n=t.token(),this._readWhitespace();return n?PropertyValuePart.fromToken(n):null},_combinator:function(){var e=this._tokenStream,t=null,n;return e.match([Tokens.PLUS,Tokens.GREATER,Tokens.TILDE])&&(n=e.token(),t=new Combinator(n.value,n.startLine,n.startCol),this._readWhitespace()),t},_unary_operator:function(){var e=this._tokenStream;return e.match([Tokens.MINUS,Tokens.PLUS])?e.token().value:null},_property:function(){var e=this._tokenStream,t=null,n=null,r,i,s,o;return e.peek()==Tokens.STAR&&this.options.starHack&&(e.get(),i=e.token(),n=i.value,s=i.startLine,o=i.startCol),e.match(Tokens.IDENT)&&(i=e.token(),r=i.value,r.charAt(0)==\"_\"&&this.options.underscoreHack&&(n=\"_\",r=r.substring(1)),t=new PropertyName(r,n,s||i.startLine,o||i.startCol),this._readWhitespace()),t},_ruleset:function(){var e=this._tokenStream,t,n;try{n=this._selectors_group()}catch(r){if(r instanceof SyntaxError&&!this.options.strict){this.fire({type:\"error\",error:r,message:r.message,line:r.line,col:r.col}),t=e.advance([Tokens.RBRACE]);if(t!=Tokens.RBRACE)throw r;return!0}throw r}return n&&(this.fire({type:\"startrule\",selectors:n,line:n[0].line,col:n[0].col}),this._readDeclarations(!0),this.fire({type:\"endrule\",selectors:n,line:n[0].line,col:n[0].col})),n},_selectors_group:function(){var e=this._tokenStream,t=[],n;n=this._selector();if(n!==null){t.push(n);while(e.match(Tokens.COMMA))this._readWhitespace(),n=this._selector(),n!==null?t.push(n):this._unexpectedToken(e.LT(1))}return t.length?t:null},_selector:function(){var e=this._tokenStream,t=[],n=null,r=null,i=null;n=this._simple_selector_sequence();if(n===null)return null;t.push(n);do{r=this._combinator();if(r!==null)t.push(r),n=this._simple_selector_sequence(),n===null?this._unexpectedToken(e.LT(1)):t.push(n);else{if(!this._readWhitespace())break;i=new Combinator(e.token().value,e.token().startLine,e.token().startCol),r=this._combinator(),n=this._simple_selector_sequence(),n===null?r!==null&&this._unexpectedToken(e.LT(1)):(r!==null?t.push(r):t.push(i),t.push(n))}}while(!0);return new Selector(t,t[0].line,t[0].col)},_simple_selector_sequence:function(){var e=this._tokenStream,t=null,n=[],r=\"\",i=[function(){return e.match(Tokens.HASH)?new SelectorSubPart(e.token().value,\"id\",e.token().startLine,e.token().startCol):null},this._class,this._attrib,this._pseudo,this._negation],s=0,o=i.length,u=null,a=!1,f,l;f=e.LT(1).startLine,l=e.LT(1).startCol,t=this._type_selector(),t||(t=this._universal()),t!==null&&(r+=t);for(;;){if(e.peek()===Tokens.S)break;while(s<o&&u===null)u=i[s++].call(this);if(u===null){if(r===\"\")return null;break}s=0,n.push(u),r+=u.toString(),u=null}return r!==\"\"?new SelectorPart(t,n,r,f,l):null},_type_selector:function(){var e=this._tokenStream,t=this._namespace_prefix(),n=this._element_name();return n?(t&&(n.text=t+n.text,n.col-=t.length),n):(t&&(e.unget(),t.length>1&&e.unget()),null)},_class:function(){var e=this._tokenStream,t;return e.match(Tokens.DOT)?(e.mustMatch(Tokens.IDENT),t=e.token(),new SelectorSubPart(\".\"+t.value,\"class\",t.startLine,t.startCol-1)):null},_element_name:function(){var e=this._tokenStream,t;return e.match(Tokens.IDENT)?(t=e.token(),new SelectorSubPart(t.value,\"elementName\",t.startLine,t.startCol)):null},_namespace_prefix:function(){var e=this._tokenStream,t=\"\";if(e.LA(1)===Tokens.PIPE||e.LA(2)===Tokens.PIPE)e.match([Tokens.IDENT,Tokens.STAR])&&(t+=e.token().value),e.mustMatch(Tokens.PIPE),t+=\"|\";return t.length?t:null},_universal:function(){var e=this._tokenStream,t=\"\",n;return n=this._namespace_prefix(),n&&(t+=n),e.match(Tokens.STAR)&&(t+=\"*\"),t.length?t:null},_attrib:function(){var e=this._tokenStream,t=null,n,r;return e.match(Tokens.LBRACKET)?(r=e.token(),t=r.value,t+=this._readWhitespace(),n=this._namespace_prefix(),n&&(t+=n),e.mustMatch(Tokens.IDENT),t+=e.token().value,t+=this._readWhitespace(),e.match([Tokens.PREFIXMATCH,Tokens.SUFFIXMATCH,Tokens.SUBSTRINGMATCH,Tokens.EQUALS,Tokens.INCLUDES,Tokens.DASHMATCH])&&(t+=e.token().value,t+=this._readWhitespace(),e.mustMatch([Tokens.IDENT,Tokens.STRING]),t+=e.token().value,t+=this._readWhitespace()),e.mustMatch(Tokens.RBRACKET),new SelectorSubPart(t+\"]\",\"attribute\",r.startLine,r.startCol)):null},_pseudo:function(){var e=this._tokenStream,t=null,n=\":\",r,i;return e.match(Tokens.COLON)&&(e.match(Tokens.COLON)&&(n+=\":\"),e.match(Tokens.IDENT)?(t=e.token().value,r=e.token().startLine,i=e.token().startCol-n.length):e.peek()==Tokens.FUNCTION&&(r=e.LT(1).startLine,i=e.LT(1).startCol-n.length,t=this._functional_pseudo()),t&&(t=new SelectorSubPart(n+t,\"pseudo\",r,i))),t},_functional_pseudo:function(){var e=this._tokenStream,t=null;return e.match(Tokens.FUNCTION)&&(t=e.token().value,t+=this._readWhitespace(),t+=this._expression(),e.mustMatch(Tokens.RPAREN),t+=\")\"),t},_expression:function(){var e=this._tokenStream,t=\"\";while(e.match([Tokens.PLUS,Tokens.MINUS,Tokens.DIMENSION,Tokens.NUMBER,Tokens.STRING,Tokens.IDENT,Tokens.LENGTH,Tokens.FREQ,Tokens.ANGLE,Tokens.TIME,Tokens.RESOLUTION,Tokens.SLASH]))t+=e.token().value,t+=this._readWhitespace();return t.length?t:null},_negation:function(){var e=this._tokenStream,t,n,r=\"\",i,s=null;return e.match(Tokens.NOT)&&(r=e.token().value,t=e.token().startLine,n=e.token().startCol,r+=this._readWhitespace(),i=this._negation_arg(),r+=i,r+=this._readWhitespace(),e.match(Tokens.RPAREN),r+=e.token().value,s=new SelectorSubPart(r,\"not\",t,n),s.args.push(i)),s},_negation_arg:function(){var e=this._tokenStream,t=[this._type_selector,this._universal,function(){return e.match(Tokens.HASH)?new SelectorSubPart(e.token().value,\"id\",e.token().startLine,e.token().startCol):null},this._class,this._attrib,this._pseudo],n=null,r=0,i=t.length,s,o,u,a;o=e.LT(1).startLine,u=e.LT(1).startCol;while(r<i&&n===null)n=t[r].call(this),r++;return n===null&&this._unexpectedToken(e.LT(1)),n.type==\"elementName\"?a=new SelectorPart(n,[],n.toString(),o,u):a=new SelectorPart(null,[n],n.toString(),o,u),a},_declaration:function(){var e=this._tokenStream,t=null,n=null,r=null,i=null,s=null,o=\"\";t=this._property();if(t!==null){e.mustMatch(Tokens.COLON),this._readWhitespace(),n=this._expr(),(!n||n.length===0)&&this._unexpectedToken(e.LT(1)),r=this._prio(),o=t.toString();if(this.options.starHack&&t.hack==\"*\"||this.options.underscoreHack&&t.hack==\"_\")o=t.text;try{this._validateProperty(o,n)}catch(u){s=u}return this.fire({type:\"property\",property:t,value:n,important:r,line:t.line,col:t.col,invalid:s}),!0}return!1},_prio:function(){var e=this._tokenStream,t=e.match(Tokens.IMPORTANT_SYM);return this._readWhitespace(),t},_expr:function(e){var t=this._tokenStream,n=[],r=null,i=null;r=this._term(e);if(r!==null){n.push(r);do{i=this._operator(e),i&&n.push(i),r=this._term(e);if(r===null)break;n.push(r)}while(!0)}return n.length>0?new PropertyValue(n,n[0].line,n[0].col):null},_term:function(e){var t=this._tokenStream,n=null,r=null,i=null,s,o,u;return n=this._unary_operator(),n!==null&&(o=t.token().startLine,u=t.token().startCol),t.peek()==Tokens.IE_FUNCTION&&this.options.ieFilters?(r=this._ie_function(),n===null&&(o=t.token().startLine,u=t.token().startCol)):e&&t.match([Tokens.LPAREN,Tokens.LBRACE,Tokens.LBRACKET])?(s=t.token(),i=s.endChar,r=s.value+this._expr(e).text,n===null&&(o=t.token().startLine,u=t.token().startCol),t.mustMatch(Tokens.type(i)),r+=i,this._readWhitespace()):t.match([Tokens.NUMBER,Tokens.PERCENTAGE,Tokens.LENGTH,Tokens.ANGLE,Tokens.TIME,Tokens.FREQ,Tokens.STRING,Tokens.IDENT,Tokens.URI,Tokens.UNICODE_RANGE])?(r=t.token().value,n===null&&(o=t.token().startLine,u=t.token().startCol),this._readWhitespace()):(s=this._hexcolor(),s===null?(n===null&&(o=t.LT(1).startLine,u=t.LT(1).startCol),r===null&&(t.LA(3)==Tokens.EQUALS&&this.options.ieFilters?r=this._ie_function():r=this._function())):(r=s.value,n===null&&(o=s.startLine,u=s.startCol))),r!==null?new PropertyValuePart(n!==null?n+r:r,o,u):null},_function:function(){var e=this._tokenStream,t=null,n=null,r;if(e.match(Tokens.FUNCTION)){t=e.token().value,this._readWhitespace(),n=this._expr(!0),t+=n;if(this.options.ieFilters&&e.peek()==Tokens.EQUALS)do{this._readWhitespace()&&(t+=e.token().value),e.LA(0)==Tokens.COMMA&&(t+=e.token().value),e.match(Tokens.IDENT),t+=e.token().value,e.match(Tokens.EQUALS),t+=e.token().value,r=e.peek();while(r!=Tokens.COMMA&&r!=Tokens.S&&r!=Tokens.RPAREN)e.get(),t+=e.token().value,r=e.peek()}while(e.match([Tokens.COMMA,Tokens.S]));e.match(Tokens.RPAREN),t+=\")\",this._readWhitespace()}return t},_ie_function:function(){var e=this._tokenStream,t=null,n=null,r;if(e.match([Tokens.IE_FUNCTION,Tokens.FUNCTION])){t=e.token().value;do{this._readWhitespace()&&(t+=e.token().value),e.LA(0)==Tokens.COMMA&&(t+=e.token().value),e.match(Tokens.IDENT),t+=e.token().value,e.match(Tokens.EQUALS),t+=e.token().value,r=e.peek();while(r!=Tokens.COMMA&&r!=Tokens.S&&r!=Tokens.RPAREN)e.get(),t+=e.token().value,r=e.peek()}while(e.match([Tokens.COMMA,Tokens.S]));e.match(Tokens.RPAREN),t+=\")\",this._readWhitespace()}return t},_hexcolor:function(){var e=this._tokenStream,t=null,n;if(e.match(Tokens.HASH)){t=e.token(),n=t.value;if(!/#[a-f0-9]{3,6}/i.test(n))throw new SyntaxError(\"Expected a hex color but found '\"+n+\"' at line \"+t.startLine+\", col \"+t.startCol+\".\",t.startLine,t.startCol);this._readWhitespace()}return t},_keyframes:function(){var e=this._tokenStream,t,n,r,i=\"\";e.mustMatch(Tokens.KEYFRAMES_SYM),t=e.token(),/^@\\-([^\\-]+)\\-/.test(t.value)&&(i=RegExp.$1),this._readWhitespace(),r=this._keyframe_name(),this._readWhitespace(),e.mustMatch(Tokens.LBRACE),this.fire({type:\"startkeyframes\",name:r,prefix:i,line:t.startLine,col:t.startCol}),this._readWhitespace(),n=e.peek();while(n==Tokens.IDENT||n==Tokens.PERCENTAGE)this._keyframe_rule(),this._readWhitespace(),n=e.peek();this.fire({type:\"endkeyframes\",name:r,prefix:i,line:t.startLine,col:t.startCol}),this._readWhitespace(),e.mustMatch(Tokens.RBRACE)},_keyframe_name:function(){var e=this._tokenStream,t;return e.mustMatch([Tokens.IDENT,Tokens.STRING]),SyntaxUnit.fromToken(e.token())},_keyframe_rule:function(){var e=this._tokenStream,t,n=this._key_list();this.fire({type:\"startkeyframerule\",keys:n,line:n[0].line,col:n[0].col}),this._readDeclarations(!0),this.fire({type:\"endkeyframerule\",keys:n,line:n[0].line,col:n[0].col})},_key_list:function(){var e=this._tokenStream,t,n,r=[];r.push(this._key()),this._readWhitespace();while(e.match(Tokens.COMMA))this._readWhitespace(),r.push(this._key()),this._readWhitespace();return r},_key:function(){var e=this._tokenStream,t;if(e.match(Tokens.PERCENTAGE))return SyntaxUnit.fromToken(e.token());if(e.match(Tokens.IDENT)){t=e.token();if(/from|to/i.test(t.value))return SyntaxUnit.fromToken(t);e.unget()}this._unexpectedToken(e.LT(1))},_skipCruft:function(){while(this._tokenStream.match([Tokens.S,Tokens.CDO,Tokens.CDC]));},_readDeclarations:function(e,t){var n=this._tokenStream,r;this._readWhitespace(),e&&n.mustMatch(Tokens.LBRACE),this._readWhitespace();try{for(;;){if(!(n.match(Tokens.SEMICOLON)||t&&this._margin())){if(!this._declaration())break;if(!n.match(Tokens.SEMICOLON))break}this._readWhitespace()}n.mustMatch(Tokens.RBRACE),this._readWhitespace()}catch(i){if(!(i instanceof SyntaxError&&!this.options.strict))throw i;this.fire({type:\"error\",error:i,message:i.message,line:i.line,col:i.col}),r=n.advance([Tokens.SEMICOLON,Tokens.RBRACE]);if(r==Tokens.SEMICOLON)this._readDeclarations(!1,t);else if(r!=Tokens.RBRACE)throw i}},_readWhitespace:function(){var e=this._tokenStream,t=\"\";while(e.match(Tokens.S))t+=e.token().value;return t},_unexpectedToken:function(e){throw new SyntaxError(\"Unexpected token '\"+e.value+\"' at line \"+e.startLine+\", col \"+e.startCol+\".\",e.startLine,e.startCol)},_verifyEnd:function(){this._tokenStream.LA(1)!=Tokens.EOF&&this._unexpectedToken(this._tokenStream.LT(1))},_validateProperty:function(e,t){Validation.validate(e,t)},parse:function(e){this._tokenStream=new TokenStream(e,Tokens),this._stylesheet()},parseStyleSheet:function(e){return this.parse(e)},parseMediaQuery:function(e){this._tokenStream=new TokenStream(e,Tokens);var t=this._media_query();return this._verifyEnd(),t},parsePropertyValue:function(e){this._tokenStream=new TokenStream(e,Tokens),this._readWhitespace();var t=this._expr();return this._readWhitespace(),this._verifyEnd(),t},parseRule:function(e){this._tokenStream=new TokenStream(e,Tokens),this._readWhitespace();var t=this._ruleset();return this._readWhitespace(),this._verifyEnd(),t},parseSelector:function(e){this._tokenStream=new TokenStream(e,Tokens),this._readWhitespace();var t=this._selector();return this._readWhitespace(),this._verifyEnd(),t},parseStyleAttribute:function(e){e+=\"}\",this._tokenStream=new TokenStream(e,Tokens),this._readDeclarations()}};for(t in n)n.hasOwnProperty(t)&&(e[t]=n[t]);return e}();var Properties={\"align-items\":\"flex-start | flex-end | center | baseline | stretch\",\"align-content\":\"flex-start | flex-end | center | space-between | space-around | stretch\",\"align-self\":\"auto | flex-start | flex-end | center | baseline | stretch\",\"-webkit-align-items\":\"flex-start | flex-end | center | baseline | stretch\",\"-webkit-align-content\":\"flex-start | flex-end | center | space-between | space-around | stretch\",\"-webkit-align-self\":\"auto | flex-start | flex-end | center | baseline | stretch\",\"alignment-adjust\":\"auto | baseline | before-edge | text-before-edge | middle | central | after-edge | text-after-edge | ideographic | alphabetic | hanging | mathematical | <percentage> | <length>\",\"alignment-baseline\":\"baseline | use-script | before-edge | text-before-edge | after-edge | text-after-edge | central | middle | ideographic | alphabetic | hanging | mathematical\",animation:1,\"animation-delay\":{multi:\"<time>\",comma:!0},\"animation-direction\":{multi:\"normal | reverse | alternate | alternate-reverse\",comma:!0},\"animation-duration\":{multi:\"<time>\",comma:!0},\"animation-fill-mode\":{multi:\"none | forwards | backwards | both\",comma:!0},\"animation-iteration-count\":{multi:\"<number> | infinite\",comma:!0},\"animation-name\":{multi:\"none | <ident>\",comma:!0},\"animation-play-state\":{multi:\"running | paused\",comma:!0},\"animation-timing-function\":1,\"-moz-animation-delay\":{multi:\"<time>\",comma:!0},\"-moz-animation-direction\":{multi:\"normal | reverse | alternate | alternate-reverse\",comma:!0},\"-moz-animation-duration\":{multi:\"<time>\",comma:!0},\"-moz-animation-iteration-count\":{multi:\"<number> | infinite\",comma:!0},\"-moz-animation-name\":{multi:\"none | <ident>\",comma:!0},\"-moz-animation-play-state\":{multi:\"running | paused\",comma:!0},\"-ms-animation-delay\":{multi:\"<time>\",comma:!0},\"-ms-animation-direction\":{multi:\"normal | reverse | alternate | alternate-reverse\",comma:!0},\"-ms-animation-duration\":{multi:\"<time>\",comma:!0},\"-ms-animation-iteration-count\":{multi:\"<number> | infinite\",comma:!0},\"-ms-animation-name\":{multi:\"none | <ident>\",comma:!0},\"-ms-animation-play-state\":{multi:\"running | paused\",comma:!0},\"-webkit-animation-delay\":{multi:\"<time>\",comma:!0},\"-webkit-animation-direction\":{multi:\"normal | reverse | alternate | alternate-reverse\",comma:!0},\"-webkit-animation-duration\":{multi:\"<time>\",comma:!0},\"-webkit-animation-fill-mode\":{multi:\"none | forwards | backwards | both\",comma:!0},\"-webkit-animation-iteration-count\":{multi:\"<number> | infinite\",comma:!0},\"-webkit-animation-name\":{multi:\"none | <ident>\",comma:!0},\"-webkit-animation-play-state\":{multi:\"running | paused\",comma:!0},\"-o-animation-delay\":{multi:\"<time>\",comma:!0},\"-o-animation-direction\":{multi:\"normal | reverse | alternate | alternate-reverse\",comma:!0},\"-o-animation-duration\":{multi:\"<time>\",comma:!0},\"-o-animation-iteration-count\":{multi:\"<number> | infinite\",comma:!0},\"-o-animation-name\":{multi:\"none | <ident>\",comma:!0},\"-o-animation-play-state\":{multi:\"running | paused\",comma:!0},appearance:\"icon | window | desktop | workspace | document | tooltip | dialog | button | push-button | hyperlink | radio-button | checkbox | menu-item | tab | menu | menubar | pull-down-menu | pop-up-menu | list-menu | radio-group | checkbox-group | outline-tree | range | field | combo-box | signature | password | normal | none | inherit\",azimuth:function(e){var t=\"<angle> | leftwards | rightwards | inherit\",n=\"left-side | far-left | left | center-left | center | center-right | right | far-right | right-side\",r=!1,i=!1,s;ValidationTypes.isAny(e,t)||(ValidationTypes.isAny(e,\"behind\")&&(r=!0,i=!0),ValidationTypes.isAny(e,n)&&(i=!0,r||ValidationTypes.isAny(e,\"behind\")));if(e.hasNext())throw s=e.next(),i?new ValidationError(\"Expected end of value but found '\"+s+\"'.\",s.line,s.col):new ValidationError(\"Expected (<'azimuth'>) but found '\"+s+\"'.\",s.line,s.col)},\"backface-visibility\":\"visible | hidden\",background:1,\"background-attachment\":{multi:\"<attachment>\",comma:!0},\"background-clip\":{multi:\"<box>\",comma:!0},\"background-color\":\"<color> | inherit\",\"background-image\":{multi:\"<bg-image>\",comma:!0},\"background-origin\":{multi:\"<box>\",comma:!0},\"background-position\":{multi:\"<bg-position>\",comma:!0},\"background-repeat\":{multi:\"<repeat-style>\"},\"background-size\":{multi:\"<bg-size>\",comma:!0},\"baseline-shift\":\"baseline | sub | super | <percentage> | <length>\",behavior:1,binding:1,bleed:\"<length>\",\"bookmark-label\":\"<content> | <attr> | <string>\",\"bookmark-level\":\"none | <integer>\",\"bookmark-state\":\"open | closed\",\"bookmark-target\":\"none | <uri> | <attr>\",border:\"<border-width> || <border-style> || <color>\",\"border-bottom\":\"<border-width> || <border-style> || <color>\",\"border-bottom-color\":\"<color> | inherit\",\"border-bottom-left-radius\":\"<x-one-radius>\",\"border-bottom-right-radius\":\"<x-one-radius>\",\"border-bottom-style\":\"<border-style>\",\"border-bottom-width\":\"<border-width>\",\"border-collapse\":\"collapse | separate | inherit\",\"border-color\":{multi:\"<color> | inherit\",max:4},\"border-image\":1,\"border-image-outset\":{multi:\"<length> | <number>\",max:4},\"border-image-repeat\":{multi:\"stretch | repeat | round\",max:2},\"border-image-slice\":function(e){var t=!1,n=\"<number> | <percentage>\",r=!1,i=0,s=4,o;ValidationTypes.isAny(e,\"fill\")&&(r=!0,t=!0);while(e.hasNext()&&i<s){t=ValidationTypes.isAny(e,n);if(!t)break;i++}r?t=!0:ValidationTypes.isAny(e,\"fill\");if(e.hasNext())throw o=e.next(),t?new ValidationError(\"Expected end of value but found '\"+o+\"'.\",o.line,o.col):new ValidationError(\"Expected ([<number> | <percentage>]{1,4} && fill?) but found '\"+o+\"'.\",o.line,o.col)},\"border-image-source\":\"<image> | none\",\"border-image-width\":{multi:\"<length> | <percentage> | <number> | auto\",max:4},\"border-left\":\"<border-width> || <border-style> || <color>\",\"border-left-color\":\"<color> | inherit\",\"border-left-style\":\"<border-style>\",\"border-left-width\":\"<border-width>\",\"border-radius\":function(e){var t=!1,n=\"<length> | <percentage> | inherit\",r=!1,i=!1,s=0,o=8,u;while(e.hasNext()&&s<o){t=ValidationTypes.isAny(e,n);if(!t){if(!(e.peek()==\"/\"&&s>0&&!r))break;r=!0,o=s+5,e.next()}s++}if(e.hasNext())throw u=e.next(),t?new ValidationError(\"Expected end of value but found '\"+u+\"'.\",u.line,u.col):new ValidationError(\"Expected (<'border-radius'>) but found '\"+u+\"'.\",u.line,u.col)},\"border-right\":\"<border-width> || <border-style> || <color>\",\"border-right-color\":\"<color> | inherit\",\"border-right-style\":\"<border-style>\",\"border-right-width\":\"<border-width>\",\"border-spacing\":{multi:\"<length> | inherit\",max:2},\"border-style\":{multi:\"<border-style>\",max:4},\"border-top\":\"<border-width> || <border-style> || <color>\",\"border-top-color\":\"<color> | inherit\",\"border-top-left-radius\":\"<x-one-radius>\",\"border-top-right-radius\":\"<x-one-radius>\",\"border-top-style\":\"<border-style>\",\"border-top-width\":\"<border-width>\",\"border-width\":{multi:\"<border-width>\",max:4},bottom:\"<margin-width> | inherit\",\"-moz-box-align\":\"start | end | center | baseline | stretch\",\"-moz-box-decoration-break\":\"slice |clone\",\"-moz-box-direction\":\"normal | reverse | inherit\",\"-moz-box-flex\":\"<number>\",\"-moz-box-flex-group\":\"<integer>\",\"-moz-box-lines\":\"single | multiple\",\"-moz-box-ordinal-group\":\"<integer>\",\"-moz-box-orient\":\"horizontal | vertical | inline-axis | block-axis | inherit\",\"-moz-box-pack\":\"start | end | center | justify\",\"-webkit-box-align\":\"start | end | center | baseline | stretch\",\"-webkit-box-decoration-break\":\"slice |clone\",\"-webkit-box-direction\":\"normal | reverse | inherit\",\"-webkit-box-flex\":\"<number>\",\"-webkit-box-flex-group\":\"<integer>\",\"-webkit-box-lines\":\"single | multiple\",\"-webkit-box-ordinal-group\":\"<integer>\",\"-webkit-box-orient\":\"horizontal | vertical | inline-axis | block-axis | inherit\",\"-webkit-box-pack\":\"start | end | center | justify\",\"box-shadow\":function(e){var t=!1,n;if(!ValidationTypes.isAny(e,\"none\"))Validation.multiProperty(\"<shadow>\",e,!0,Infinity);else if(e.hasNext())throw n=e.next(),new ValidationError(\"Expected end of value but found '\"+n+\"'.\",n.line,n.col)},\"box-sizing\":\"content-box | border-box | inherit\",\"break-after\":\"auto | always | avoid | left | right | page | column | avoid-page | avoid-column\",\"break-before\":\"auto | always | avoid | left | right | page | column | avoid-page | avoid-column\",\"break-inside\":\"auto | avoid | avoid-page | avoid-column\",\"caption-side\":\"top | bottom | inherit\",clear:\"none | right | left | both | inherit\",clip:1,color:\"<color> | inherit\",\"color-profile\":1,\"column-count\":\"<integer> | auto\",\"column-fill\":\"auto | balance\",\"column-gap\":\"<length> | normal\",\"column-rule\":\"<border-width> || <border-style> || <color>\",\"column-rule-color\":\"<color>\",\"column-rule-style\":\"<border-style>\",\"column-rule-width\":\"<border-width>\",\"column-span\":\"none | all\",\"column-width\":\"<length> | auto\",columns:1,content:1,\"counter-increment\":1,\"counter-reset\":1,crop:\"<shape> | auto\",cue:\"cue-after | cue-before | inherit\",\"cue-after\":1,\"cue-before\":1,cursor:1,direction:\"ltr | rtl | inherit\",display:\"inline | block | list-item | inline-block | table | inline-table | table-row-group | table-header-group | table-footer-group | table-row | table-column-group | table-column | table-cell | table-caption | grid | inline-grid | none | inherit | -moz-box | -moz-inline-block | -moz-inline-box | -moz-inline-grid | -moz-inline-stack | -moz-inline-table | -moz-grid | -moz-grid-group | -moz-grid-line | -moz-groupbox | -moz-deck | -moz-popup | -moz-stack | -moz-marker | -webkit-box | -webkit-inline-box | -ms-flexbox | -ms-inline-flexbox | flex | -webkit-flex | inline-flex | -webkit-inline-flex\",\"dominant-baseline\":1,\"drop-initial-after-adjust\":\"central | middle | after-edge | text-after-edge | ideographic | alphabetic | mathematical | <percentage> | <length>\",\"drop-initial-after-align\":\"baseline | use-script | before-edge | text-before-edge | after-edge | text-after-edge | central | middle | ideographic | alphabetic | hanging | mathematical\",\"drop-initial-before-adjust\":\"before-edge | text-before-edge | central | middle | hanging | mathematical | <percentage> | <length>\",\"drop-initial-before-align\":\"caps-height | baseline | use-script | before-edge | text-before-edge | after-edge | text-after-edge | central | middle | ideographic | alphabetic | hanging | mathematical\",\"drop-initial-size\":\"auto | line | <length> | <percentage>\",\"drop-initial-value\":\"initial | <integer>\",elevation:\"<angle> | below | level | above | higher | lower | inherit\",\"empty-cells\":\"show | hide | inherit\",filter:1,fit:\"fill | hidden | meet | slice\",\"fit-position\":1,flex:\"<flex>\",\"flex-basis\":\"<width>\",\"flex-direction\":\"row | row-reverse | column | column-reverse\",\"flex-flow\":\"<flex-direction> || <flex-wrap>\",\"flex-grow\":\"<number>\",\"flex-shrink\":\"<number>\",\"flex-wrap\":\"nowrap | wrap | wrap-reverse\",\"-webkit-flex\":\"<flex>\",\"-webkit-flex-basis\":\"<width>\",\"-webkit-flex-direction\":\"row | row-reverse | column | column-reverse\",\"-webkit-flex-flow\":\"<flex-direction> || <flex-wrap>\",\"-webkit-flex-grow\":\"<number>\",\"-webkit-flex-shrink\":\"<number>\",\"-webkit-flex-wrap\":\"nowrap | wrap | wrap-reverse\",\"-ms-flex\":\"<flex>\",\"-ms-flex-align\":\"start | end | center | stretch | baseline\",\"-ms-flex-direction\":\"row | row-reverse | column | column-reverse | inherit\",\"-ms-flex-order\":\"<number>\",\"-ms-flex-pack\":\"start | end | center | justify\",\"-ms-flex-wrap\":\"nowrap | wrap | wrap-reverse\",\"float\":\"left | right | none | inherit\",\"float-offset\":1,font:1,\"font-family\":1,\"font-size\":\"<absolute-size> | <relative-size> | <length> | <percentage> | inherit\",\"font-size-adjust\":\"<number> | none | inherit\",\"font-stretch\":\"normal | ultra-condensed | extra-condensed | condensed | semi-condensed | semi-expanded | expanded | extra-expanded | ultra-expanded | inherit\",\"font-style\":\"normal | italic | oblique | inherit\",\"font-variant\":\"normal | small-caps | inherit\",\"font-weight\":\"normal | bold | bolder | lighter | 100 | 200 | 300 | 400 | 500 | 600 | 700 | 800 | 900 | inherit\",\"grid-cell-stacking\":\"columns | rows | layer\",\"grid-column\":1,\"grid-columns\":1,\"grid-column-align\":\"start | end | center | stretch\",\"grid-column-sizing\":1,\"grid-column-span\":\"<integer>\",\"grid-flow\":\"none | rows | columns\",\"grid-layer\":\"<integer>\",\"grid-row\":1,\"grid-rows\":1,\"grid-row-align\":\"start | end | center | stretch\",\"grid-row-span\":\"<integer>\",\"grid-row-sizing\":1,\"hanging-punctuation\":1,height:\"<margin-width> | <content-sizing> | inherit\",\"hyphenate-after\":\"<integer> | auto\",\"hyphenate-before\":\"<integer> | auto\",\"hyphenate-character\":\"<string> | auto\",\"hyphenate-lines\":\"no-limit | <integer>\",\"hyphenate-resource\":1,hyphens:\"none | manual | auto\",icon:1,\"image-orientation\":\"angle | auto\",\"image-rendering\":1,\"image-resolution\":1,\"inline-box-align\":\"initial | last | <integer>\",\"justify-content\":\"flex-start | flex-end | center | space-between | space-around\",\"-webkit-justify-content\":\"flex-start | flex-end | center | space-between | space-around\",left:\"<margin-width> | inherit\",\"letter-spacing\":\"<length> | normal | inherit\",\"line-height\":\"<number> | <length> | <percentage> | normal | inherit\",\"line-break\":\"auto | loose | normal | strict\",\"line-stacking\":1,\"line-stacking-ruby\":\"exclude-ruby | include-ruby\",\"line-stacking-shift\":\"consider-shifts | disregard-shifts\",\"line-stacking-strategy\":\"inline-line-height | block-line-height | max-height | grid-height\",\"list-style\":1,\"list-style-image\":\"<uri> | none | inherit\",\"list-style-position\":\"inside | outside | inherit\",\"list-style-type\":\"disc | circle | square | decimal | decimal-leading-zero | lower-roman | upper-roman | lower-greek | lower-latin | upper-latin | armenian | georgian | lower-alpha | upper-alpha | none | inherit\",margin:{multi:\"<margin-width> | inherit\",max:4},\"margin-bottom\":\"<margin-width> | inherit\",\"margin-left\":\"<margin-width> | inherit\",\"margin-right\":\"<margin-width> | inherit\",\"margin-top\":\"<margin-width> | inherit\",mark:1,\"mark-after\":1,\"mark-before\":1,marks:1,\"marquee-direction\":1,\"marquee-play-count\":1,\"marquee-speed\":1,\"marquee-style\":1,\"max-height\":\"<length> | <percentage> | <content-sizing> | none | inherit\",\"max-width\":\"<length> | <percentage> | <content-sizing> | none | inherit\",\"min-height\":\"<length> | <percentage> | <content-sizing> | contain-floats | -moz-contain-floats | -webkit-contain-floats | inherit\",\"min-width\":\"<length> | <percentage> | <content-sizing> | contain-floats | -moz-contain-floats | -webkit-contain-floats | inherit\",\"move-to\":1,\"nav-down\":1,\"nav-index\":1,\"nav-left\":1,\"nav-right\":1,\"nav-up\":1,opacity:\"<number> | inherit\",order:\"<integer>\",\"-webkit-order\":\"<integer>\",orphans:\"<integer> | inherit\",outline:1,\"outline-color\":\"<color> | invert | inherit\",\"outline-offset\":1,\"outline-style\":\"<border-style> | inherit\",\"outline-width\":\"<border-width> | inherit\",overflow:\"visible | hidden | scroll | auto | inherit\",\"overflow-style\":1,\"overflow-wrap\":\"normal | break-word\",\"overflow-x\":1,\"overflow-y\":1,padding:{multi:\"<padding-width> | inherit\",max:4},\"padding-bottom\":\"<padding-width> | inherit\",\"padding-left\":\"<padding-width> | inherit\",\"padding-right\":\"<padding-width> | inherit\",\"padding-top\":\"<padding-width> | inherit\",page:1,\"page-break-after\":\"auto | always | avoid | left | right | inherit\",\"page-break-before\":\"auto | always | avoid | left | right | inherit\",\"page-break-inside\":\"auto | avoid | inherit\",\"page-policy\":1,pause:1,\"pause-after\":1,\"pause-before\":1,perspective:1,\"perspective-origin\":1,phonemes:1,pitch:1,\"pitch-range\":1,\"play-during\":1,\"pointer-events\":\"auto | none | visiblePainted | visibleFill | visibleStroke | visible | painted | fill | stroke | all | inherit\",position:\"static | relative | absolute | fixed | inherit\",\"presentation-level\":1,\"punctuation-trim\":1,quotes:1,\"rendering-intent\":1,resize:1,rest:1,\"rest-after\":1,\"rest-before\":1,richness:1,right:\"<margin-width> | inherit\",rotation:1,\"rotation-point\":1,\"ruby-align\":1,\"ruby-overhang\":1,\"ruby-position\":1,\"ruby-span\":1,size:1,speak:\"normal | none | spell-out | inherit\",\"speak-header\":\"once | always | inherit\",\"speak-numeral\":\"digits | continuous | inherit\",\"speak-punctuation\":\"code | none | inherit\",\"speech-rate\":1,src:1,stress:1,\"string-set\":1,\"table-layout\":\"auto | fixed | inherit\",\"tab-size\":\"<integer> | <length>\",target:1,\"target-name\":1,\"target-new\":1,\"target-position\":1,\"text-align\":\"left | right | center | justify | inherit\",\"text-align-last\":1,\"text-decoration\":1,\"text-emphasis\":1,\"text-height\":1,\"text-indent\":\"<length> | <percentage> | inherit\",\"text-justify\":\"auto | none | inter-word | inter-ideograph | inter-cluster | distribute | kashida\",\"text-outline\":1,\"text-overflow\":1,\"text-rendering\":\"auto | optimizeSpeed | optimizeLegibility | geometricPrecision | inherit\",\"text-shadow\":1,\"text-transform\":\"capitalize | uppercase | lowercase | none | inherit\",\"text-wrap\":\"normal | none | avoid\",top:\"<margin-width> | inherit\",\"-ms-touch-action\":\"auto | none | pan-x | pan-y\",\"touch-action\":\"auto | none | pan-x | pan-y\",transform:1,\"transform-origin\":1,\"transform-style\":1,transition:1,\"transition-delay\":1,\"transition-duration\":1,\"transition-property\":1,\"transition-timing-function\":1,\"unicode-bidi\":\"normal | embed | isolate | bidi-override | isolate-override | plaintext | inherit\",\"user-modify\":\"read-only | read-write | write-only | inherit\",\"user-select\":\"none | text | toggle | element | elements | all | inherit\",\"vertical-align\":\"auto | use-script | baseline | sub | super | top | text-top | central | middle | bottom | text-bottom | <percentage> | <length>\",visibility:\"visible | hidden | collapse | inherit\",\"voice-balance\":1,\"voice-duration\":1,\"voice-family\":1,\"voice-pitch\":1,\"voice-pitch-range\":1,\"voice-rate\":1,\"voice-stress\":1,\"voice-volume\":1,volume:1,\"white-space\":\"normal | pre | nowrap | pre-wrap | pre-line | inherit | -pre-wrap | -o-pre-wrap | -moz-pre-wrap | -hp-pre-wrap\",\"white-space-collapse\":1,widows:\"<integer> | inherit\",width:\"<length> | <percentage> | <content-sizing> | auto | inherit\",\"word-break\":\"normal | keep-all | break-all\",\"word-spacing\":\"<length> | normal | inherit\",\"word-wrap\":\"normal | break-word\",\"writing-mode\":\"horizontal-tb | vertical-rl | vertical-lr | lr-tb | rl-tb | tb-rl | bt-rl | tb-lr | bt-lr | lr-bt | rl-bt | lr | rl | tb | inherit\",\"z-index\":\"<integer> | auto | inherit\",zoom:\"<number> | <percentage> | normal\"};PropertyName.prototype=new SyntaxUnit,PropertyName.prototype.constructor=PropertyName,PropertyName.prototype.toString=function(){return(this.hack?this.hack:\"\")+this.text},PropertyValue.prototype=new SyntaxUnit,PropertyValue.prototype.constructor=PropertyValue,PropertyValueIterator.prototype.count=function(){return this._parts.length},PropertyValueIterator.prototype.isFirst=function(){return this._i===0},PropertyValueIterator.prototype.hasNext=function(){return this._i<this._parts.length},PropertyValueIterator.prototype.mark=function(){this._marks.push(this._i)},PropertyValueIterator.prototype.peek=function(e){return this.hasNext()?this._parts[this._i+(e||0)]:null},PropertyValueIterator.prototype.next=function(){return this.hasNext()?this._parts[this._i++]:null},PropertyValueIterator.prototype.previous=function(){return this._i>0?this._parts[--this._i]:null},PropertyValueIterator.prototype.restore=function(){this._marks.length&&(this._i=this._marks.pop())},PropertyValuePart.prototype=new SyntaxUnit,PropertyValuePart.prototype.constructor=PropertyValuePart,PropertyValuePart.fromToken=function(e){return new PropertyValuePart(e.value,e.startLine,e.startCol)};var Pseudos={\":first-letter\":1,\":first-line\":1,\":before\":1,\":after\":1};Pseudos.ELEMENT=1,Pseudos.CLASS=2,Pseudos.isElement=function(e){return e.indexOf(\"::\")===0||Pseudos[e.toLowerCase()]==Pseudos.ELEMENT},Selector.prototype=new SyntaxUnit,Selector.prototype.constructor=Selector,SelectorPart.prototype=new SyntaxUnit,SelectorPart.prototype.constructor=SelectorPart,SelectorSubPart.prototype=new SyntaxUnit,SelectorSubPart.prototype.constructor=SelectorSubPart,Specificity.prototype={constructor:Specificity,compare:function(e){var t=[\"a\",\"b\",\"c\",\"d\"],n,r;for(n=0,r=t.length;n<r;n++){if(this[t[n]]<e[t[n]])return-1;if(this[t[n]]>e[t[n]])return 1}return 0},valueOf:function(){return this.a*1e3+this.b*100+this.c*10+this.d},toString:function(){return this.a+\",\"+this.b+\",\"+this.c+\",\"+this.d}},Specificity.calculate=function(e){function u(e){var t,n,r,a,f=e.elementName?e.elementName.text:\"\",l;f&&f.charAt(f.length-1)!=\"*\"&&o++;for(t=0,r=e.modifiers.length;t<r;t++){l=e.modifiers[t];switch(l.type){case\"class\":case\"attribute\":s++;break;case\"id\":i++;break;case\"pseudo\":Pseudos.isElement(l.text)?o++:s++;break;case\"not\":for(n=0,a=l.args.length;n<a;n++)u(l.args[n])}}}var t,n,r,i=0,s=0,o=0;for(t=0,n=e.parts.length;t<n;t++)r=e.parts[t],r instanceof SelectorPart&&u(r);return new Specificity(0,i,s,o)};var h=/^[0-9a-fA-F]$/,nonascii=/^[\\u0080-\\uFFFF]$/,nl=/\\n|\\r\\n|\\r|\\f/;TokenStream.prototype=mix(new TokenStreamBase,{_getToken:function(e){var t,n=this._reader,r=null,i=n.getLine(),s=n.getCol();t=n.read();while(t){switch(t){case\"/\":n.peek()==\"*\"?r=this.commentToken(t,i,s):r=this.charToken(t,i,s);break;case\"|\":case\"~\":case\"^\":case\"$\":case\"*\":n.peek()==\"=\"?r=this.comparisonToken(t,i,s):r=this.charToken(t,i,s);break;case'\"':case\"'\":r=this.stringToken(t,i,s);break;case\"#\":isNameChar(n.peek())?r=this.hashToken(t,i,s):r=this.charToken(t,i,s);break;case\".\":isDigit(n.peek())?r=this.numberToken(t,i,s):r=this.charToken(t,i,s);break;case\"-\":n.peek()==\"-\"?r=this.htmlCommentEndToken(t,i,s):isNameStart(n.peek())?r=this.identOrFunctionToken(t,i,s):r=this.charToken(t,i,s);break;case\"!\":r=this.importantToken(t,i,s);break;case\"@\":r=this.atRuleToken(t,i,s);break;case\":\":r=this.notToken(t,i,s);break;case\"<\":r=this.htmlCommentStartToken(t,i,s);break;case\"U\":case\"u\":if(n.peek()==\"+\"){r=this.unicodeRangeToken(t,i,s);break};default:isDigit(t)?r=this.numberToken(t,i,s):isWhitespace(t)?r=this.whitespaceToken(t,i,s):isIdentStart(t)?r=this.identOrFunctionToken(t,i,s):r=this.charToken(t,i,s)}break}return!r&&t===null&&(r=this.createToken(Tokens.EOF,null,i,s)),r},createToken:function(e,t,n,r,i){var s=this._reader;return i=i||{},{value:t,type:e,channel:i.channel,endChar:i.endChar,hide:i.hide||!1,startLine:n,startCol:r,endLine:s.getLine(),endCol:s.getCol()}},atRuleToken:function(e,t,n){var r=e,i=this._reader,s=Tokens.CHAR,o=!1,u,a;i.mark(),u=this.readName(),r=e+u,s=Tokens.type(r.toLowerCase());if(s==Tokens.CHAR||s==Tokens.UNKNOWN)r.length>1?s=Tokens.UNKNOWN_SYM:(s=Tokens.CHAR,r=e,i.reset());return this.createToken(s,r,t,n)},charToken:function(e,t,n){var r=Tokens.type(e),i={};return r==-1?r=Tokens.CHAR:i.endChar=Tokens[r].endChar,this.createToken(r,e,t,n,i)},commentToken:function(e,t,n){var r=this._reader,i=this.readComment(e);return this.createToken(Tokens.COMMENT,i,t,n)},comparisonToken:function(e,t,n){var r=this._reader,i=e+r.read(),s=Tokens.type(i)||Tokens.CHAR;return this.createToken(s,i,t,n)},hashToken:function(e,t,n){var r=this._reader,i=this.readName(e);return this.createToken(Tokens.HASH,i,t,n)},htmlCommentStartToken:function(e,t,n){var r=this._reader,i=e;return r.mark(),i+=r.readCount(3),i==\"<!--\"?this.createToken(Tokens.CDO,i,t,n):(r.reset(),this.charToken(e,t,n))},htmlCommentEndToken:function(e,t,n){var r=this._reader,i=e;return r.mark(),i+=r.readCount(2),i==\"-->\"?this.createToken(Tokens.CDC,i,t,n):(r.reset(),this.charToken(e,t,n))},identOrFunctionToken:function(e,t,n){var r=this._reader,i=this.readName(e),s=Tokens.IDENT;return r.peek()==\"(\"?(i+=r.read(),i.toLowerCase()==\"url(\"?(s=Tokens.URI,i=this.readURI(i),i.toLowerCase()==\"url(\"&&(s=Tokens.FUNCTION)):s=Tokens.FUNCTION):r.peek()==\":\"&&i.toLowerCase()==\"progid\"&&(i+=r.readTo(\"(\"),s=Tokens.IE_FUNCTION),this.createToken(s,i,t,n)},importantToken:function(e,t,n){var r=this._reader,i=e,s=Tokens.CHAR,o,u;r.mark(),u=r.read();while(u){if(u==\"/\"){if(r.peek()!=\"*\")break;o=this.readComment(u);if(o===\"\")break}else{if(!isWhitespace(u)){if(/i/i.test(u)){o=r.readCount(8),/mportant/i.test(o)&&(i+=u+o,s=Tokens.IMPORTANT_SYM);break}break}i+=u+this.readWhitespace()}u=r.read()}return s==Tokens.CHAR?(r.reset(),this.charToken(e,t,n)):this.createToken(s,i,t,n)},notToken:function(e,t,n){var r=this._reader,i=e;return r.mark(),i+=r.readCount(4),i.toLowerCase()==\":not(\"?this.createToken(Tokens.NOT,i,t,n):(r.reset(),this.charToken(e,t,n))},numberToken:function(e,t,n){var r=this._reader,i=this.readNumber(e),s,o=Tokens.NUMBER,u=r.peek();return isIdentStart(u)?(s=this.readName(r.read()),i+=s,/^em$|^ex$|^px$|^gd$|^rem$|^vw$|^vh$|^vmax$|^vmin$|^ch$|^cm$|^mm$|^in$|^pt$|^pc$/i.test(s)?o=Tokens.LENGTH:/^deg|^rad$|^grad$/i.test(s)?o=Tokens.ANGLE:/^ms$|^s$/i.test(s)?o=Tokens.TIME:/^hz$|^khz$/i.test(s)?o=Tokens.FREQ:/^dpi$|^dpcm$/i.test(s)?o=Tokens.RESOLUTION:o=Tokens.DIMENSION):u==\"%\"&&(i+=r.read(),o=Tokens.PERCENTAGE),this.createToken(o,i,t,n)},stringToken:function(e,t,n){var r=e,i=e,s=this._reader,o=e,u=Tokens.STRING,a=s.read();while(a){i+=a;if(a==r&&o!=\"\\\\\")break;if(isNewLine(s.peek())&&a!=\"\\\\\"){u=Tokens.INVALID;break}o=a,a=s.read()}return a===null&&(u=Tokens.INVALID),this.createToken(u,i,t,n)},unicodeRangeToken:function(e,t,n){var r=this._reader,i=e,s,o=Tokens.CHAR;return r.peek()==\"+\"&&(r.mark(),i+=r.read(),i+=this.readUnicodeRangePart(!0),i.length==2?r.reset():(o=Tokens.UNICODE_RANGE,i.indexOf(\"?\")==-1&&r.peek()==\"-\"&&(r.mark(),s=r.read(),s+=this.readUnicodeRangePart(!1),s.length==1?r.reset():i+=s))),this.createToken(o,i,t,n)},whitespaceToken:function(e,t,n){var r=this._reader,i=e+this.readWhitespace();return this.createToken(Tokens.S,i,t,n)},readUnicodeRangePart:function(e){var t=this._reader,n=\"\",r=t.peek();while(isHexDigit(r)&&n.length<6)t.read(),n+=r,r=t.peek();if(e)while(r==\"?\"&&n.length<6)t.read(),n+=r,r=t.peek();return n},readWhitespace:function(){var e=this._reader,t=\"\",n=e.peek();while(isWhitespace(n))e.read(),t+=n,n=e.peek();return t},readNumber:function(e){var t=this._reader,n=e,r=e==\".\",i=t.peek();while(i){if(isDigit(i))n+=t.read();else{if(i!=\".\")break;if(r)break;r=!0,n+=t.read()}i=t.peek()}return n},readString:function(){var e=this._reader,t=e.read(),n=t,r=t,i=e.peek();while(i){i=e.read(),n+=i;if(i==t&&r!=\"\\\\\")break;if(isNewLine(e.peek())&&i!=\"\\\\\"){n=\"\";break}r=i,i=e.peek()}return i===null&&(n=\"\"),n},readURI:function(e){var t=this._reader,n=e,r=\"\",i=t.peek();t.mark();while(i&&isWhitespace(i))t.read(),i=t.peek();i==\"'\"||i=='\"'?r=this.readString():r=this.readURL(),i=t.peek();while(i&&isWhitespace(i))t.read(),i=t.peek();return r===\"\"||i!=\")\"?(n=e,t.reset()):n+=r+t.read(),n},readURL:function(){var e=this._reader,t=\"\",n=e.peek();while(/^[!#$%&\\\\*-~]$/.test(n))t+=e.read(),n=e.peek();return t},readName:function(e){var t=this._reader,n=e||\"\",r=t.peek();for(;;)if(r==\"\\\\\")n+=this.readEscape(t.read()),r=t.peek();else{if(!r||!isNameChar(r))break;n+=t.read(),r=t.peek()}return n},readEscape:function(e){var t=this._reader,n=e||\"\",r=0,i=t.peek();if(isHexDigit(i))do n+=t.read(),i=t.peek();while(i&&isHexDigit(i)&&++r<6);return n.length==3&&/\\s/.test(i)||n.length==7||n.length==1?t.read():i=\"\",n+i},readComment:function(e){var t=this._reader,n=e||\"\",r=t.read();if(r==\"*\"){while(r){n+=r;if(n.length>2&&r==\"*\"&&t.peek()==\"/\"){n+=t.read();break}r=t.read()}return n}return\"\"}});var Tokens=[{name:\"CDO\"},{name:\"CDC\"},{name:\"S\",whitespace:!0},{name:\"COMMENT\",comment:!0,hide:!0,channel:\"comment\"},{name:\"INCLUDES\",text:\"~=\"},{name:\"DASHMATCH\",text:\"|=\"},{name:\"PREFIXMATCH\",text:\"^=\"},{name:\"SUFFIXMATCH\",text:\"$=\"},{name:\"SUBSTRINGMATCH\",text:\"*=\"},{name:\"STRING\"},{name:\"IDENT\"},{name:\"HASH\"},{name:\"IMPORT_SYM\",text:\"@import\"},{name:\"PAGE_SYM\",text:\"@page\"},{name:\"MEDIA_SYM\",text:\"@media\"},{name:\"FONT_FACE_SYM\",text:\"@font-face\"},{name:\"CHARSET_SYM\",text:\"@charset\"},{name:\"NAMESPACE_SYM\",text:\"@namespace\"},{name:\"VIEWPORT_SYM\",text:[\"@viewport\",\"@-ms-viewport\"]},{name:\"UNKNOWN_SYM\"},{name:\"KEYFRAMES_SYM\",text:[\"@keyframes\",\"@-webkit-keyframes\",\"@-moz-keyframes\",\"@-o-keyframes\"]},{name:\"IMPORTANT_SYM\"},{name:\"LENGTH\"},{name:\"ANGLE\"},{name:\"TIME\"},{name:\"FREQ\"},{name:\"DIMENSION\"},{name:\"PERCENTAGE\"},{name:\"NUMBER\"},{name:\"URI\"},{name:\"FUNCTION\"},{name:\"UNICODE_RANGE\"},{name:\"INVALID\"},{name:\"PLUS\",text:\"+\"},{name:\"GREATER\",text:\">\"},{name:\"COMMA\",text:\",\"},{name:\"TILDE\",text:\"~\"},{name:\"NOT\"},{name:\"TOPLEFTCORNER_SYM\",text:\"@top-left-corner\"},{name:\"TOPLEFT_SYM\",text:\"@top-left\"},{name:\"TOPCENTER_SYM\",text:\"@top-center\"},{name:\"TOPRIGHT_SYM\",text:\"@top-right\"},{name:\"TOPRIGHTCORNER_SYM\",text:\"@top-right-corner\"},{name:\"BOTTOMLEFTCORNER_SYM\",text:\"@bottom-left-corner\"},{name:\"BOTTOMLEFT_SYM\",text:\"@bottom-left\"},{name:\"BOTTOMCENTER_SYM\",text:\"@bottom-center\"},{name:\"BOTTOMRIGHT_SYM\",text:\"@bottom-right\"},{name:\"BOTTOMRIGHTCORNER_SYM\",text:\"@bottom-right-corner\"},{name:\"LEFTTOP_SYM\",text:\"@left-top\"},{name:\"LEFTMIDDLE_SYM\",text:\"@left-middle\"},{name:\"LEFTBOTTOM_SYM\",text:\"@left-bottom\"},{name:\"RIGHTTOP_SYM\",text:\"@right-top\"},{name:\"RIGHTMIDDLE_SYM\",text:\"@right-middle\"},{name:\"RIGHTBOTTOM_SYM\",text:\"@right-bottom\"},{name:\"RESOLUTION\",state:\"media\"},{name:\"IE_FUNCTION\"},{name:\"CHAR\"},{name:\"PIPE\",text:\"|\"},{name:\"SLASH\",text:\"/\"},{name:\"MINUS\",text:\"-\"},{name:\"STAR\",text:\"*\"},{name:\"LBRACE\",endChar:\"}\",text:\"{\"},{name:\"RBRACE\",text:\"}\"},{name:\"LBRACKET\",endChar:\"]\",text:\"[\"},{name:\"RBRACKET\",text:\"]\"},{name:\"EQUALS\",text:\"=\"},{name:\"COLON\",text:\":\"},{name:\"SEMICOLON\",text:\";\"},{name:\"LPAREN\",endChar:\")\",text:\"(\"},{name:\"RPAREN\",text:\")\"},{name:\"DOT\",text:\".\"}];(function(){var e=[],t={};Tokens.UNKNOWN=-1,Tokens.unshift({name:\"EOF\"});for(var n=0,r=Tokens.length;n<r;n++){e.push(Tokens[n].name),Tokens[Tokens[n].name]=n;if(Tokens[n].text)if(Tokens[n].text instanceof Array)for(var i=0;i<Tokens[n].text.length;i++)t[Tokens[n].text[i]]=n;else t[Tokens[n].text]=n}Tokens.name=function(t){return e[t]},Tokens.type=function(e){return t[e]||-1}})();var Validation={validate:function(e,t){var n=e.toString().toLowerCase(),r=t.parts,i=new PropertyValueIterator(t),s=Properties[n],o,u,a,f,l,c,h,p,d,v,m;if(!s){if(n.indexOf(\"-\")!==0)throw new ValidationError(\"Unknown property '\"+e+\"'.\",e.line,e.col)}else typeof s!=\"number\"&&(typeof s==\"string\"?s.indexOf(\"||\")>-1?this.groupProperty(s,i):this.singleProperty(s,i,1):s.multi?this.multiProperty(s.multi,i,s.comma,s.max||Infinity):typeof s==\"function\"&&s(i))},singleProperty:function(e,t,n,r){var i=!1,s=t.value,o=0,u;while(t.hasNext()&&o<n){i=ValidationTypes.isAny(t,e);if(!i)break;o++}if(!i)throw t.hasNext()&&!t.isFirst()?(u=t.peek(),new ValidationError(\"Expected end of value but found '\"+u+\"'.\",u.line,u.col)):new ValidationError(\"Expected (\"+e+\") but found '\"+s+\"'.\",s.line,s.col);if(t.hasNext())throw u=t.next(),new ValidationError(\"Expected end of value but found '\"+u+\"'.\",u.line,u.col)},multiProperty:function(e,t,n,r){var i=!1,s=t.value,o=0,u=!1,a;while(t.hasNext()&&!i&&o<r){if(!ValidationTypes.isAny(t,e))break;o++;if(!t.hasNext())i=!0;else if(n){if(t.peek()!=\",\")break;a=t.next()}}if(!i)throw t.hasNext()&&!t.isFirst()?(a=t.peek(),new ValidationError(\"Expected end of value but found '\"+a+\"'.\",a.line,a.col)):(a=t.previous(),n&&a==\",\"?new ValidationError(\"Expected end of value but found '\"+a+\"'.\",a.line,a.col):new ValidationError(\"Expected (\"+e+\") but found '\"+s+\"'.\",s.line,s.col));if(t.hasNext())throw a=t.next(),new ValidationError(\"Expected end of value but found '\"+a+\"'.\",a.line,a.col)},groupProperty:function(e,t,n){var r=!1,i=t.value,s=e.split(\"||\").length,o={count:0},u=!1,a,f;while(t.hasNext()&&!r){a=ValidationTypes.isAnyOfGroup(t,e);if(!a)break;if(o[a])break;o[a]=1,o.count++,u=!0;if(o.count==s||!t.hasNext())r=!0}if(!r)throw u&&t.hasNext()?(f=t.peek(),new ValidationError(\"Expected end of value but found '\"+f+\"'.\",f.line,f.col)):new ValidationError(\"Expected (\"+e+\") but found '\"+i+\"'.\",i.line,i.col);if(t.hasNext())throw f=t.next(),new ValidationError(\"Expected end of value but found '\"+f+\"'.\",f.line,f.col)}};ValidationError.prototype=new Error;var ValidationTypes={isLiteral:function(e,t){var n=e.text.toString().toLowerCase(),r=t.split(\" | \"),i,s,o=!1;for(i=0,s=r.length;i<s&&!o;i++)n==r[i].toLowerCase()&&(o=!0);return o},isSimple:function(e){return!!this.simple[e]},isComplex:function(e){return!!this.complex[e]},isAny:function(e,t){var n=t.split(\" | \"),r,i,s=!1;for(r=0,i=n.length;r<i&&!s&&e.hasNext();r++)s=this.isType(e,n[r]);return s},isAnyOfGroup:function(e,t){var n=t.split(\" || \"),r,i,s=!1;for(r=0,i=n.length;r<i&&!s;r++)s=this.isType(e,n[r]);return s?n[r-1]:!1},isType:function(e,t){var n=e.peek(),r=!1;return t.charAt(0)!=\"<\"?(r=this.isLiteral(n,t),r&&e.next()):this.simple[t]?(r=this.simple[t](n),r&&e.next()):r=this.complex[t](e),r},simple:{\"<absolute-size>\":function(e){return ValidationTypes.isLiteral(e,\"xx-small | x-small | small | medium | large | x-large | xx-large\")},\"<attachment>\":function(e){return ValidationTypes.isLiteral(e,\"scroll | fixed | local\")},\"<attr>\":function(e){return e.type==\"function\"&&e.name==\"attr\"},\"<bg-image>\":function(e){return this[\"<image>\"](e)||this[\"<gradient>\"](e)||e==\"none\"},\"<gradient>\":function(e){return e.type==\"function\"&&/^(?:\\-(?:ms|moz|o|webkit)\\-)?(?:repeating\\-)?(?:radial\\-|linear\\-)?gradient/i.test(e)},\"<box>\":function(e){return ValidationTypes.isLiteral(e,\"padding-box | border-box | content-box\")},\"<content>\":function(e){return e.type==\"function\"&&e.name==\"content\"},\"<relative-size>\":function(e){return ValidationTypes.isLiteral(e,\"smaller | larger\")},\"<ident>\":function(e){return e.type==\"identifier\"},\"<length>\":function(e){return e.type==\"function\"&&/^(?:\\-(?:ms|moz|o|webkit)\\-)?calc/i.test(e)?!0:e.type==\"length\"||e.type==\"number\"||e.type==\"integer\"||e==\"0\"},\"<color>\":function(e){return e.type==\"color\"||e==\"transparent\"},\"<number>\":function(e){return e.type==\"number\"||this[\"<integer>\"](e)},\"<integer>\":function(e){return e.type==\"integer\"},\"<line>\":function(e){return e.type==\"integer\"},\"<angle>\":function(e){return e.type==\"angle\"},\"<uri>\":function(e){return e.type==\"uri\"},\"<image>\":function(e){return this[\"<uri>\"](e)},\"<percentage>\":function(e){return e.type==\"percentage\"||e==\"0\"},\"<border-width>\":function(e){return this[\"<length>\"](e)||ValidationTypes.isLiteral(e,\"thin | medium | thick\")},\"<border-style>\":function(e){return ValidationTypes.isLiteral(e,\"none | hidden | dotted | dashed | solid | double | groove | ridge | inset | outset\")},\"<content-sizing>\":function(e){return ValidationTypes.isLiteral(e,\"fill-available | -moz-available | -webkit-fill-available | max-content | -moz-max-content | -webkit-max-content | min-content | -moz-min-content | -webkit-min-content | fit-content | -moz-fit-content | -webkit-fit-content\")},\"<margin-width>\":function(e){return this[\"<length>\"](e)||this[\"<percentage>\"](e)||ValidationTypes.isLiteral(e,\"auto\")},\"<padding-width>\":function(e){return this[\"<length>\"](e)||this[\"<percentage>\"](e)},\"<shape>\":function(e){return e.type==\"function\"&&(e.name==\"rect\"||e.name==\"inset-rect\")},\"<time>\":function(e){return e.type==\"time\"},\"<flex-grow>\":function(e){return this[\"<number>\"](e)},\"<flex-shrink>\":function(e){return this[\"<number>\"](e)},\"<width>\":function(e){return this[\"<margin-width>\"](e)},\"<flex-basis>\":function(e){return this[\"<width>\"](e)},\"<flex-direction>\":function(e){return ValidationTypes.isLiteral(e,\"row | row-reverse | column | column-reverse\")},\"<flex-wrap>\":function(e){return ValidationTypes.isLiteral(e,\"nowrap | wrap | wrap-reverse\")}},complex:{\"<bg-position>\":function(e){var t=this,n=!1,r=\"<percentage> | <length>\",i=\"left | right\",s=\"top | bottom\",o=0,u=function(){return e.hasNext()&&e.peek()!=\",\"};while(e.peek(o)&&e.peek(o)!=\",\")o++;return o<3?ValidationTypes.isAny(e,i+\" | center | \"+r)?(n=!0,ValidationTypes.isAny(e,s+\" | center | \"+r)):ValidationTypes.isAny(e,s)&&(n=!0,ValidationTypes.isAny(e,i+\" | center\")):ValidationTypes.isAny(e,i)?ValidationTypes.isAny(e,s)?(n=!0,ValidationTypes.isAny(e,r)):ValidationTypes.isAny(e,r)&&(ValidationTypes.isAny(e,s)?(n=!0,ValidationTypes.isAny(e,r)):ValidationTypes.isAny(e,\"center\")&&(n=!0)):ValidationTypes.isAny(e,s)?ValidationTypes.isAny(e,i)?(n=!0,ValidationTypes.isAny(e,r)):ValidationTypes.isAny(e,r)&&(ValidationTypes.isAny(e,i)?(n=!0,ValidationTypes.isAny(e,r)):ValidationTypes.isAny(e,\"center\")&&(n=!0)):ValidationTypes.isAny(e,\"center\")&&ValidationTypes.isAny(e,i+\" | \"+s)&&(n=!0,ValidationTypes.isAny(e,r)),n},\"<bg-size>\":function(e){var t=this,n=!1,r=\"<percentage> | <length> | auto\",i,s,o;return ValidationTypes.isAny(e,\"cover | contain\")?n=!0:ValidationTypes.isAny(e,r)&&(n=!0,ValidationTypes.isAny(e,r)),n},\"<repeat-style>\":function(e){var t=!1,n=\"repeat | space | round | no-repeat\",r;return e.hasNext()&&(r=e.next(),ValidationTypes.isLiteral(r,\"repeat-x | repeat-y\")?t=!0:ValidationTypes.isLiteral(r,n)&&(t=!0,e.hasNext()&&ValidationTypes.isLiteral(e.peek(),n)&&e.next())),t},\"<shadow>\":function(e){var t=!1,n=0,r=!1,i=!1,s;if(e.hasNext()){ValidationTypes.isAny(e,\"inset\")&&(r=!0),ValidationTypes.isAny(e,\"<color>\")&&(i=!0);while(ValidationTypes.isAny(e,\"<length>\")&&n<4)n++;e.hasNext()&&(i||ValidationTypes.isAny(e,\"<color>\"),r||ValidationTypes.isAny(e,\"inset\")),t=n>=2&&n<=4}return t},\"<x-one-radius>\":function(e){var t=!1,n=\"<length> | <percentage> | inherit\";return ValidationTypes.isAny(e,n)&&(t=!0,ValidationTypes.isAny(e,n)),t},\"<flex>\":function(e){var t,n=!1;ValidationTypes.isAny(e,\"none | inherit\")?n=!0:ValidationTypes.isType(e,\"<flex-grow>\")?e.peek()?ValidationTypes.isType(e,\"<flex-shrink>\")?e.peek()?n=ValidationTypes.isType(e,\"<flex-basis>\"):n=!0:ValidationTypes.isType(e,\"<flex-basis>\")&&(n=e.peek()===null):n=!0:ValidationTypes.isType(e,\"<flex-basis>\")&&(n=!0);if(!n)throw t=e.peek(),new ValidationError(\"Expected (none | [ <flex-grow> <flex-shrink>? || <flex-basis> ]) but found '\"+e.value.text+\"'.\",t.line,t.col);return n}}};parserlib.css={Colors:Colors,Combinator:Combinator,Parser:Parser,PropertyName:PropertyName,PropertyValue:PropertyValue,PropertyValuePart:PropertyValuePart,MediaFeature:MediaFeature,MediaQuery:MediaQuery,Selector:Selector,SelectorPart:SelectorPart,SelectorSubPart:SelectorSubPart,Specificity:Specificity,TokenStream:TokenStream,Tokens:Tokens,ValidationError:ValidationError}}(),function(){for(var e in parserlib)exports[e]=parserlib[e]}();var util={isArray:function(e){return Array.isArray(e)||typeof e==\"object\"&&objectToString(e)===\"[object Array]\"},isDate:function(e){return typeof e==\"object\"&&objectToString(e)===\"[object Date]\"},isRegExp:function(e){return typeof e==\"object\"&&objectToString(e)===\"[object RegExp]\"},getRegExpFlags:function(e){var t=\"\";return e.global&&(t+=\"g\"),e.ignoreCase&&(t+=\"i\"),e.multiline&&(t+=\"m\"),t}};typeof module==\"object\"&&(module.exports=clone),clone.clonePrototype=function(e){if(e===null)return null;var t=function(){};return t.prototype=e,new t};var CSSLint=function(){function i(e,t){var r,i=e&&e.match(n),s=i&&i[1];return s&&(r={\"true\":2,\"\":1,\"false\":0,2:2,1:1,0:0},s.toLowerCase().split(\",\").forEach(function(e){var n=e.split(\":\"),i=n[0]||\"\",s=n[1]||\"\";t[i.trim()]=r[s.trim()]})),t}var e=[],t=[],n=/\\/\\*csslint([^\\*]*)\\*\\//,r=new parserlib.util.EventTarget;return r.version=\"@VERSION@\",r.addRule=function(t){e.push(t),e[t.id]=t},r.clearRules=function(){e=[]},r.getRules=function(){return[].concat(e).sort(function(e,t){return e.id>t.id?1:0})},r.getRuleset=function(){var t={},n=0,r=e.length;while(n<r)t[e[n++].id]=1;return t},r.addFormatter=function(e){t[e.id]=e},r.getFormatter=function(e){return t[e]},r.format=function(e,t,n,r){var i=this.getFormatter(n),s=null;return i&&(s=i.startFormat(),s+=i.formatResults(e,t,r||{}),s+=i.endFormat()),s},r.hasFormat=function(e){return t.hasOwnProperty(e)},r.verify=function(t,r){var s=0,o,u,a,f=new parserlib.css.Parser({starHack:!0,ieFilters:!0,underscoreHack:!0,strict:!1});u=t.replace(/\\n\\r?/g,\"$split$\").split(\"$split$\"),r||(r=this.getRuleset()),n.test(t)&&(r=clone(r),r=i(t,r)),o=new Reporter(u,r),r.errors=2;for(s in r)r.hasOwnProperty(s)&&r[s]&&e[s]&&e[s].init(f,o);try{f.parse(t)}catch(l){o.error(\"Fatal error, cannot continue: \"+l.message,l.line,l.col,{})}return a={messages:o.messages,stats:o.stats,ruleset:o.ruleset},a.messages.sort(function(e,t){return e.rollup&&!t.rollup?1:!e.rollup&&t.rollup?-1:e.line-t.line}),a},r}();Reporter.prototype={constructor:Reporter,error:function(e,t,n,r){this.messages.push({type:\"error\",line:t,col:n,message:e,evidence:this.lines[t-1],rule:r||{}})},warn:function(e,t,n,r){this.report(e,t,n,r)},report:function(e,t,n,r){this.messages.push({type:this.ruleset[r.id]===2?\"error\":\"warning\",line:t,col:n,message:e,evidence:this.lines[t-1],rule:r})},info:function(e,t,n,r){this.messages.push({type:\"info\",line:t,col:n,message:e,evidence:this.lines[t-1],rule:r})},rollupError:function(e,t){this.messages.push({type:\"error\",rollup:!0,message:e,rule:t})},rollupWarn:function(e,t){this.messages.push({type:\"warning\",rollup:!0,message:e,rule:t})},stat:function(e,t){this.stats[e]=t}},CSSLint._Reporter=Reporter,CSSLint.Util={mix:function(e,t){var n;for(n in t)t.hasOwnProperty(n)&&(e[n]=t[n]);return n},indexOf:function(e,t){if(e.indexOf)return e.indexOf(t);for(var n=0,r=e.length;n<r;n++)if(e[n]===t)return n;return-1},forEach:function(e,t){if(e.forEach)return e.forEach(t);for(var n=0,r=e.length;n<r;n++)t(e[n],n,e)}},CSSLint.addRule({id:\"adjoining-classes\",name:\"Disallow adjoining classes\",desc:\"Don't use adjoining classes.\",browsers:\"IE6\",init:function(e,t){var n=this;e.addListener(\"startrule\",function(r){var i=r.selectors,s,o,u,a,f,l,c;for(f=0;f<i.length;f++){s=i[f];for(l=0;l<s.parts.length;l++){o=s.parts[l];if(o.type===e.SELECTOR_PART_TYPE){a=0;for(c=0;c<o.modifiers.length;c++)u=o.modifiers[c],u.type===\"class\"&&a++,a>1&&t.report(\"Don't use adjoining classes.\",o.line,o.col,n)}}}})}}),CSSLint.addRule({id:\"box-model\",name:\"Beware of broken box size\",desc:\"Don't use width or height when using padding or border.\",browsers:\"All\",init:function(e,t){function u(){s={},o=!1}function a(){var e,u;if(!o){if(s.height)for(e in i)i.hasOwnProperty(e)&&s[e]&&(u=s[e].value,(e!==\"padding\"||u.parts.length!==2||u.parts[0].value!==0)&&t.report(\"Using height with \"+e+\" can sometimes make elements larger than you expect.\",s[e].line,s[e].col,n));if(s.width)for(e in r)r.hasOwnProperty(e)&&s[e]&&(u=s[e].value,(e!==\"padding\"||u.parts.length!==2||u.parts[1].value!==0)&&t.report(\"Using width with \"+e+\" can sometimes make elements larger than you expect.\",s[e].line,s[e].col,n))}}var n=this,r={border:1,\"border-left\":1,\"border-right\":1,padding:1,\"padding-left\":1,\"padding-right\":1},i={border:1,\"border-bottom\":1,\"border-top\":1,padding:1,\"padding-bottom\":1,\"padding-top\":1},s,o=!1;e.addListener(\"startrule\",u),e.addListener(\"startfontface\",u),e.addListener(\"startpage\",u),e.addListener(\"startpagemargin\",u),e.addListener(\"startkeyframerule\",u),e.addListener(\"property\",function(e){var t=e.property.text.toLowerCase();i[t]||r[t]?!/^0\\S*$/.test(e.value)&&(t!==\"border\"||e.value.toString()!==\"none\")&&(s[t]={line:e.property.line,col:e.property.col,value:e.value}):/^(width|height)/i.test(t)&&/^(length|percentage)/.test(e.value.parts[0].type)?s[t]=1:t===\"box-sizing\"&&(o=!0)}),e.addListener(\"endrule\",a),e.addListener(\"endfontface\",a),e.addListener(\"endpage\",a),e.addListener(\"endpagemargin\",a),e.addListener(\"endkeyframerule\",a)}}),CSSLint.addRule({id:\"box-sizing\",name:\"Disallow use of box-sizing\",desc:\"The box-sizing properties isn't supported in IE6 and IE7.\",browsers:\"IE6, IE7\",tags:[\"Compatibility\"],init:function(e,t){var n=this;e.addListener(\"property\",function(e){var r=e.property.text.toLowerCase();r===\"box-sizing\"&&t.report(\"The box-sizing property isn't supported in IE6 and IE7.\",e.line,e.col,n)})}}),CSSLint.addRule({id:\"bulletproof-font-face\",name:\"Use the bulletproof @font-face syntax\",desc:\"Use the bulletproof @font-face syntax to avoid 404's in old IE (http://www.fontspring.com/blog/the-new-bulletproof-font-face-syntax).\",browsers:\"All\",init:function(e,t){var n=this,r=!1,i=!0,s=!1,o,u;e.addListener(\"startfontface\",function(){r=!0}),e.addListener(\"property\",function(e){if(!r)return;var t=e.property.toString().toLowerCase(),n=e.value.toString();o=e.line,u=e.col;if(t===\"src\"){var a=/^\\s?url\\(['\"].+\\.eot\\?.*['\"]\\)\\s*format\\(['\"]embedded-opentype['\"]\\).*$/i;!n.match(a)&&i?(s=!0,i=!1):n.match(a)&&!i&&(s=!1)}}),e.addListener(\"endfontface\",function(){r=!1,s&&t.report(\"@font-face declaration doesn't follow the fontspring bulletproof syntax.\",o,u,n)})}}),CSSLint.addRule({id:\"compatible-vendor-prefixes\",name:\"Require compatible vendor prefixes\",desc:\"Include all compatible vendor prefixes to reach a wider range of users.\",browsers:\"All\",init:function(e,t){var n=this,r,i,s,o,u,a,f,l=!1,c=Array.prototype.push,h=[];r={animation:\"webkit moz\",\"animation-delay\":\"webkit moz\",\"animation-direction\":\"webkit moz\",\"animation-duration\":\"webkit moz\",\"animation-fill-mode\":\"webkit moz\",\"animation-iteration-count\":\"webkit moz\",\"animation-name\":\"webkit moz\",\"animation-play-state\":\"webkit moz\",\"animation-timing-function\":\"webkit moz\",appearance:\"webkit moz\",\"border-end\":\"webkit moz\",\"border-end-color\":\"webkit moz\",\"border-end-style\":\"webkit moz\",\"border-end-width\":\"webkit moz\",\"border-image\":\"webkit moz o\",\"border-radius\":\"webkit\",\"border-start\":\"webkit moz\",\"border-start-color\":\"webkit moz\",\"border-start-style\":\"webkit moz\",\"border-start-width\":\"webkit moz\",\"box-align\":\"webkit moz ms\",\"box-direction\":\"webkit moz ms\",\"box-flex\":\"webkit moz ms\",\"box-lines\":\"webkit ms\",\"box-ordinal-group\":\"webkit moz ms\",\"box-orient\":\"webkit moz ms\",\"box-pack\":\"webkit moz ms\",\"box-sizing\":\"webkit moz\",\"box-shadow\":\"webkit moz\",\"column-count\":\"webkit moz ms\",\"column-gap\":\"webkit moz ms\",\"column-rule\":\"webkit moz ms\",\"column-rule-color\":\"webkit moz ms\",\"column-rule-style\":\"webkit moz ms\",\"column-rule-width\":\"webkit moz ms\",\"column-width\":\"webkit moz ms\",hyphens:\"epub moz\",\"line-break\":\"webkit ms\",\"margin-end\":\"webkit moz\",\"margin-start\":\"webkit moz\",\"marquee-speed\":\"webkit wap\",\"marquee-style\":\"webkit wap\",\"padding-end\":\"webkit moz\",\"padding-start\":\"webkit moz\",\"tab-size\":\"moz o\",\"text-size-adjust\":\"webkit ms\",transform:\"webkit moz ms o\",\"transform-origin\":\"webkit moz ms o\",transition:\"webkit moz o\",\"transition-delay\":\"webkit moz o\",\"transition-duration\":\"webkit moz o\",\"transition-property\":\"webkit moz o\",\"transition-timing-function\":\"webkit moz o\",\"user-modify\":\"webkit moz\",\"user-select\":\"webkit moz ms\",\"word-break\":\"epub ms\",\"writing-mode\":\"epub ms\"};for(s in r)if(r.hasOwnProperty(s)){o=[],u=r[s].split(\" \");for(a=0,f=u.length;a<f;a++)o.push(\"-\"+u[a]+\"-\"+s);r[s]=o,c.apply(h,o)}e.addListener(\"startrule\",function(){i=[]}),e.addListener(\"startkeyframes\",function(e){l=e.prefix||!0}),e.addListener(\"endkeyframes\",function(){l=!1}),e.addListener(\"property\",function(e){var t=e.property;CSSLint.Util.indexOf(h,t.text)>-1&&(!l||typeof l!=\"string\"||t.text.indexOf(\"-\"+l+\"-\")!==0)&&i.push(t)}),e.addListener(\"endrule\",function(){if(!i.length)return;var e={},s,o,u,a,f,l,c,h,p,d;for(s=0,o=i.length;s<o;s++){u=i[s];for(a in r)r.hasOwnProperty(a)&&(f=r[a],CSSLint.Util.indexOf(f,u.text)>-1&&(e[a]||(e[a]={full:f.slice(0),actual:[],actualNodes:[]}),CSSLint.Util.indexOf(e[a].actual,u.text)===-1&&(e[a].actual.push(u.text),e[a].actualNodes.push(u))))}for(a in e)if(e.hasOwnProperty(a)){l=e[a],c=l.full,h=l.actual;if(c.length>h.length)for(s=0,o=c.length;s<o;s++)p=c[s],CSSLint.Util.indexOf(h,p)===-1&&(d=h.length===1?h[0]:h.length===2?h.join(\" and \"):h.join(\", \"),t.report(\"The property \"+p+\" is compatible with \"+d+\" and should be included as well.\",l.actualNodes[0].line,l.actualNodes[0].col,n))}})}}),CSSLint.addRule({id:\"display-property-grouping\",name:\"Require properties appropriate for display\",desc:\"Certain properties shouldn't be used with certain display property values.\",browsers:\"All\",init:function(e,t){function s(e,s,o){i[e]&&(typeof r[e]!=\"string\"||i[e].value.toLowerCase()!==r[e])&&t.report(o||e+\" can't be used with display: \"+s+\".\",i[e].line,i[e].col,n)}function o(){i={}}function u(){var e=i.display?i.display.value:null;if(e)switch(e){case\"inline\":s(\"height\",e),s(\"width\",e),s(\"margin\",e),s(\"margin-top\",e),s(\"margin-bottom\",e),s(\"float\",e,\"display:inline has no effect on floated elements (but may be used to fix the IE6 double-margin bug).\");break;case\"block\":s(\"vertical-align\",e);break;case\"inline-block\":s(\"float\",e);break;default:e.indexOf(\"table-\")===0&&(s(\"margin\",e),s(\"margin-left\",e),s(\"margin-right\",e),s(\"margin-top\",e),s(\"margin-bottom\",e),s(\"float\",e))}}var n=this,r={display:1,\"float\":\"none\",height:1,width:1,margin:1,\"margin-left\":1,\"margin-right\":1,\"margin-bottom\":1,\"margin-top\":1,padding:1,\"padding-left\":1,\"padding-right\":1,\"padding-bottom\":1,\"padding-top\":1,\"vertical-align\":1},i;e.addListener(\"startrule\",o),e.addListener(\"startfontface\",o),e.addListener(\"startkeyframerule\",o),e.addListener(\"startpagemargin\",o),e.addListener(\"startpage\",o),e.addListener(\"property\",function(e){var t=e.property.text.toLowerCase();r[t]&&(i[t]={value:e.value.text,line:e.property.line,col:e.property.col})}),e.addListener(\"endrule\",u),e.addListener(\"endfontface\",u),e.addListener(\"endkeyframerule\",u),e.addListener(\"endpagemargin\",u),e.addListener(\"endpage\",u)}}),CSSLint.addRule({id:\"duplicate-background-images\",name:\"Disallow duplicate background images\",desc:\"Every background-image should be unique. Use a common class for e.g. sprites.\",browsers:\"All\",init:function(e,t){var n=this,r={};e.addListener(\"property\",function(e){var i=e.property.text,s=e.value,o,u;if(i.match(/background/i))for(o=0,u=s.parts.length;o<u;o++)s.parts[o].type===\"uri\"&&(typeof r[s.parts[o].uri]==\"undefined\"?r[s.parts[o].uri]=e:t.report(\"Background image '\"+s.parts[o].uri+\"' was used multiple times, first declared at line \"+r[s.parts[o].uri].line+\", col \"+r[s.parts[o].uri].col+\".\",e.line,e.col,n))})}}),CSSLint.addRule({id:\"duplicate-properties\",name:\"Disallow duplicate properties\",desc:\"Duplicate properties must appear one after the other.\",browsers:\"All\",init:function(e,t){function s(){r={}}var n=this,r,i;e.addListener(\"startrule\",s),e.addListener(\"startfontface\",s),e.addListener(\"startpage\",s),e.addListener(\"startpagemargin\",s),e.addListener(\"startkeyframerule\",s),e.addListener(\"property\",function(e){var s=e.property,o=s.text.toLowerCase();r[o]&&(i!==o||r[o]===e.value.text)&&t.report(\"Duplicate property '\"+e.property+\"' found.\",e.line,e.col,n),r[o]=e.value.text,i=o})}}),CSSLint.addRule({id:\"empty-rules\",name:\"Disallow empty rules\",desc:\"Rules without any properties specified should be removed.\",browsers:\"All\",init:function(e,t){var n=this,r=0;e.addListener(\"startrule\",function(){r=0}),e.addListener(\"property\",function(){r++}),e.addListener(\"endrule\",function(e){var i=e.selectors;r===0&&t.report(\"Rule is empty.\",i[0].line,i[0].col,n)})}}),CSSLint.addRule({id:\"errors\",name:\"Parsing Errors\",desc:\"This rule looks for recoverable syntax errors.\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"error\",function(e){t.error(e.message,e.line,e.col,n)})}}),CSSLint.addRule({id:\"fallback-colors\",name:\"Require fallback colors\",desc:\"For older browsers that don't support RGBA, HSL, or HSLA, provide a fallback color.\",browsers:\"IE6,IE7,IE8\",init:function(e,t){function o(){s={},r=null}var n=this,r,i={color:1,background:1,\"border-color\":1,\"border-top-color\":1,\"border-right-color\":1,\"border-bottom-color\":1,\"border-left-color\":1,border:1,\"border-top\":1,\"border-right\":1,\"border-bottom\":1,\"border-left\":1,\"background-color\":1},s;e.addListener(\"startrule\",o),e.addListener(\"startfontface\",o),e.addListener(\"startpage\",o),e.addListener(\"startpagemargin\",o),e.addListener(\"startkeyframerule\",o),e.addListener(\"property\",function(e){var s=e.property,o=s.text.toLowerCase(),u=e.value.parts,a=0,f=\"\",l=u.length;if(i[o])while(a<l)u[a].type===\"color\"&&(\"alpha\"in u[a]||\"hue\"in u[a]?(/([^\\)]+)\\(/.test(u[a])&&(f=RegExp.$1.toUpperCase()),(!r||r.property.text.toLowerCase()!==o||r.colorType!==\"compat\")&&t.report(\"Fallback \"+o+\" (hex or RGB) should precede \"+f+\" \"+o+\".\",e.line,e.col,n)):e.colorType=\"compat\"),a++;r=e})}}),CSSLint.addRule({id:\"floats\",name:\"Disallow too many floats\",desc:\"This rule tests if the float property is used too many times\",browsers:\"All\",init:function(e,t){var n=this,r=0;e.addListener(\"property\",function(e){e.property.text.toLowerCase()===\"float\"&&e.value.text.toLowerCase()!==\"none\"&&r++}),e.addListener(\"endstylesheet\",function(){t.stat(\"floats\",r),r>=10&&t.rollupWarn(\"Too many floats (\"+r+\"), you're probably using them for layout. Consider using a grid system instead.\",n)})}}),CSSLint.addRule({id:\"font-faces\",name:\"Don't use too many web fonts\",desc:\"Too many different web fonts in the same stylesheet.\",browsers:\"All\",init:function(e,t){var n=this,r=0;e.addListener(\"startfontface\",function(){r++}),e.addListener(\"endstylesheet\",function(){r>5&&t.rollupWarn(\"Too many @font-face declarations (\"+r+\").\",n)})}}),CSSLint.addRule({id:\"font-sizes\",name:\"Disallow too many font sizes\",desc:\"Checks the number of font-size declarations.\",browsers:\"All\",init:function(e,t){var n=this,r=0;e.addListener(\"property\",function(e){e.property.toString()===\"font-size\"&&r++}),e.addListener(\"endstylesheet\",function(){t.stat(\"font-sizes\",r),r>=10&&t.rollupWarn(\"Too many font-size declarations (\"+r+\"), abstraction needed.\",n)})}}),CSSLint.addRule({id:\"gradients\",name:\"Require all gradient definitions\",desc:\"When using a vendor-prefixed gradient, make sure to use them all.\",browsers:\"All\",init:function(e,t){var n=this,r;e.addListener(\"startrule\",function(){r={moz:0,webkit:0,oldWebkit:0,o:0}}),e.addListener(\"property\",function(e){/\\-(moz|o|webkit)(?:\\-(?:linear|radial))\\-gradient/i.test(e.value)?r[RegExp.$1]=1:/\\-webkit\\-gradient/i.test(e.value)&&(r.oldWebkit=1)}),e.addListener(\"endrule\",function(e){var i=[];r.moz||i.push(\"Firefox 3.6+\"),r.webkit||i.push(\"Webkit (Safari 5+, Chrome)\"),r.oldWebkit||i.push(\"Old Webkit (Safari 4+, Chrome)\"),r.o||i.push(\"Opera 11.1+\"),i.length&&i.length<4&&t.report(\"Missing vendor-prefixed CSS gradients for \"+i.join(\", \")+\".\",e.selectors[0].line,e.selectors[0].col,n)})}}),CSSLint.addRule({id:\"ids\",name:\"Disallow IDs in selectors\",desc:\"Selectors should not contain IDs.\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"startrule\",function(r){var i=r.selectors,s,o,u,a,f,l,c;for(f=0;f<i.length;f++){s=i[f],a=0;for(l=0;l<s.parts.length;l++){o=s.parts[l];if(o.type===e.SELECTOR_PART_TYPE)for(c=0;c<o.modifiers.length;c++)u=o.modifiers[c],u.type===\"id\"&&a++}a===1?t.report(\"Don't use IDs in selectors.\",s.line,s.col,n):a>1&&t.report(a+\" IDs in the selector, really?\",s.line,s.col,n)}})}}),CSSLint.addRule({id:\"import\",name:\"Disallow @import\",desc:\"Don't use @import, use <link> instead.\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"import\",function(e){t.report(\"@import prevents parallel downloads, use <link> instead.\",e.line,e.col,n)})}}),CSSLint.addRule({id:\"important\",name:\"Disallow !important\",desc:\"Be careful when using !important declaration\",browsers:\"All\",init:function(e,t){var n=this,r=0;e.addListener(\"property\",function(e){e.important===!0&&(r++,t.report(\"Use of !important\",e.line,e.col,n))}),e.addListener(\"endstylesheet\",function(){t.stat(\"important\",r),r>=10&&t.rollupWarn(\"Too many !important declarations (\"+r+\"), try to use less than 10 to avoid specificity issues.\",n)})}}),CSSLint.addRule({id:\"known-properties\",name:\"Require use of known properties\",desc:\"Properties should be known (listed in CSS3 specification) or be a vendor-prefixed property.\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"property\",function(e){e.invalid&&t.report(e.invalid.message,e.line,e.col,n)})}}),CSSLint.addRule({id:\"order-alphabetical\",name:\"Alphabetical order\",desc:\"Assure properties are in alphabetical order\",browsers:\"All\",init:function(e,t){var n=this,r,i=function(){r=[]};e.addListener(\"startrule\",i),e.addListener(\"startfontface\",i),e.addListener(\"startpage\",i),e.addListener(\"startpagemargin\",i),e.addListener(\"startkeyframerule\",i),e.addListener(\"property\",function(e){var t=e.property.text,n=t.toLowerCase().replace(/^-.*?-/,\"\");r.push(n)}),e.addListener(\"endrule\",function(e){var i=r.join(\",\"),s=r.sort().join(\",\");i!==s&&t.report(\"Rule doesn't have all its properties in alphabetical ordered.\",e.line,e.col,n)})}}),CSSLint.addRule({id:\"outline-none\",name:\"Disallow outline: none\",desc:\"Use of outline: none or outline: 0 should be limited to :focus rules.\",browsers:\"All\",tags:[\"Accessibility\"],init:function(e,t){function i(e){e.selectors?r={line:e.line,col:e.col,selectors:e.selectors,propCount:0,outline:!1}:r=null}function s(){r&&r.outline&&(r.selectors.toString().toLowerCase().indexOf(\":focus\")===-1?t.report(\"Outlines should only be modified using :focus.\",r.line,r.col,n):r.propCount===1&&t.report(\"Outlines shouldn't be hidden unless other visual changes are made.\",r.line,r.col,n))}var n=this,r;e.addListener(\"startrule\",i),e.addListener(\"startfontface\",i),e.addListener(\"startpage\",i),e.addListener(\"startpagemargin\",i),e.addListener(\"startkeyframerule\",i),e.addListener(\"property\",function(e){var t=e.property.text.toLowerCase(),n=e.value;r&&(r.propCount++,t===\"outline\"&&(n.toString()===\"none\"||n.toString()===\"0\")&&(r.outline=!0))}),e.addListener(\"endrule\",s),e.addListener(\"endfontface\",s),e.addListener(\"endpage\",s),e.addListener(\"endpagemargin\",s),e.addListener(\"endkeyframerule\",s)}}),CSSLint.addRule({id:\"overqualified-elements\",name:\"Disallow overqualified elements\",desc:\"Don't use classes or IDs with elements (a.foo or a#foo).\",browsers:\"All\",init:function(e,t){var n=this,r={};e.addListener(\"startrule\",function(i){var s=i.selectors,o,u,a,f,l,c;for(f=0;f<s.length;f++){o=s[f];for(l=0;l<o.parts.length;l++){u=o.parts[l];if(u.type===e.SELECTOR_PART_TYPE)for(c=0;c<u.modifiers.length;c++)a=u.modifiers[c],u.elementName&&a.type===\"id\"?t.report(\"Element (\"+u+\") is overqualified, just use \"+a+\" without element name.\",u.line,u.col,n):a.type===\"class\"&&(r[a]||(r[a]=[]),r[a].push({modifier:a,part:u}))}}}),e.addListener(\"endstylesheet\",function(){var e;for(e in r)r.hasOwnProperty(e)&&r[e].length===1&&r[e][0].part.elementName&&t.report(\"Element (\"+r[e][0].part+\") is overqualified, just use \"+r[e][0].modifier+\" without element name.\",r[e][0].part.line,r[e][0].part.col,n)})}}),CSSLint.addRule({id:\"qualified-headings\",name:\"Disallow qualified headings\",desc:\"Headings should not be qualified (namespaced).\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"startrule\",function(r){var i=r.selectors,s,o,u,a;for(u=0;u<i.length;u++){s=i[u];for(a=0;a<s.parts.length;a++)o=s.parts[a],o.type===e.SELECTOR_PART_TYPE&&o.elementName&&/h[1-6]/.test(o.elementName.toString())&&a>0&&t.report(\"Heading (\"+o.elementName+\") should not be qualified.\",o.line,o.col,n)}})}}),CSSLint.addRule({id:\"regex-selectors\",name:\"Disallow selectors that look like regexs\",desc:\"Selectors that look like regular expressions are slow and should be avoided.\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"startrule\",function(r){var i=r.selectors,s,o,u,a,f,l;for(a=0;a<i.length;a++){s=i[a];for(f=0;f<s.parts.length;f++){o=s.parts[f];if(o.type===e.SELECTOR_PART_TYPE)for(l=0;l<o.modifiers.length;l++)u=o.modifiers[l],u.type===\"attribute\"&&/([\\~\\|\\^\\$\\*]=)/.test(u)&&t.report(\"Attribute selectors with \"+RegExp.$1+\" are slow!\",u.line,u.col,n)}}})}}),CSSLint.addRule({id:\"rules-count\",name:\"Rules Count\",desc:\"Track how many rules there are.\",browsers:\"All\",init:function(e,t){var n=0;e.addListener(\"startrule\",function(){n++}),e.addListener(\"endstylesheet\",function(){t.stat(\"rule-count\",n)})}}),CSSLint.addRule({id:\"selector-max-approaching\",name:\"Warn when approaching the 4095 selector limit for IE\",desc:\"Will warn when selector count is >= 3800 selectors.\",browsers:\"IE\",init:function(e,t){var n=this,r=0;e.addListener(\"startrule\",function(e){r+=e.selectors.length}),e.addListener(\"endstylesheet\",function(){r>=3800&&t.report(\"You have \"+r+\" selectors. Internet Explorer supports a maximum of 4095 selectors per stylesheet. Consider refactoring.\",0,0,n)})}}),CSSLint.addRule({id:\"selector-max\",name:\"Error when past the 4095 selector limit for IE\",desc:\"Will error when selector count is > 4095.\",browsers:\"IE\",init:function(e,t){var n=this,r=0;e.addListener(\"startrule\",function(e){r+=e.selectors.length}),e.addListener(\"endstylesheet\",function(){r>4095&&t.report(\"You have \"+r+\" selectors. Internet Explorer supports a maximum of 4095 selectors per stylesheet. Consider refactoring.\",0,0,n)})}}),CSSLint.addRule({id:\"selector-newline\",name:\"Disallow new-line characters in selectors\",desc:\"New-line characters in selectors are usually a forgotten comma and not a descendant combinator.\",browsers:\"All\",init:function(e,t){function r(e){var r,i,s,o,u,a,f,l,c,h,p,d=e.selectors;for(r=0,i=d.length;r<i;r++){s=d[r];for(o=0,a=s.parts.length;o<a;o++)for(u=o+1;u<a;u++)f=s.parts[o],l=s.parts[u],c=f.type,h=f.line,p=l.line,c===\"descendant\"&&p>h&&t.report(\"newline character found in selector (forgot a comma?)\",h,d[r].parts[0].col,n)}}var n=this;e.addListener(\"startrule\",r)}}),CSSLint.addRule({id:\"shorthand\",name:\"Require shorthand properties\",desc:\"Use shorthand properties where possible.\",browsers:\"All\",init:function(e,t){function f(){u={}}function l(e){var r,i,s,o;for(r in a)if(a.hasOwnProperty(r)){o=0;for(i=0,s=a[r].length;i<s;i++)o+=u[a[r][i]]?1:0;o===a[r].length&&t.report(\"The properties \"+a[r].join(\", \")+\" can be replaced by \"+r+\".\",e.line,e.col,n)}}var n=this,r,i,s,o={},u,a={margin:[\"margin-top\",\"margin-bottom\",\"margin-left\",\"margin-right\"],padding:[\"padding-top\",\"padding-bottom\",\"padding-left\",\"padding-right\"]};for(r in a)if(a.hasOwnProperty(r))for(i=0,s=a[r].length;i<s;i++)o[a[r][i]]=r;e.addListener(\"startrule\",f),e.addListener(\"startfontface\",f),e.addListener(\"property\",function(e){var t=e.property.toString().toLowerCase();o[t]&&(u[t]=1)}),e.addListener(\"endrule\",l),e.addListener(\"endfontface\",l)}}),CSSLint.addRule({id:\"star-property-hack\",name:\"Disallow properties with a star prefix\",desc:\"Checks for the star property hack (targets IE6/7)\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"property\",function(e){var r=e.property;r.hack===\"*\"&&t.report(\"Property with star prefix found.\",e.property.line,e.property.col,n)})}}),CSSLint.addRule({id:\"text-indent\",name:\"Disallow negative text-indent\",desc:\"Checks for text indent less than -99px\",browsers:\"All\",init:function(e,t){function s(){r=!1,i=\"inherit\"}function o(){r&&i!==\"ltr\"&&t.report(\"Negative text-indent doesn't work well with RTL. If you use text-indent for image replacement explicitly set direction for that item to ltr.\",r.line,r.col,n)}var n=this,r,i;e.addListener(\"startrule\",s),e.addListener(\"startfontface\",s),e.addListener(\"property\",function(e){var t=e.property.toString().toLowerCase(),n=e.value;t===\"text-indent\"&&n.parts[0].value<-99?r=e.property:t===\"direction\"&&n.toString()===\"ltr\"&&(i=\"ltr\")}),e.addListener(\"endrule\",o),e.addListener(\"endfontface\",o)}}),CSSLint.addRule({id:\"underscore-property-hack\",name:\"Disallow properties with an underscore prefix\",desc:\"Checks for the underscore property hack (targets IE6)\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"property\",function(e){var r=e.property;r.hack===\"_\"&&t.report(\"Property with underscore prefix found.\",e.property.line,e.property.col,n)})}}),CSSLint.addRule({id:\"unique-headings\",name:\"Headings should only be defined once\",desc:\"Headings should be defined only once.\",browsers:\"All\",init:function(e,t){var n=this,r={h1:0,h2:0,h3:0,h4:0,h5:0,h6:0};e.addListener(\"startrule\",function(e){var i=e.selectors,s,o,u,a,f;for(a=0;a<i.length;a++){s=i[a],o=s.parts[s.parts.length-1];if(o.elementName&&/(h[1-6])/i.test(o.elementName.toString())){for(f=0;f<o.modifiers.length;f++)if(o.modifiers[f].type===\"pseudo\"){u=!0;break}u||(r[RegExp.$1]++,r[RegExp.$1]>1&&t.report(\"Heading (\"+o.elementName+\") has already been defined.\",o.line,o.col,n))}}}),e.addListener(\"endstylesheet\",function(){var e,i=[];for(e in r)r.hasOwnProperty(e)&&r[e]>1&&i.push(r[e]+\" \"+e+\"s\");i.length&&t.rollupWarn(\"You have \"+i.join(\", \")+\" defined in this stylesheet.\",n)})}}),CSSLint.addRule({id:\"universal-selector\",name:\"Disallow universal selector\",desc:\"The universal selector (*) is known to be slow.\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"startrule\",function(e){var r=e.selectors,i,s,o;for(o=0;o<r.length;o++)i=r[o],s=i.parts[i.parts.length-1],s.elementName===\"*\"&&t.report(n.desc,s.line,s.col,n)})}}),CSSLint.addRule({id:\"unqualified-attributes\",name:\"Disallow unqualified attribute selectors\",desc:\"Unqualified attribute selectors are known to be slow.\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"startrule\",function(r){var i=r.selectors,s,o,u,a,f;for(a=0;a<i.length;a++){s=i[a],o=s.parts[s.parts.length-1];if(o.type===e.SELECTOR_PART_TYPE)for(f=0;f<o.modifiers.length;f++)u=o.modifiers[f],u.type===\"attribute\"&&(!o.elementName||o.elementName===\"*\")&&t.report(n.desc,o.line,o.col,n)}})}}),CSSLint.addRule({id:\"vendor-prefix\",name:\"Require standard property with vendor prefix\",desc:\"When using a vendor-prefixed property, make sure to include the standard one.\",browsers:\"All\",init:function(e,t){function o(){r={},i=1}function u(){var e,i,o,u,a,f=[];for(e in r)s[e]&&f.push({actual:e,needed:s[e]});for(i=0,o=f.length;i<o;i++)u=f[i].needed,a=f[i].actual,r[u]?r[u][0].pos<r[a][0].pos&&t.report(\"Standard property '\"+u+\"' should come after vendor-prefixed property '\"+a+\"'.\",r[a][0].name.line,r[a][0].name.col,n):t.report(\"Missing standard property '\"+u+\"' to go along with '\"+a+\"'.\",r[a][0].name.line,r[a][0].name.col,n)}var n=this,r,i,s={\"-webkit-border-radius\":\"border-radius\",\"-webkit-border-top-left-radius\":\"border-top-left-radius\",\"-webkit-border-top-right-radius\":\"border-top-right-radius\",\"-webkit-border-bottom-left-radius\":\"border-bottom-left-radius\",\"-webkit-border-bottom-right-radius\":\"border-bottom-right-radius\",\"-o-border-radius\":\"border-radius\",\"-o-border-top-left-radius\":\"border-top-left-radius\",\"-o-border-top-right-radius\":\"border-top-right-radius\",\"-o-border-bottom-left-radius\":\"border-bottom-left-radius\",\"-o-border-bottom-right-radius\":\"border-bottom-right-radius\",\"-moz-border-radius\":\"border-radius\",\"-moz-border-radius-topleft\":\"border-top-left-radius\",\"-moz-border-radius-topright\":\"border-top-right-radius\",\"-moz-border-radius-bottomleft\":\"border-bottom-left-radius\",\"-moz-border-radius-bottomright\":\"border-bottom-right-radius\",\"-moz-column-count\":\"column-count\",\"-webkit-column-count\":\"column-count\",\"-moz-column-gap\":\"column-gap\",\"-webkit-column-gap\":\"column-gap\",\"-moz-column-rule\":\"column-rule\",\"-webkit-column-rule\":\"column-rule\",\"-moz-column-rule-style\":\"column-rule-style\",\"-webkit-column-rule-style\":\"column-rule-style\",\"-moz-column-rule-color\":\"column-rule-color\",\"-webkit-column-rule-color\":\"column-rule-color\",\"-moz-column-rule-width\":\"column-rule-width\",\"-webkit-column-rule-width\":\"column-rule-width\",\"-moz-column-width\":\"column-width\",\"-webkit-column-width\":\"column-width\",\"-webkit-column-span\":\"column-span\",\"-webkit-columns\":\"columns\",\"-moz-box-shadow\":\"box-shadow\",\"-webkit-box-shadow\":\"box-shadow\",\"-moz-transform\":\"transform\",\"-webkit-transform\":\"transform\",\"-o-transform\":\"transform\",\"-ms-transform\":\"transform\",\"-moz-transform-origin\":\"transform-origin\",\"-webkit-transform-origin\":\"transform-origin\",\"-o-transform-origin\":\"transform-origin\",\"-ms-transform-origin\":\"transform-origin\",\"-moz-box-sizing\":\"box-sizing\",\"-webkit-box-sizing\":\"box-sizing\"};e.addListener(\"startrule\",o),e.addListener(\"startfontface\",o),e.addListener(\"startpage\",o),e.addListener(\"startpagemargin\",o),e.addListener(\"startkeyframerule\",o),e.addListener(\"property\",function(e){var t=e.property.text.toLowerCase();r[t]||(r[t]=[]),r[t].push({name:e.property,value:e.value,pos:i++})}),e.addListener(\"endrule\",u),e.addListener(\"endfontface\",u),e.addListener(\"endpage\",u),e.addListener(\"endpagemargin\",u),e.addListener(\"endkeyframerule\",u)}}),CSSLint.addRule({id:\"zero-units\",name:\"Disallow units for 0 values\",desc:\"You don't need to specify units when a value is 0.\",browsers:\"All\",init:function(e,t){var n=this;e.addListener(\"property\",function(e){var r=e.value.parts,i=0,s=r.length;while(i<s)(r[i].units||r[i].type===\"percentage\")&&r[i].value===0&&r[i].type!==\"time\"&&t.report(\"Values of 0 shouldn't have units specified.\",r[i].line,r[i].col,n),i++})}}),function(){var e=function(e){return!e||e.constructor!==String?\"\":e.replace(/[\\\"&><]/g,function(e){switch(e){case'\"':return\"&quot;\";case\"&\":return\"&amp;\";case\"<\":return\"&lt;\";case\">\":return\"&gt;\"}})};CSSLint.addFormatter({id:\"checkstyle-xml\",name:\"Checkstyle XML format\",startFormat:function(){return'<?xml version=\"1.0\" encoding=\"utf-8\"?><checkstyle>'},endFormat:function(){return\"</checkstyle>\"},readError:function(t,n){return'<file name=\"'+e(t)+'\"><error line=\"0\" column=\"0\" severty=\"error\" message=\"'+e(n)+'\"></error></file>'},formatResults:function(t,n){var r=t.messages,i=[],s=function(e){return!!e&&\"name\"in e?\"net.csslint.\"+e.name.replace(/\\s/g,\"\"):\"\"};return r.length>0&&(i.push('<file name=\"'+n+'\">'),CSSLint.Util.forEach(r,function(t){t.rollup||i.push('<error line=\"'+t.line+'\" column=\"'+t.col+'\" severity=\"'+t.type+'\"'+' message=\"'+e(t.message)+'\" source=\"'+s(t.rule)+'\"/>')}),i.push(\"</file>\")),i.join(\"\")}})}(),CSSLint.addFormatter({id:\"compact\",name:\"Compact, 'porcelain' format\",startFormat:function(){return\"\"},endFormat:function(){return\"\"},formatResults:function(e,t,n){var r=e.messages,i=\"\";n=n||{};var s=function(e){return e.charAt(0).toUpperCase()+e.slice(1)};return r.length===0?n.quiet?\"\":t+\": Lint Free!\":(CSSLint.Util.forEach(r,function(e){e.rollup?i+=t+\": \"+s(e.type)+\" - \"+e.message+\"\\n\":i+=t+\": \"+\"line \"+e.line+\", col \"+e.col+\", \"+s(e.type)+\" - \"+e.message+\" (\"+e.rule.id+\")\\n\"}),i)}}),CSSLint.addFormatter({id:\"csslint-xml\",name:\"CSSLint XML format\",startFormat:function(){return'<?xml version=\"1.0\" encoding=\"utf-8\"?><csslint>'},endFormat:function(){return\"</csslint>\"},formatResults:function(e,t){var n=e.messages,r=[],i=function(e){return!e||e.constructor!==String?\"\":e.replace(/\\\"/g,\"'\").replace(/&/g,\"&amp;\").replace(/</g,\"&lt;\").replace(/>/g,\"&gt;\")};return n.length>0&&(r.push('<file name=\"'+t+'\">'),CSSLint.Util.forEach(n,function(e){e.rollup?r.push('<issue severity=\"'+e.type+'\" reason=\"'+i(e.message)+'\" evidence=\"'+i(e.evidence)+'\"/>'):r.push('<issue line=\"'+e.line+'\" char=\"'+e.col+'\" severity=\"'+e.type+'\"'+' reason=\"'+i(e.message)+'\" evidence=\"'+i(e.evidence)+'\"/>')}),r.push(\"</file>\")),r.join(\"\")}}),CSSLint.addFormatter({id:\"junit-xml\",name:\"JUNIT XML format\",startFormat:function(){return'<?xml version=\"1.0\" encoding=\"utf-8\"?><testsuites>'},endFormat:function(){return\"</testsuites>\"},formatResults:function(e,t){var n=e.messages,r=[],i={error:0,failure:0},s=function(e){return!!e&&\"name\"in e?\"net.csslint.\"+e.name.replace(/\\s/g,\"\"):\"\"},o=function(e){return!e||e.constructor!==String?\"\":e.replace(/\\\"/g,\"'\").replace(/</g,\"&lt;\").replace(/>/g,\"&gt;\")};return n.length>0&&(n.forEach(function(e){var t=e.type===\"warning\"?\"error\":e.type;e.rollup||(r.push('<testcase time=\"0\" name=\"'+s(e.rule)+'\">'),r.push(\"<\"+t+' message=\"'+o(e.message)+'\"><![CDATA['+e.line+\":\"+e.col+\":\"+o(e.evidence)+\"]]></\"+t+\">\"),r.push(\"</testcase>\"),i[t]+=1)}),r.unshift('<testsuite time=\"0\" tests=\"'+n.length+'\" skipped=\"0\" errors=\"'+i.error+'\" failures=\"'+i.failure+'\" package=\"net.csslint\" name=\"'+t+'\">'),r.push(\"</testsuite>\")),r.join(\"\")}}),CSSLint.addFormatter({id:\"lint-xml\",name:\"Lint XML format\",startFormat:function(){return'<?xml version=\"1.0\" encoding=\"utf-8\"?><lint>'},endFormat:function(){return\"</lint>\"},formatResults:function(e,t){var n=e.messages,r=[],i=function(e){return!e||e.constructor!==String?\"\":e.replace(/\\\"/g,\"'\").replace(/&/g,\"&amp;\").replace(/</g,\"&lt;\").replace(/>/g,\"&gt;\")};return n.length>0&&(r.push('<file name=\"'+t+'\">'),CSSLint.Util.forEach(n,function(e){e.rollup?r.push('<issue severity=\"'+e.type+'\" reason=\"'+i(e.message)+'\" evidence=\"'+i(e.evidence)+'\"/>'):r.push('<issue line=\"'+e.line+'\" char=\"'+e.col+'\" severity=\"'+e.type+'\"'+' reason=\"'+i(e.message)+'\" evidence=\"'+i(e.evidence)+'\"/>')}),r.push(\"</file>\")),r.join(\"\")}}),CSSLint.addFormatter({id:\"text\",name:\"Plain Text\",startFormat:function(){return\"\"},endFormat:function(){return\"\"},formatResults:function(e,t,n){var r=e.messages,i=\"\";n=n||{};if(r.length===0)return n.quiet?\"\":\"\\n\\ncsslint: No errors in \"+t+\".\";i=\"\\n\\ncsslint: There \",r.length===1?i+=\"is 1 problem\":i+=\"are \"+r.length+\" problems\",i+=\" in \"+t+\".\";var s=t.lastIndexOf(\"/\"),o=t;return s===-1&&(s=t.lastIndexOf(\"\\\\\")),s>-1&&(o=t.substring(s+1)),CSSLint.Util.forEach(r,function(e,t){i=i+\"\\n\\n\"+o,e.rollup?(i+=\"\\n\"+(t+1)+\": \"+e.type,i+=\"\\n\"+e.message):(i+=\"\\n\"+(t+1)+\": \"+e.type+\" at line \"+e.line+\", col \"+e.col,i+=\"\\n\"+e.message,i+=\"\\n\"+e.evidence)}),i}}),module.exports.CSSLint=CSSLint}),define(\"ace/mode/css_worker\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/worker/mirror\",\"ace/mode/css/csslint\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"../worker/mirror\").Mirror,o=e(\"./css/csslint\").CSSLint,u=t.Worker=function(e){s.call(this,e),this.setTimeout(400),this.ruleset=null,this.setDisabledRules(\"ids|order-alphabetical\"),this.setInfoRules(\"adjoining-classes|qualified-headings|zero-units|gradients|import|outline-none|vendor-prefix\")};r.inherits(u,s),function(){this.setInfoRules=function(e){typeof e==\"string\"&&(e=e.split(\"|\")),this.infoRules=i.arrayToMap(e),this.doc.getValue()&&this.deferredUpdate.schedule(100)},this.setDisabledRules=function(e){if(!e)this.ruleset=null;else{typeof e==\"string\"&&(e=e.split(\"|\"));var t={};o.getRules().forEach(function(e){t[e.id]=!0}),e.forEach(function(e){delete t[e]}),this.ruleset=t}this.doc.getValue()&&this.deferredUpdate.schedule(100)},this.onUpdate=function(){var e=this.doc.getValue();if(!e)return this.sender.emit(\"annotate\",[]);var t=this.infoRules,n=o.verify(e,this.ruleset);this.sender.emit(\"annotate\",n.messages.map(function(e){return{row:e.line-1,column:e.col-1,text:e.message,type:t[e.rule.id]?\"info\":e.type,rule:e.rule.name}}))}}.call(u.prototype)}),define(\"ace/lib/es5-shim\",[\"require\",\"exports\",\"module\"],function(e,t,n){function r(){}function w(e){try{return Object.defineProperty(e,\"sentinel\",{}),\"sentinel\"in e}catch(t){}}function H(e){return e=+e,e!==e?e=0:e!==0&&e!==1/0&&e!==-1/0&&(e=(e>0||-1)*Math.floor(Math.abs(e))),e}function B(e){var t=typeof e;return e===null||t===\"undefined\"||t===\"boolean\"||t===\"number\"||t===\"string\"}function j(e){var t,n,r;if(B(e))return e;n=e.valueOf;if(typeof n==\"function\"){t=n.call(e);if(B(t))return t}r=e.toString;if(typeof r==\"function\"){t=r.call(e);if(B(t))return t}throw new TypeError}Function.prototype.bind||(Function.prototype.bind=function(t){var n=this;if(typeof n!=\"function\")throw new TypeError(\"Function.prototype.bind called on incompatible \"+n);var i=u.call(arguments,1),s=function(){if(this instanceof s){var e=n.apply(this,i.concat(u.call(arguments)));return Object(e)===e?e:this}return n.apply(t,i.concat(u.call(arguments)))};return n.prototype&&(r.prototype=n.prototype,s.prototype=new r,r.prototype=null),s});var i=Function.prototype.call,s=Array.prototype,o=Object.prototype,u=s.slice,a=i.bind(o.toString),f=i.bind(o.hasOwnProperty),l,c,h,p,d;if(d=f(o,\"__defineGetter__\"))l=i.bind(o.__defineGetter__),c=i.bind(o.__defineSetter__),h=i.bind(o.__lookupGetter__),p=i.bind(o.__lookupSetter__);if([1,2].splice(0).length!=2)if(!function(){function e(e){var t=new Array(e+2);return t[0]=t[1]=0,t}var t=[],n;t.splice.apply(t,e(20)),t.splice.apply(t,e(26)),n=t.length,t.splice(5,0,\"XXX\"),n+1==t.length;if(n+1==t.length)return!0}())Array.prototype.splice=function(e,t){var n=this.length;e>0?e>n&&(e=n):e==void 0?e=0:e<0&&(e=Math.max(n+e,0)),e+t<n||(t=n-e);var r=this.slice(e,e+t),i=u.call(arguments,2),s=i.length;if(e===n)s&&this.push.apply(this,i);else{var o=Math.min(t,n-e),a=e+o,f=a+s-o,l=n-a,c=n-o;if(f<a)for(var h=0;h<l;++h)this[f+h]=this[a+h];else if(f>a)for(h=l;h--;)this[f+h]=this[a+h];if(s&&e===c)this.length=c,this.push.apply(this,i);else{this.length=c+s;for(h=0;h<s;++h)this[e+h]=i[h]}}return r};else{var v=Array.prototype.splice;Array.prototype.splice=function(e,t){return arguments.length?v.apply(this,[e===void 0?0:e,t===void 0?this.length-e:t].concat(u.call(arguments,2))):[]}}Array.isArray||(Array.isArray=function(t){return a(t)==\"[object Array]\"});var m=Object(\"a\"),g=m[0]!=\"a\"||!(0 in m);Array.prototype.forEach||(Array.prototype.forEach=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=arguments[1],s=-1,o=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError;while(++s<o)s in r&&t.call(i,r[s],s,n)}),Array.prototype.map||(Array.prototype.map=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=Array(i),o=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var u=0;u<i;u++)u in r&&(s[u]=t.call(o,r[u],u,n));return s}),Array.prototype.filter||(Array.prototype.filter=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=[],o,u=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var f=0;f<i;f++)f in r&&(o=r[f],t.call(u,o,f,n)&&s.push(o));return s}),Array.prototype.every||(Array.prototype.every=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&!t.call(s,r[o],o,n))return!1;return!0}),Array.prototype.some||(Array.prototype.some=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&t.call(s,r[o],o,n))return!0;return!1}),Array.prototype.reduce||(Array.prototype.reduce=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduce of empty array with no initial value\");var s=0,o;if(arguments.length>=2)o=arguments[1];else do{if(s in r){o=r[s++];break}if(++s>=i)throw new TypeError(\"reduce of empty array with no initial value\")}while(!0);for(;s<i;s++)s in r&&(o=t.call(void 0,o,r[s],s,n));return o}),Array.prototype.reduceRight||(Array.prototype.reduceRight=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduceRight of empty array with no initial value\");var s,o=i-1;if(arguments.length>=2)s=arguments[1];else do{if(o in r){s=r[o--];break}if(--o<0)throw new TypeError(\"reduceRight of empty array with no initial value\")}while(!0);do o in this&&(s=t.call(void 0,s,r[o],o,n));while(o--);return s});if(!Array.prototype.indexOf||[0,1].indexOf(1,2)!=-1)Array.prototype.indexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=0;arguments.length>1&&(i=H(arguments[1])),i=i>=0?i:Math.max(0,r+i);for(;i<r;i++)if(i in n&&n[i]===t)return i;return-1};if(!Array.prototype.lastIndexOf||[0,1].lastIndexOf(0,-3)!=-1)Array.prototype.lastIndexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=r-1;arguments.length>1&&(i=Math.min(i,H(arguments[1]))),i=i>=0?i:r-Math.abs(i);for(;i>=0;i--)if(i in n&&t===n[i])return i;return-1};Object.getPrototypeOf||(Object.getPrototypeOf=function(t){return t.__proto__||(t.constructor?t.constructor.prototype:o)});if(!Object.getOwnPropertyDescriptor){var y=\"Object.getOwnPropertyDescriptor called on a non-object: \";Object.getOwnPropertyDescriptor=function(t,n){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(y+t);if(!f(t,n))return;var r,i,s;r={enumerable:!0,configurable:!0};if(d){var u=t.__proto__;t.__proto__=o;var i=h(t,n),s=p(t,n);t.__proto__=u;if(i||s)return i&&(r.get=i),s&&(r.set=s),r}return r.value=t[n],r}}Object.getOwnPropertyNames||(Object.getOwnPropertyNames=function(t){return Object.keys(t)});if(!Object.create){var b;Object.prototype.__proto__===null?b=function(){return{__proto__:null}}:b=function(){var e={};for(var t in e)e[t]=null;return e.constructor=e.hasOwnProperty=e.propertyIsEnumerable=e.isPrototypeOf=e.toLocaleString=e.toString=e.valueOf=e.__proto__=null,e},Object.create=function(t,n){var r;if(t===null)r=b();else{if(typeof t!=\"object\")throw new TypeError(\"typeof prototype[\"+typeof t+\"] != 'object'\");var i=function(){};i.prototype=t,r=new i,r.__proto__=t}return n!==void 0&&Object.defineProperties(r,n),r}}if(Object.defineProperty){var E=w({}),S=typeof document==\"undefined\"||w(document.createElement(\"div\"));if(!E||!S)var x=Object.defineProperty}if(!Object.defineProperty||x){var T=\"Property description must be an object: \",N=\"Object.defineProperty called on non-object: \",C=\"getters & setters can not be defined on this javascript engine\";Object.defineProperty=function(t,n,r){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(N+t);if(typeof r!=\"object\"&&typeof r!=\"function\"||r===null)throw new TypeError(T+r);if(x)try{return x.call(Object,t,n,r)}catch(i){}if(f(r,\"value\"))if(d&&(h(t,n)||p(t,n))){var s=t.__proto__;t.__proto__=o,delete t[n],t[n]=r.value,t.__proto__=s}else t[n]=r.value;else{if(!d)throw new TypeError(C);f(r,\"get\")&&l(t,n,r.get),f(r,\"set\")&&c(t,n,r.set)}return t}}Object.defineProperties||(Object.defineProperties=function(t,n){for(var r in n)f(n,r)&&Object.defineProperty(t,r,n[r]);return t}),Object.seal||(Object.seal=function(t){return t}),Object.freeze||(Object.freeze=function(t){return t});try{Object.freeze(function(){})}catch(k){Object.freeze=function(t){return function(n){return typeof n==\"function\"?n:t(n)}}(Object.freeze)}Object.preventExtensions||(Object.preventExtensions=function(t){return t}),Object.isSealed||(Object.isSealed=function(t){return!1}),Object.isFrozen||(Object.isFrozen=function(t){return!1}),Object.isExtensible||(Object.isExtensible=function(t){if(Object(t)===t)throw new TypeError;var n=\"\";while(f(t,n))n+=\"?\";t[n]=!0;var r=f(t,n);return delete t[n],r});if(!Object.keys){var L=!0,A=[\"toString\",\"toLocaleString\",\"valueOf\",\"hasOwnProperty\",\"isPrototypeOf\",\"propertyIsEnumerable\",\"constructor\"],O=A.length;for(var M in{toString:null})L=!1;Object.keys=function I(e){if(typeof e!=\"object\"&&typeof e!=\"function\"||e===null)throw new TypeError(\"Object.keys called on a non-object\");var I=[];for(var t in e)f(e,t)&&I.push(t);if(L)for(var n=0,r=O;n<r;n++){var i=A[n];f(e,i)&&I.push(i)}return I}}Date.now||(Date.now=function(){return(new Date).getTime()});var _=\"\t\\n\u000b\\f\\r \\u00a0\\u1680\\u180e\\u2000\\u2001\\u2002\\u2003\\u2004\\u2005\\u2006\\u2007\\u2008\\u2009\\u200a\\u202f\\u205f\\u3000\\u2028\\u2029\\ufeff\";if(!String.prototype.trim||_.trim()){_=\"[\"+_+\"]\";var D=new RegExp(\"^\"+_+_+\"*\"),P=new RegExp(_+_+\"*$\");String.prototype.trim=function(){return String(this).replace(D,\"\").replace(P,\"\")}}var F=function(e){if(e==null)throw new TypeError(\"can't convert \"+e+\" to object\");return Object(e)}})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/worker-html.js",
    "content": "\"no use strict\";(function(e){function t(e,t){var n=e,r=\"\";while(n){var i=t[n];if(typeof i==\"string\")return i+r;if(i)return i.location.replace(/\\/*$/,\"/\")+(r||i.main||i.name);if(i===!1)return\"\";var s=n.lastIndexOf(\"/\");if(s===-1)break;r=n.substr(s)+r,n=n.slice(0,s)}return e}if(typeof e.window!=\"undefined\"&&e.document)return;if(e.require&&e.define)return;e.console||(e.console=function(){var e=Array.prototype.slice.call(arguments,0);postMessage({type:\"log\",data:e})},e.console.error=e.console.warn=e.console.log=e.console.trace=e.console),e.window=e,e.ace=e,e.onerror=function(e,t,n,r,i){postMessage({type:\"error\",data:{message:e,data:i.data,file:t,line:n,col:r,stack:i.stack}})},e.normalizeModule=function(t,n){if(n.indexOf(\"!\")!==-1){var r=n.split(\"!\");return e.normalizeModule(t,r[0])+\"!\"+e.normalizeModule(t,r[1])}if(n.charAt(0)==\".\"){var i=t.split(\"/\").slice(0,-1).join(\"/\");n=(i?i+\"/\":\"\")+n;while(n.indexOf(\".\")!==-1&&s!=n){var s=n;n=n.replace(/^\\.\\//,\"\").replace(/\\/\\.\\//,\"/\").replace(/[^\\/]+\\/\\.\\.\\//,\"\")}}return n},e.require=function(r,i){i||(i=r,r=null);if(!i.charAt)throw new Error(\"worker.js require() accepts only (parentId, id) as arguments\");i=e.normalizeModule(r,i);var s=e.require.modules[i];if(s)return s.initialized||(s.initialized=!0,s.exports=s.factory().exports),s.exports;if(!e.require.tlns)return console.log(\"unable to load \"+i);var o=t(i,e.require.tlns);return o.slice(-3)!=\".js\"&&(o+=\".js\"),e.require.id=i,e.require.modules[i]={},importScripts(o),e.require(r,i)},e.require.modules={},e.require.tlns={},e.define=function(t,n,r){arguments.length==2?(r=n,typeof t!=\"string\"&&(n=t,t=e.require.id)):arguments.length==1&&(r=t,n=[],t=e.require.id);if(typeof r!=\"function\"){e.require.modules[t]={exports:r,initialized:!0};return}n.length||(n=[\"require\",\"exports\",\"module\"]);var i=function(n){return e.require(t,n)};e.require.modules[t]={exports:{},factory:function(){var e=this,t=r.apply(this,n.map(function(t){switch(t){case\"require\":return i;case\"exports\":return e.exports;case\"module\":return e;default:return i(t)}}));return t&&(e.exports=t),e}}},e.define.amd={},require.tlns={},e.initBaseUrls=function(t){for(var n in t)require.tlns[n]=t[n]},e.initSender=function(){var n=e.require(\"ace/lib/event_emitter\").EventEmitter,r=e.require(\"ace/lib/oop\"),i=function(){};return function(){r.implement(this,n),this.callback=function(e,t){postMessage({type:\"call\",id:t,data:e})},this.emit=function(e,t){postMessage({type:\"event\",name:e,data:t})}}.call(i.prototype),new i};var n=e.main=null,r=e.sender=null;e.onmessage=function(t){var i=t.data;if(i.event&&r)r._signal(i.event,i.data);else if(i.command)if(n[i.command])n[i.command].apply(n,i.args);else{if(!e[i.command])throw new Error(\"Unknown command:\"+i.command);e[i.command].apply(e,i.args)}else if(i.init){e.initBaseUrls(i.tlns),require(\"ace/lib/es5-shim\"),r=e.sender=e.initSender();var s=require(i.module)[i.classname];n=e.main=new s(r)}}})(this),define(\"ace/lib/oop\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.inherits=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})},t.mixin=function(e,t){for(var n in t)e[n]=t[n];return e},t.implement=function(e,n){t.mixin(e,n)}}),define(\"ace/lib/lang\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.last=function(e){return e[e.length-1]},t.stringReverse=function(e){return e.split(\"\").reverse().join(\"\")},t.stringRepeat=function(e,t){var n=\"\";while(t>0){t&1&&(n+=e);if(t>>=1)e+=e}return n};var r=/^\\s\\s*/,i=/\\s\\s*$/;t.stringTrimLeft=function(e){return e.replace(r,\"\")},t.stringTrimRight=function(e){return e.replace(i,\"\")},t.copyObject=function(e){var t={};for(var n in e)t[n]=e[n];return t},t.copyArray=function(e){var t=[];for(var n=0,r=e.length;n<r;n++)e[n]&&typeof e[n]==\"object\"?t[n]=this.copyObject(e[n]):t[n]=e[n];return t},t.deepCopy=function s(e){if(typeof e!=\"object\"||!e)return e;var t;if(Array.isArray(e)){t=[];for(var n=0;n<e.length;n++)t[n]=s(e[n]);return t}if(Object.prototype.toString.call(e)!==\"[object Object]\")return e;t={};for(var n in e)t[n]=s(e[n]);return t},t.arrayToMap=function(e){var t={};for(var n=0;n<e.length;n++)t[e[n]]=1;return t},t.createMap=function(e){var t=Object.create(null);for(var n in e)t[n]=e[n];return t},t.arrayRemove=function(e,t){for(var n=0;n<=e.length;n++)t===e[n]&&e.splice(n,1)},t.escapeRegExp=function(e){return e.replace(/([.*+?^${}()|[\\]\\/\\\\])/g,\"\\\\$1\")},t.escapeHTML=function(e){return e.replace(/&/g,\"&#38;\").replace(/\"/g,\"&#34;\").replace(/'/g,\"&#39;\").replace(/</g,\"&#60;\")},t.getMatchOffsets=function(e,t){var n=[];return e.replace(t,function(e){n.push({offset:arguments[arguments.length-2],length:e.length})}),n},t.deferredCall=function(e){var t=null,n=function(){t=null,e()},r=function(e){return r.cancel(),t=setTimeout(n,e||0),r};return r.schedule=r,r.call=function(){return this.cancel(),e(),r},r.cancel=function(){return clearTimeout(t),t=null,r},r.isPending=function(){return t},r},t.delayedCall=function(e,t){var n=null,r=function(){n=null,e()},i=function(e){n==null&&(n=setTimeout(r,e||t))};return i.delay=function(e){n&&clearTimeout(n),n=setTimeout(r,e||t)},i.schedule=i,i.call=function(){this.cancel(),e()},i.cancel=function(){n&&clearTimeout(n),n=null},i.isPending=function(){return n},i}}),define(\"ace/range\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(e,t){return e.row-t.row||e.column-t.column},i=function(e,t,n,r){this.start={row:e,column:t},this.end={row:n,column:r}};(function(){this.isEqual=function(e){return this.start.row===e.start.row&&this.end.row===e.end.row&&this.start.column===e.start.column&&this.end.column===e.end.column},this.toString=function(){return\"Range: [\"+this.start.row+\"/\"+this.start.column+\"] -> [\"+this.end.row+\"/\"+this.end.column+\"]\"},this.contains=function(e,t){return this.compare(e,t)==0},this.compareRange=function(e){var t,n=e.end,r=e.start;return t=this.compare(n.row,n.column),t==1?(t=this.compare(r.row,r.column),t==1?2:t==0?1:0):t==-1?-2:(t=this.compare(r.row,r.column),t==-1?-1:t==1?42:0)},this.comparePoint=function(e){return this.compare(e.row,e.column)},this.containsRange=function(e){return this.comparePoint(e.start)==0&&this.comparePoint(e.end)==0},this.intersects=function(e){var t=this.compareRange(e);return t==-1||t==0||t==1},this.isEnd=function(e,t){return this.end.row==e&&this.end.column==t},this.isStart=function(e,t){return this.start.row==e&&this.start.column==t},this.setStart=function(e,t){typeof e==\"object\"?(this.start.column=e.column,this.start.row=e.row):(this.start.row=e,this.start.column=t)},this.setEnd=function(e,t){typeof e==\"object\"?(this.end.column=e.column,this.end.row=e.row):(this.end.row=e,this.end.column=t)},this.inside=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)||this.isStart(e,t)?!1:!0:!1},this.insideStart=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)?!1:!0:!1},this.insideEnd=function(e,t){return this.compare(e,t)==0?this.isStart(e,t)?!1:!0:!1},this.compare=function(e,t){return!this.isMultiLine()&&e===this.start.row?t<this.start.column?-1:t>this.end.column?1:0:e<this.start.row?-1:e>this.end.row?1:this.start.row===e?t>=this.start.column?0:-1:this.end.row===e?t<=this.end.column?0:1:0},this.compareStart=function(e,t){return this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.compareEnd=function(e,t){return this.end.row==e&&this.end.column==t?1:this.compare(e,t)},this.compareInside=function(e,t){return this.end.row==e&&this.end.column==t?1:this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.clipRows=function(e,t){if(this.end.row>t)var n={row:t+1,column:0};else if(this.end.row<e)var n={row:e,column:0};if(this.start.row>t)var r={row:t+1,column:0};else if(this.start.row<e)var r={row:e,column:0};return i.fromPoints(r||this.start,n||this.end)},this.extend=function(e,t){var n=this.compare(e,t);if(n==0)return this;if(n==-1)var r={row:e,column:t};else var s={row:e,column:t};return i.fromPoints(r||this.start,s||this.end)},this.isEmpty=function(){return this.start.row===this.end.row&&this.start.column===this.end.column},this.isMultiLine=function(){return this.start.row!==this.end.row},this.clone=function(){return i.fromPoints(this.start,this.end)},this.collapseRows=function(){return this.end.column==0?new i(this.start.row,0,Math.max(this.start.row,this.end.row-1),0):new i(this.start.row,0,this.end.row,0)},this.toScreenRange=function(e){var t=e.documentToScreenPosition(this.start),n=e.documentToScreenPosition(this.end);return new i(t.row,t.column,n.row,n.column)},this.moveBy=function(e,t){this.start.row+=e,this.start.column+=t,this.end.row+=e,this.end.column+=t}}).call(i.prototype),i.fromPoints=function(e,t){return new i(e.row,e.column,t.row,t.column)},i.comparePoints=r,i.comparePoints=function(e,t){return e.row-t.row||e.column-t.column},t.Range=i}),define(\"ace/apply_delta\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function r(e,t){throw console.log(\"Invalid Delta:\",e),\"Invalid Delta: \"+t}function i(e,t){return t.row>=0&&t.row<e.length&&t.column>=0&&t.column<=e[t.row].length}function s(e,t){t.action!=\"insert\"&&t.action!=\"remove\"&&r(t,\"delta.action must be 'insert' or 'remove'\"),t.lines instanceof Array||r(t,\"delta.lines must be an Array\"),(!t.start||!t.end)&&r(t,\"delta.start/end must be an present\");var n=t.start;i(e,t.start)||r(t,\"delta.start must be contained in document\");var s=t.end;t.action==\"remove\"&&!i(e,s)&&r(t,\"delta.end must contained in document for 'remove' actions\");var o=s.row-n.row,u=s.column-(o==0?n.column:0);(o!=t.lines.length-1||t.lines[o].length!=u)&&r(t,\"delta.range must match delta lines\")}t.applyDelta=function(e,t,n){var r=t.start.row,i=t.start.column,s=e[r]||\"\";switch(t.action){case\"insert\":var o=t.lines;if(o.length===1)e[r]=s.substring(0,i)+t.lines[0]+s.substring(i);else{var u=[r,1].concat(t.lines);e.splice.apply(e,u),e[r]=s.substring(0,i)+e[r],e[r+t.lines.length-1]+=s.substring(i)}break;case\"remove\":var a=t.end.column,f=t.end.row;r===f?e[r]=s.substring(0,i)+s.substring(a):e.splice(r,f-r+1,s.substring(0,i)+e[f].substring(a))}}}),define(\"ace/lib/event_emitter\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={},i=function(){this.propagationStopped=!0},s=function(){this.defaultPrevented=!0};r._emit=r._dispatchEvent=function(e,t){this._eventRegistry||(this._eventRegistry={}),this._defaultHandlers||(this._defaultHandlers={});var n=this._eventRegistry[e]||[],r=this._defaultHandlers[e];if(!n.length&&!r)return;if(typeof t!=\"object\"||!t)t={};t.type||(t.type=e),t.stopPropagation||(t.stopPropagation=i),t.preventDefault||(t.preventDefault=s),n=n.slice();for(var o=0;o<n.length;o++){n[o](t,this);if(t.propagationStopped)break}if(r&&!t.defaultPrevented)return r(t,this)},r._signal=function(e,t){var n=(this._eventRegistry||{})[e];if(!n)return;n=n.slice();for(var r=0;r<n.length;r++)n[r](t,this)},r.once=function(e,t){var n=this;t&&this.addEventListener(e,function r(){n.removeEventListener(e,r),t.apply(null,arguments)})},r.setDefaultHandler=function(e,t){var n=this._defaultHandlers;n||(n=this._defaultHandlers={_disabled_:{}});if(n[e]){var r=n[e],i=n._disabled_[e];i||(n._disabled_[e]=i=[]),i.push(r);var s=i.indexOf(t);s!=-1&&i.splice(s,1)}n[e]=t},r.removeDefaultHandler=function(e,t){var n=this._defaultHandlers;if(!n)return;var r=n._disabled_[e];if(n[e]==t){var i=n[e];r&&this.setDefaultHandler(e,r.pop())}else if(r){var s=r.indexOf(t);s!=-1&&r.splice(s,1)}},r.on=r.addEventListener=function(e,t,n){this._eventRegistry=this._eventRegistry||{};var r=this._eventRegistry[e];return r||(r=this._eventRegistry[e]=[]),r.indexOf(t)==-1&&r[n?\"unshift\":\"push\"](t),t},r.off=r.removeListener=r.removeEventListener=function(e,t){this._eventRegistry=this._eventRegistry||{};var n=this._eventRegistry[e];if(!n)return;var r=n.indexOf(t);r!==-1&&n.splice(r,1)},r.removeAllListeners=function(e){this._eventRegistry&&(this._eventRegistry[e]=[])},t.EventEmitter=r}),define(\"ace/anchor\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/event_emitter\").EventEmitter,s=t.Anchor=function(e,t,n){this.$onChange=this.onChange.bind(this),this.attach(e),typeof n==\"undefined\"?this.setPosition(t.row,t.column):this.setPosition(t,n)};(function(){function e(e,t,n){var r=n?e.column<=t.column:e.column<t.column;return e.row<t.row||e.row==t.row&&r}function t(t,n,r){var i=t.action==\"insert\",s=(i?1:-1)*(t.end.row-t.start.row),o=(i?1:-1)*(t.end.column-t.start.column),u=t.start,a=i?u:t.end;return e(n,u,r)?{row:n.row,column:n.column}:e(a,n,!r)?{row:n.row+s,column:n.column+(n.row==a.row?o:0)}:{row:u.row,column:u.column}}r.implement(this,i),this.getPosition=function(){return this.$clipPositionToDocument(this.row,this.column)},this.getDocument=function(){return this.document},this.$insertRight=!1,this.onChange=function(e){if(e.start.row==e.end.row&&e.start.row!=this.row)return;if(e.start.row>this.row)return;var n=t(e,{row:this.row,column:this.column},this.$insertRight);this.setPosition(n.row,n.column,!0)},this.setPosition=function(e,t,n){var r;n?r={row:e,column:t}:r=this.$clipPositionToDocument(e,t);if(this.row==r.row&&this.column==r.column)return;var i={row:this.row,column:this.column};this.row=r.row,this.column=r.column,this._signal(\"change\",{old:i,value:r})},this.detach=function(){this.document.removeEventListener(\"change\",this.$onChange)},this.attach=function(e){this.document=e||this.document,this.document.on(\"change\",this.$onChange)},this.$clipPositionToDocument=function(e,t){var n={};return e>=this.document.getLength()?(n.row=Math.max(0,this.document.getLength()-1),n.column=this.document.getLine(n.row).length):e<0?(n.row=0,n.column=0):(n.row=e,n.column=Math.min(this.document.getLine(n.row).length,Math.max(0,t))),t<0&&(n.column=0),n}}).call(s.prototype)}),define(\"ace/document\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/apply_delta\",\"ace/lib/event_emitter\",\"ace/range\",\"ace/anchor\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./apply_delta\").applyDelta,s=e(\"./lib/event_emitter\").EventEmitter,o=e(\"./range\").Range,u=e(\"./anchor\").Anchor,a=function(e){this.$lines=[\"\"],e.length===0?this.$lines=[\"\"]:Array.isArray(e)?this.insertMergedLines({row:0,column:0},e):this.insert({row:0,column:0},e)};(function(){r.implement(this,s),this.setValue=function(e){var t=this.getLength()-1;this.remove(new o(0,0,t,this.getLine(t).length)),this.insert({row:0,column:0},e)},this.getValue=function(){return this.getAllLines().join(this.getNewLineCharacter())},this.createAnchor=function(e,t){return new u(this,e,t)},\"aaa\".split(/a/).length===0?this.$split=function(e){return e.replace(/\\r\\n|\\r/g,\"\\n\").split(\"\\n\")}:this.$split=function(e){return e.split(/\\r\\n|\\r|\\n/)},this.$detectNewLine=function(e){var t=e.match(/^.*?(\\r\\n|\\r|\\n)/m);this.$autoNewLine=t?t[1]:\"\\n\",this._signal(\"changeNewLineMode\")},this.getNewLineCharacter=function(){switch(this.$newLineMode){case\"windows\":return\"\\r\\n\";case\"unix\":return\"\\n\";default:return this.$autoNewLine||\"\\n\"}},this.$autoNewLine=\"\",this.$newLineMode=\"auto\",this.setNewLineMode=function(e){if(this.$newLineMode===e)return;this.$newLineMode=e,this._signal(\"changeNewLineMode\")},this.getNewLineMode=function(){return this.$newLineMode},this.isNewLine=function(e){return e==\"\\r\\n\"||e==\"\\r\"||e==\"\\n\"},this.getLine=function(e){return this.$lines[e]||\"\"},this.getLines=function(e,t){return this.$lines.slice(e,t+1)},this.getAllLines=function(){return this.getLines(0,this.getLength())},this.getLength=function(){return this.$lines.length},this.getTextRange=function(e){return this.getLinesForRange(e).join(this.getNewLineCharacter())},this.getLinesForRange=function(e){var t;if(e.start.row===e.end.row)t=[this.getLine(e.start.row).substring(e.start.column,e.end.column)];else{t=this.getLines(e.start.row,e.end.row),t[0]=(t[0]||\"\").substring(e.start.column);var n=t.length-1;e.end.row-e.start.row==n&&(t[n]=t[n].substring(0,e.end.column))}return t},this.insertLines=function(e,t){return console.warn(\"Use of document.insertLines is deprecated. Use the insertFullLines method instead.\"),this.insertFullLines(e,t)},this.removeLines=function(e,t){return console.warn(\"Use of document.removeLines is deprecated. Use the removeFullLines method instead.\"),this.removeFullLines(e,t)},this.insertNewLine=function(e){return console.warn(\"Use of document.insertNewLine is deprecated. Use insertMergedLines(position, ['', '']) instead.\"),this.insertMergedLines(e,[\"\",\"\"])},this.insert=function(e,t){return this.getLength()<=1&&this.$detectNewLine(t),this.insertMergedLines(e,this.$split(t))},this.insertInLine=function(e,t){var n=this.clippedPos(e.row,e.column),r=this.pos(e.row,e.column+t.length);return this.applyDelta({start:n,end:r,action:\"insert\",lines:[t]},!0),this.clonePos(r)},this.clippedPos=function(e,t){var n=this.getLength();e===undefined?e=n:e<0?e=0:e>=n&&(e=n-1,t=undefined);var r=this.getLine(e);return t==undefined&&(t=r.length),t=Math.min(Math.max(t,0),r.length),{row:e,column:t}},this.clonePos=function(e){return{row:e.row,column:e.column}},this.pos=function(e,t){return{row:e,column:t}},this.$clipPosition=function(e){var t=this.getLength();return e.row>=t?(e.row=Math.max(0,t-1),e.column=this.getLine(t-1).length):(e.row=Math.max(0,e.row),e.column=Math.min(Math.max(e.column,0),this.getLine(e.row).length)),e},this.insertFullLines=function(e,t){e=Math.min(Math.max(e,0),this.getLength());var n=0;e<this.getLength()?(t=t.concat([\"\"]),n=0):(t=[\"\"].concat(t),e--,n=this.$lines[e].length),this.insertMergedLines({row:e,column:n},t)},this.insertMergedLines=function(e,t){var n=this.clippedPos(e.row,e.column),r={row:n.row+t.length-1,column:(t.length==1?n.column:0)+t[t.length-1].length};return this.applyDelta({start:n,end:r,action:\"insert\",lines:t}),this.clonePos(r)},this.remove=function(e){var t=this.clippedPos(e.start.row,e.start.column),n=this.clippedPos(e.end.row,e.end.column);return this.applyDelta({start:t,end:n,action:\"remove\",lines:this.getLinesForRange({start:t,end:n})}),this.clonePos(t)},this.removeInLine=function(e,t,n){var r=this.clippedPos(e,t),i=this.clippedPos(e,n);return this.applyDelta({start:r,end:i,action:\"remove\",lines:this.getLinesForRange({start:r,end:i})},!0),this.clonePos(r)},this.removeFullLines=function(e,t){e=Math.min(Math.max(0,e),this.getLength()-1),t=Math.min(Math.max(0,t),this.getLength()-1);var n=t==this.getLength()-1&&e>0,r=t<this.getLength()-1,i=n?e-1:e,s=n?this.getLine(i).length:0,u=r?t+1:t,a=r?0:this.getLine(u).length,f=new o(i,s,u,a),l=this.$lines.slice(e,t+1);return this.applyDelta({start:f.start,end:f.end,action:\"remove\",lines:this.getLinesForRange(f)}),l},this.removeNewLine=function(e){e<this.getLength()-1&&e>=0&&this.applyDelta({start:this.pos(e,this.getLine(e).length),end:this.pos(e+1,0),action:\"remove\",lines:[\"\",\"\"]})},this.replace=function(e,t){e instanceof o||(e=o.fromPoints(e.start,e.end));if(t.length===0&&e.isEmpty())return e.start;if(t==this.getTextRange(e))return e.end;this.remove(e);var n;return t?n=this.insert(e.start,t):n=e.start,n},this.applyDeltas=function(e){for(var t=0;t<e.length;t++)this.applyDelta(e[t])},this.revertDeltas=function(e){for(var t=e.length-1;t>=0;t--)this.revertDelta(e[t])},this.applyDelta=function(e,t){var n=e.action==\"insert\";if(n?e.lines.length<=1&&!e.lines[0]:!o.comparePoints(e.start,e.end))return;n&&e.lines.length>2e4&&this.$splitAndapplyLargeDelta(e,2e4),i(this.$lines,e,t),this._signal(\"change\",e)},this.$splitAndapplyLargeDelta=function(e,t){var n=e.lines,r=n.length,i=e.start.row,s=e.start.column,o=0,u=0;do{o=u,u+=t-1;var a=n.slice(o,u);if(u>r){e.lines=a,e.start.row=i+o,e.start.column=s;break}a.push(\"\"),this.applyDelta({start:this.pos(i+o,s),end:this.pos(i+u,s=0),action:e.action,lines:a},!0)}while(!0)},this.revertDelta=function(e){this.applyDelta({start:this.clonePos(e.start),end:this.clonePos(e.end),action:e.action==\"insert\"?\"remove\":\"insert\",lines:e.lines.slice()})},this.indexToPosition=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length;for(var i=t||0,s=n.length;i<s;i++){e-=n[i].length+r;if(e<0)return{row:i,column:e+n[i].length+r}}return{row:s-1,column:n[s-1].length}},this.positionToIndex=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length,i=0,s=Math.min(e.row,n.length);for(var o=t||0;o<s;++o)i+=n[o].length+r;return i+e.column}}).call(a.prototype),t.Document=a}),define(\"ace/worker/mirror\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/document\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=e(\"../document\").Document,s=e(\"../lib/lang\"),o=t.Mirror=function(e){this.sender=e;var t=this.doc=new i(\"\"),n=this.deferredUpdate=s.delayedCall(this.onUpdate.bind(this)),r=this;e.on(\"change\",function(e){var i=e.data;if(i[0].start)t.applyDeltas(i);else for(var s=0;s<i.length;s+=2){if(Array.isArray(i[s+1]))var o={action:\"insert\",start:i[s],lines:i[s+1]};else var o={action:\"remove\",start:i[s],end:i[s+1]};t.applyDelta(o,!0)}if(r.$timeout)return n.schedule(r.$timeout);r.onUpdate()})};(function(){this.$timeout=500,this.setTimeout=function(e){this.$timeout=e},this.setValue=function(e){this.doc.setValue(e),this.deferredUpdate.schedule(this.$timeout)},this.getValue=function(e){this.sender.callback(this.doc.getValue(),e)},this.onUpdate=function(){},this.isPending=function(){return this.deferredUpdate.isPending()}}).call(o.prototype)}),define(\"ace/mode/html/saxparser\",[\"require\",\"exports\",\"module\"],function(e,t,n){n.exports=function r(t,n,i){function s(u,a){if(!n[u]){if(!t[u]){var f=typeof e==\"function\"&&e;if(!a&&f)return f(u,!0);if(o)return o(u,!0);throw new Error(\"Cannot find module '\"+u+\"'\")}var l=n[u]={exports:{}};t[u][0].call(l.exports,function(e){var n=t[u][1][e];return s(n?n:e)},l,l.exports,r,t,n,i)}return n[u].exports}var o=typeof e==\"function\"&&e;for(var u=0;u<i.length;u++)s(i[u]);return s}({1:[function(e,t,n){function r(e){if(e.namespaceURI===\"http://www.w3.org/1999/xhtml\")return e.localName===\"applet\"||e.localName===\"caption\"||e.localName===\"marquee\"||e.localName===\"object\"||e.localName===\"table\"||e.localName===\"td\"||e.localName===\"th\";if(e.namespaceURI===\"http://www.w3.org/1998/Math/MathML\")return e.localName===\"mi\"||e.localName===\"mo\"||e.localName===\"mn\"||e.localName===\"ms\"||e.localName===\"mtext\"||e.localName===\"annotation-xml\";if(e.namespaceURI===\"http://www.w3.org/2000/svg\")return e.localName===\"foreignObject\"||e.localName===\"desc\"||e.localName===\"title\"}function i(e){return r(e)||e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"ol\"||e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"ul\"}function s(e){return e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"table\"||e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"html\"}function o(e){return e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"tbody\"||e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"tfoot\"||e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"thead\"||e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"html\"}function u(e){return e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"tr\"||e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"html\"}function a(e){return r(e)||e.namespaceURI===\"http://www.w3.org/1999/xhtml\"&&e.localName===\"button\"}function f(e){return(e.namespaceURI!==\"http://www.w3.org/1999/xhtml\"||e.localName!==\"optgroup\")&&(e.namespaceURI!==\"http://www.w3.org/1999/xhtml\"||e.localName!==\"option\")}function l(){this.elements=[],this.rootNode=null,this.headElement=null,this.bodyElement=null}l.prototype._inScope=function(e,t){for(var n=this.elements.length-1;n>=0;n--){var r=this.elements[n];if(r.localName===e)return!0;if(t(r))return!1}},l.prototype.push=function(e){this.elements.push(e)},l.prototype.pushHtmlElement=function(e){this.rootNode=e.node,this.push(e)},l.prototype.pushHeadElement=function(e){this.headElement=e.node,this.push(e)},l.prototype.pushBodyElement=function(e){this.bodyElement=e.node,this.push(e)},l.prototype.pop=function(){return this.elements.pop()},l.prototype.remove=function(e){this.elements.splice(this.elements.indexOf(e),1)},l.prototype.popUntilPopped=function(e){var t;do t=this.pop();while(t.localName!=e)},l.prototype.popUntilTableScopeMarker=function(){while(!s(this.top))this.pop()},l.prototype.popUntilTableBodyScopeMarker=function(){while(!o(this.top))this.pop()},l.prototype.popUntilTableRowScopeMarker=function(){while(!u(this.top))this.pop()},l.prototype.item=function(e){return this.elements[e]},l.prototype.contains=function(e){return this.elements.indexOf(e)!==-1},l.prototype.inScope=function(e){return this._inScope(e,r)},l.prototype.inListItemScope=function(e){return this._inScope(e,i)},l.prototype.inTableScope=function(e){return this._inScope(e,s)},l.prototype.inButtonScope=function(e){return this._inScope(e,a)},l.prototype.inSelectScope=function(e){return this._inScope(e,f)},l.prototype.hasNumberedHeaderElementInScope=function(){for(var e=this.elements.length-1;e>=0;e--){var t=this.elements[e];if(t.isNumberedHeader())return!0;if(r(t))return!1}},l.prototype.furthestBlockForFormattingElement=function(e){var t=null;for(var n=this.elements.length-1;n>=0;n--){var r=this.elements[n];if(r.node===e)break;r.isSpecial()&&(t=r)}return t},l.prototype.findIndex=function(e){for(var t=this.elements.length-1;t>=0;t--)if(this.elements[t].localName==e)return t;return-1},l.prototype.remove_openElements_until=function(e){var t=!1,n;while(!t)n=this.elements.pop(),t=e(n);return n},Object.defineProperty(l.prototype,\"top\",{get:function(){return this.elements[this.elements.length-1]}}),Object.defineProperty(l.prototype,\"length\",{get:function(){return this.elements.length}}),n.ElementStack=l},{}],2:[function(e,t,n){function o(e){return e>=\"0\"&&e<=\"9\"||e>=\"a\"&&e<=\"z\"||e>=\"A\"&&e<=\"Z\"}function u(e){return e>=\"0\"&&e<=\"9\"||e>=\"a\"&&e<=\"f\"||e>=\"A\"&&e<=\"F\"}function a(e){return e>=\"0\"&&e<=\"9\"}var r=e(\"html5-entities\"),i=e(\"./InputStream\").InputStream,s={};Object.keys(r).forEach(function(e){for(var t=0;t<e.length;t++)s[e.substring(0,t+1)]=!0});var f={};f.consumeEntity=function(e,t,n){var f=\"\",l=\"\",c=e.char();if(c===i.EOF)return!1;l+=c;if(c==\"\t\"||c==\"\\n\"||c==\"\u000b\"||c==\" \"||c==\"<\"||c==\"&\")return e.unget(l),!1;if(n===c)return e.unget(l),!1;if(c==\"#\"){c=e.shift(1);if(c===i.EOF)return t._parseError(\"expected-numeric-entity-but-got-eof\"),e.unget(l),!1;l+=c;var h=10,p=a;if(c==\"x\"||c==\"X\"){h=16,p=u,c=e.shift(1);if(c===i.EOF)return t._parseError(\"expected-numeric-entity-but-got-eof\"),e.unget(l),!1;l+=c}if(p(c)){var d=\"\";while(c!==i.EOF&&p(c))d+=c,c=e.char();d=parseInt(d,h);var v=this.replaceEntityNumbers(d);v&&(t._parseError(\"invalid-numeric-entity-replaced\"),d=v);if(d>65535&&d<=1114111){d-=65536;var m=((1047552&d)>>10)+55296,g=(1023&d)+56320;f=String.fromCharCode(m,g)}else f=String.fromCharCode(d);return c!==\";\"&&(t._parseError(\"numeric-entity-without-semicolon\"),e.unget(c)),f}return e.unget(l),t._parseError(\"expected-numeric-entity\"),!1}if(c>=\"a\"&&c<=\"z\"||c>=\"A\"&&c<=\"Z\"){var y=\"\";while(s[l]){r[l]&&(y=l);if(c==\";\")break;c=e.char();if(c===i.EOF)break;l+=c}return y?(f=r[y],c===\";\"||!n||!o(c)&&c!==\"=\"?(l.length>y.length&&e.unget(l.substring(y.length)),c!==\";\"&&t._parseError(\"named-entity-without-semicolon\"),f):(e.unget(l),!1)):(t._parseError(\"expected-named-entity\"),e.unget(l),!1)}},f.replaceEntityNumbers=function(e){switch(e){case 0:return 65533;case 19:return 16;case 128:return 8364;case 129:return 129;case 130:return 8218;case 131:return 402;case 132:return 8222;case 133:return 8230;case 134:return 8224;case 135:return 8225;case 136:return 710;case 137:return 8240;case 138:return 352;case 139:return 8249;case 140:return 338;case 141:return 141;case 142:return 381;case 143:return 143;case 144:return 144;case 145:return 8216;case 146:return 8217;case 147:return 8220;case 148:return 8221;case 149:return 8226;case 150:return 8211;case 151:return 8212;case 152:return 732;case 153:return 8482;case 154:return 353;case 155:return 8250;case 156:return 339;case 157:return 157;case 158:return 382;case 159:return 376;default:if(e>=55296&&e<=57343||e>1114111)return 65533;if(e>=1&&e<=8||e>=14&&e<=31||e>=127&&e<=159||e>=64976&&e<=65007||e==11||e==65534||e==131070||e==3145726||e==196607||e==262142||e==262143||e==327678||e==327679||e==393214||e==393215||e==458750||e==458751||e==524286||e==524287||e==589822||e==589823||e==655358||e==655359||e==720894||e==720895||e==786430||e==786431||e==851966||e==851967||e==917502||e==917503||e==983038||e==983039||e==1048574||e==1048575||e==1114110||e==1114111)return e}},n.EntityParser=f},{\"./InputStream\":3,\"html5-entities\":12}],3:[function(e,t,n){function r(){this.data=\"\",this.start=0,this.committed=0,this.eof=!1,this.lastLocation={line:0,column:0}}r.EOF=-1,r.DRAIN=-2,r.prototype={slice:function(){if(this.start>=this.data.length){if(!this.eof)throw r.DRAIN;return r.EOF}return this.data.slice(this.start,this.data.length)},\"char\":function(){if(!this.eof&&this.start>=this.data.length-1)throw r.DRAIN;if(this.start>=this.data.length)return r.EOF;var e=this.data[this.start++];return e===\"\\r\"&&(e=\"\\n\"),e},advance:function(e){this.start+=e;if(this.start>=this.data.length){if(!this.eof)throw r.DRAIN;return r.EOF}this.committed>this.data.length/2&&(this.lastLocation=this.location(),this.data=this.data.slice(this.committed),this.start=this.start-this.committed,this.committed=0)},matchWhile:function(e){if(this.eof&&this.start>=this.data.length)return\"\";var t=new RegExp(\"^\"+e+\"+\"),n=t.exec(this.slice());if(n){if(!this.eof&&n[0].length==this.data.length-this.start)throw r.DRAIN;return this.advance(n[0].length),n[0]}return\"\"},matchUntil:function(e){var t,n;n=this.slice();if(n===r.EOF)return\"\";if(t=(new RegExp(e+(this.eof?\"|$\":\"\"))).exec(n)){var i=this.data.slice(this.start,this.start+t.index);return this.advance(t.index),i.replace(/\\r/g,\"\\n\").replace(/\\n{2,}/g,\"\\n\")}throw r.DRAIN},append:function(e){this.data+=e},shift:function(e){if(!this.eof&&this.start+e>=this.data.length)throw r.DRAIN;if(this.eof&&this.start>=this.data.length)return r.EOF;var t=this.data.slice(this.start,this.start+e).toString();return this.advance(Math.min(e,this.data.length-this.start)),t},peek:function(e){if(!this.eof&&this.start+e>=this.data.length)throw r.DRAIN;return this.eof&&this.start>=this.data.length?r.EOF:this.data.slice(this.start,Math.min(this.start+e,this.data.length)).toString()},length:function(){return this.data.length-this.start-1},unget:function(e){if(e===r.EOF)return;this.start-=e.length},undo:function(){this.start=this.committed},commit:function(){this.committed=this.start},location:function(){var e=this.lastLocation.line,t=this.lastLocation.column,n=this.data.slice(0,this.committed),r=n.match(/\\n/g),i=r?e+r.length:e,s=r?n.length-n.lastIndexOf(\"\\n\")-1:t+n.length;return{line:i,column:s}}},n.InputStream=r},{}],4:[function(e,t,n){function i(e,t,n,r){this.localName=t,this.namespaceURI=e,this.attributes=n,this.node=r}function s(e,t){for(var n=0;n<e.attributes.length;n++)if(e.attributes[n].nodeName==t)return e.attributes[n].nodeValue;return null}var r={\"http://www.w3.org/1999/xhtml\":[\"address\",\"applet\",\"area\",\"article\",\"aside\",\"base\",\"basefont\",\"bgsound\",\"blockquote\",\"body\",\"br\",\"button\",\"caption\",\"center\",\"col\",\"colgroup\",\"dd\",\"details\",\"dir\",\"div\",\"dl\",\"dt\",\"embed\",\"fieldset\",\"figcaption\",\"figure\",\"footer\",\"form\",\"frame\",\"frameset\",\"h1\",\"h2\",\"h3\",\"h4\",\"h5\",\"h6\",\"head\",\"header\",\"hgroup\",\"hr\",\"html\",\"iframe\",\"img\",\"input\",\"isindex\",\"li\",\"link\",\"listing\",\"main\",\"marquee\",\"menu\",\"menuitem\",\"meta\",\"nav\",\"noembed\",\"noframes\",\"noscript\",\"object\",\"ol\",\"p\",\"param\",\"plaintext\",\"pre\",\"script\",\"section\",\"select\",\"source\",\"style\",\"summary\",\"table\",\"tbody\",\"td\",\"textarea\",\"tfoot\",\"th\",\"thead\",\"title\",\"tr\",\"track\",\"ul\",\"wbr\",\"xmp\"],\"http://www.w3.org/1998/Math/MathML\":[\"mi\",\"mo\",\"mn\",\"ms\",\"mtext\",\"annotation-xml\"],\"http://www.w3.org/2000/svg\":[\"foreignObject\",\"desc\",\"title\"]};i.prototype.isSpecial=function(){return this.namespaceURI in r&&r[this.namespaceURI].indexOf(this.localName)>-1},i.prototype.isFosterParenting=function(){return this.namespaceURI===\"http://www.w3.org/1999/xhtml\"?this.localName===\"table\"||this.localName===\"tbody\"||this.localName===\"tfoot\"||this.localName===\"thead\"||this.localName===\"tr\":!1},i.prototype.isNumberedHeader=function(){return this.namespaceURI===\"http://www.w3.org/1999/xhtml\"?this.localName===\"h1\"||this.localName===\"h2\"||this.localName===\"h3\"||this.localName===\"h4\"||this.localName===\"h5\"||this.localName===\"h6\":!1},i.prototype.isForeign=function(){return this.namespaceURI!=\"http://www.w3.org/1999/xhtml\"},i.prototype.isHtmlIntegrationPoint=function(){if(this.namespaceURI===\"http://www.w3.org/1998/Math/MathML\"){if(this.localName!==\"annotation-xml\")return!1;var e=s(this,\"encoding\");return e?(e=e.toLowerCase(),e===\"text/html\"||e===\"application/xhtml+xml\"):!1}return this.namespaceURI===\"http://www.w3.org/2000/svg\"?this.localName===\"foreignObject\"||this.localName===\"desc\"||this.localName===\"title\":!1},i.prototype.isMathMLTextIntegrationPoint=function(){return this.namespaceURI===\"http://www.w3.org/1998/Math/MathML\"?this.localName===\"mi\"||this.localName===\"mo\"||this.localName===\"mn\"||this.localName===\"ms\"||this.localName===\"mtext\":!1},n.StackItem=i},{}],5:[function(e,t,n){function s(e){return e===\" \"||e===\"\\n\"||e===\"\t\"||e===\"\\r\"||e===\"\\f\"}function o(e){return e>=\"A\"&&e<=\"Z\"||e>=\"a\"&&e<=\"z\"}function u(e){this._tokenHandler=e,this._state=u.DATA,this._inputStream=new r,this._currentToken=null,this._temporaryBuffer=\"\",this._additionalAllowedCharacter=\"\"}var r=e(\"./InputStream\").InputStream,i=e(\"./EntityParser\").EntityParser;u.prototype._parseError=function(e,t){this._tokenHandler.parseError(e,t)},u.prototype._emitToken=function(e){if(e.type===\"StartTag\")for(var t=1;t<e.data.length;t++)e.data[t].nodeName||e.data.splice(t--,1);else e.type===\"EndTag\"&&(e.selfClosing&&this._parseError(\"self-closing-flag-on-end-tag\"),e.data.length!==0&&this._parseError(\"attributes-in-end-tag\"));this._tokenHandler.processToken(e),e.type===\"StartTag\"&&e.selfClosing&&!this._tokenHandler.isSelfClosingFlagAcknowledged()&&this._parseError(\"non-void-element-with-trailing-solidus\",{name:e.name})},u.prototype._emitCurrentToken=function(){this._state=u.DATA,this._emitToken(this._currentToken)},u.prototype._currentAttribute=function(){return this._currentToken.data[this._currentToken.data.length-1]},u.prototype.setState=function(e){this._state=e},u.prototype.tokenize=function(e){function n(e){var n=e.char();if(n===r.EOF)return t._emitToken({type:\"EOF\",data:null}),!1;if(n===\"&\")t.setState(a);else if(n===\"<\")t.setState(j);else if(n===\"\\0\")t._emitToken({type:\"Characters\",data:n}),e.commit();else{var i=e.matchUntil(\"&|<|\\0\");t._emitToken({type:\"Characters\",data:n+i}),e.commit()}return!0}function a(e){var r=i.consumeEntity(e,t);return t.setState(n),t._emitToken({type:\"Characters\",data:r||\"&\"}),!0}function f(e){var n=e.char();if(n===r.EOF)return t._emitToken({type:\"EOF\",data:null}),!1;if(n===\"&\")t.setState(l);else if(n===\"<\")t.setState(d);else if(n===\"\\0\")t._parseError(\"invalid-codepoint\"),t._emitToken({type:\"Characters\",data:\"\\ufffd\"}),e.commit();else{var i=e.matchUntil(\"&|<|\\0\");t._emitToken({type:\"Characters\",data:n+i}),e.commit()}return!0}function l(e){var n=i.consumeEntity(e,t);return t.setState(f),t._emitToken({type:\"Characters\",data:n||\"&\"}),!0}function c(e){var n=e.char();if(n===r.EOF)return t._emitToken({type:\"EOF\",data:null}),!1;if(n===\"<\")t.setState(g);else if(n===\"\\0\")t._parseError(\"invalid-codepoint\"),t._emitToken({type:\"Characters\",data:\"\\ufffd\"}),e.commit();else{var i=e.matchUntil(\"<|\\0\");t._emitToken({type:\"Characters\",data:n+i})}return!0}function h(e){var n=e.char();if(n===r.EOF)return t._emitToken({type:\"EOF\",data:null}),!1;if(n===\"\\0\")t._parseError(\"invalid-codepoint\"),t._emitToken({type:\"Characters\",data:\"\\ufffd\"}),e.commit();else{var i=e.matchUntil(\"\\0\");t._emitToken({type:\"Characters\",data:n+i})}return!0}function p(e){var n=e.char();if(n===r.EOF)return t._emitToken({type:\"EOF\",data:null}),!1;if(n===\"<\")t.setState(w);else if(n===\"\\0\")t._parseError(\"invalid-codepoint\"),t._emitToken({type:\"Characters\",data:\"\\ufffd\"}),e.commit();else{var i=e.matchUntil(\"<|\\0\");t._emitToken({type:\"Characters\",data:n+i})}return!0}function d(e){var n=e.char();return n===\"/\"?(this._temporaryBuffer=\"\",t.setState(v)):(t._emitToken({type:\"Characters\",data:\"<\"}),e.unget(n),t.setState(f)),!0}function v(e){var n=e.char();return o(n)?(this._temporaryBuffer+=n,t.setState(m)):(t._emitToken({type:\"Characters\",data:\"</\"}),e.unget(n),t.setState(f)),!0}function m(e){var r=t._currentToken&&t._currentToken.name===this._temporaryBuffer.toLowerCase(),i=e.char();return s(i)&&r?(t._currentToken={type:\"EndTag\",name:this._temporaryBuffer,data:[],selfClosing:!1},t.setState(q)):i===\"/\"&&r?(t._currentToken={type:\"EndTag\",name:this._temporaryBuffer,data:[],selfClosing:!1},t.setState(K)):i===\">\"&&r?(t._currentToken={type:\"EndTag\",name:this._temporaryBuffer,data:[],selfClosing:!1},t._emitCurrentToken(),t.setState(n)):o(i)?(this._temporaryBuffer+=i,e.commit()):(t._emitToken({type:\"Characters\",data:\"</\"+this._temporaryBuffer}),e.unget(i),t.setState(f)),!0}function g(e){var n=e.char();return n===\"/\"?(this._temporaryBuffer=\"\",t.setState(y)):(t._emitToken({type:\"Characters\",data:\"<\"}),e.unget(n),t.setState(c)),!0}function y(e){var n=e.char();return o(n)?(this._temporaryBuffer+=n,t.setState(b)):(t._emitToken({type:\"Characters\",data:\"</\"}),e.unget(n),t.setState(c)),!0}function b(e){var r=t._currentToken&&t._currentToken.name===this._temporaryBuffer.toLowerCase(),i=e.char();return s(i)&&r?(t._currentToken={type:\"EndTag\",name:this._temporaryBuffer,data:[],selfClosing:!1},t.setState(q)):i===\"/\"&&r?(t._currentToken={type:\"EndTag\",name:this._temporaryBuffer,data:[],selfClosing:!1},t.setState(K)):i===\">\"&&r?(t._currentToken={type:\"EndTag\",name:this._temporaryBuffer,data:[],selfClosing:!1},t._emitCurrentToken(),t.setState(n)):o(i)?(this._temporaryBuffer+=i,e.commit()):(t._emitToken({type:\"Characters\",data:\"</\"+this._temporaryBuffer}),e.unget(i),t.setState(c)),!0}function w(e){var n=e.char();return n===\"/\"?(this._temporaryBuffer=\"\",t.setState(E)):n===\"!\"?(t._emitToken({type:\"Characters\",data:\"<!\"}),t.setState(x)):(t._emitToken({type:\"Characters\",data:\"<\"}),e.unget(n),t.setState(p)),!0}function E(e){var n=e.char();return o(n)?(this._temporaryBuffer+=n,t.setState(S)):(t._emitToken({type:\"Characters\",data:\"</\"}),e.unget(n),t.setState(p)),!0}function S(e){var n=t._currentToken&&t._currentToken.name===this._temporaryBuffer.toLowerCase(),r=e.char();return s(r)&&n?(t._currentToken={type:\"EndTag\",name:\"script\",data:[],selfClosing:!1},t.setState(q)):r===\"/\"&&n?(t._currentToken={type:\"EndTag\",name:\"script\",data:[],selfClosing:!1},t.setState(K)):r===\">\"&&n?(t._currentToken={type:\"EndTag\",name:\"script\",data:[],selfClosing:!1},t._emitCurrentToken()):o(r)?(this._temporaryBuffer+=r,e.commit()):(t._emitToken({type:\"Characters\",data:\"</\"+this._temporaryBuffer}),e.unget(r),t.setState(p)),!0}function x(e){var n=e.char();return n===\"-\"?(t._emitToken({type:\"Characters\",data:\"-\"}),t.setState(T)):(e.unget(n),t.setState(p)),!0}function T(e){var n=e.char();return n===\"-\"?(t._emitToken({type:\"Characters\",data:\"-\"}),t.setState(k)):(e.unget(n),t.setState(p)),!0}function N(e){var i=e.char();if(i===r.EOF)e.unget(i),t.setState(n);else if(i===\"-\")t._emitToken({type:\"Characters\",data:\"-\"}),t.setState(C);else if(i===\"<\")t.setState(L);else if(i===\"\\0\")t._parseError(\"invalid-codepoint\"),t._emitToken({type:\"Characters\",data:\"\\ufffd\"}),e.commit();else{var s=e.matchUntil(\"<|-|\\0\");t._emitToken({type:\"Characters\",data:i+s})}return!0}function C(e){var i=e.char();return i===r.EOF?(e.unget(i),t.setState(n)):i===\"-\"?(t._emitToken({type:\"Characters\",data:\"-\"}),t.setState(k)):i===\"<\"?t.setState(L):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._emitToken({type:\"Characters\",data:\"\\ufffd\"}),t.setState(N)):(t._emitToken({type:\"Characters\",data:i}),t.setState(N)),!0}function k(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-script\"),e.unget(i),t.setState(n)):i===\"<\"?t.setState(L):i===\">\"?(t._emitToken({type:\"Characters\",data:\">\"}),t.setState(p)):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._emitToken({type:\"Characters\",data:\"\\ufffd\"}),t.setState(N)):(t._emitToken({type:\"Characters\",data:i}),t.setState(N)),!0}function L(e){var n=e.char();return n===\"/\"?(this._temporaryBuffer=\"\",t.setState(A)):o(n)?(t._emitToken({type:\"Characters\",data:\"<\"+n}),this._temporaryBuffer=n,t.setState(M)):(t._emitToken({type:\"Characters\",data:\"<\"}),e.unget(n),t.setState(N)),!0}function A(e){var n=e.char();return o(n)?(this._temporaryBuffer=n,t.setState(O)):(t._emitToken({type:\"Characters\",data:\"</\"}),e.unget(n),t.setState(N)),!0}function O(e){var r=t._currentToken&&t._currentToken.name===this._temporaryBuffer.toLowerCase(),i=e.char();return s(i)&&r?(t._currentToken={type:\"EndTag\",name:\"script\",data:[],selfClosing:!1},t.setState(q)):i===\"/\"&&r?(t._currentToken={type:\"EndTag\",name:\"script\",data:[],selfClosing:!1},t.setState(K)):i===\">\"&&r?(t._currentToken={type:\"EndTag\",name:\"script\",data:[],selfClosing:!1},t.setState(n),t._emitCurrentToken()):o(i)?(this._temporaryBuffer+=i,e.commit()):(t._emitToken({type:\"Characters\",data:\"</\"+this._temporaryBuffer}),e.unget(i),t.setState(N)),!0}function M(e){var n=e.char();return s(n)||n===\"/\"||n===\">\"?(t._emitToken({type:\"Characters\",data:n}),this._temporaryBuffer.toLowerCase()===\"script\"?t.setState(_):t.setState(N)):o(n)?(t._emitToken({type:\"Characters\",data:n}),this._temporaryBuffer+=n,e.commit()):(e.unget(n),t.setState(N)),!0}function _(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-script\"),e.unget(i),t.setState(n)):i===\"-\"?(t._emitToken({type:\"Characters\",data:\"-\"}),t.setState(D)):i===\"<\"?(t._emitToken({type:\"Characters\",data:\"<\"}),t.setState(H)):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._emitToken({type:\"Characters\",data:\"\\ufffd\"}),e.commit()):(t._emitToken({type:\"Characters\",data:i}),e.commit()),!0}function D(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-script\"),e.unget(i),t.setState(n)):i===\"-\"?(t._emitToken({type:\"Characters\",data:\"-\"}),t.setState(P)):i===\"<\"?(t._emitToken({type:\"Characters\",data:\"<\"}),t.setState(H)):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._emitToken({type:\"Characters\",data:\"\\ufffd\"}),t.setState(_)):(t._emitToken({type:\"Characters\",data:i}),t.setState(_)),!0}function P(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-script\"),e.unget(i),t.setState(n)):i===\"-\"?(t._emitToken({type:\"Characters\",data:\"-\"}),e.commit()):i===\"<\"?(t._emitToken({type:\"Characters\",data:\"<\"}),t.setState(H)):i===\">\"?(t._emitToken({type:\"Characters\",data:\">\"}),t.setState(p)):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._emitToken({type:\"Characters\",data:\"\\ufffd\"}),t.setState(_)):(t._emitToken({type:\"Characters\",data:i}),t.setState(_)),!0}function H(e){var n=e.char();return n===\"/\"?(t._emitToken({type:\"Characters\",data:\"/\"}),this._temporaryBuffer=\"\",t.setState(B)):(e.unget(n),t.setState(_)),!0}function B(e){var n=e.char();return s(n)||n===\"/\"||n===\">\"?(t._emitToken({type:\"Characters\",data:n}),this._temporaryBuffer.toLowerCase()===\"script\"?t.setState(N):t.setState(_)):o(n)?(t._emitToken({type:\"Characters\",data:n}),this._temporaryBuffer+=n,e.commit()):(e.unget(n),t.setState(_)),!0}function j(e){var i=e.char();return i===r.EOF?(t._parseError(\"bare-less-than-sign-at-eof\"),t._emitToken({type:\"Characters\",data:\"<\"}),e.unget(i),t.setState(n)):o(i)?(t._currentToken={type:\"StartTag\",name:i.toLowerCase(),data:[]},t.setState(I)):i===\"!\"?t.setState(G):i===\"/\"?t.setState(F):i===\">\"?(t._parseError(\"expected-tag-name-but-got-right-bracket\"),t._emitToken({type:\"Characters\",data:\"<>\"}),t.setState(n)):i===\"?\"?(t._parseError(\"expected-tag-name-but-got-question-mark\"),e.unget(i),t.setState(Q)):(t._parseError(\"expected-tag-name\"),t._emitToken({type:\"Characters\",data:\"<\"}),e.unget(i),t.setState(n)),!0}function F(e){var i=e.char();return i===r.EOF?(t._parseError(\"expected-closing-tag-but-got-eof\"),t._emitToken({type:\"Characters\",data:\"</\"}),e.unget(i),t.setState(n)):o(i)?(t._currentToken={type:\"EndTag\",name:i.toLowerCase(),data:[]},t.setState(I)):i===\">\"?(t._parseError(\"expected-closing-tag-but-got-right-bracket\"),t.setState(n)):(t._parseError(\"expected-closing-tag-but-got-char\",{data:i}),e.unget(i),t.setState(Q)),!0}function I(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-tag-name\"),e.unget(i),t.setState(n)):s(i)?t.setState(q):o(i)?t._currentToken.name+=i.toLowerCase():i===\">\"?t._emitCurrentToken():i===\"/\"?t.setState(K):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentToken.name+=\"\\ufffd\"):t._currentToken.name+=i,e.commit(),!0}function q(e){var i=e.char();if(i===r.EOF)t._parseError(\"expected-attribute-name-but-got-eof\"),e.unget(i),t.setState(n);else{if(s(i))return!0;o(i)?(t._currentToken.data.push({nodeName:i.toLowerCase(),nodeValue:\"\"}),t.setState(R)):i===\">\"?t._emitCurrentToken():i===\"/\"?t.setState(K):i===\"'\"||i==='\"'||i===\"=\"||i===\"<\"?(t._parseError(\"invalid-character-in-attribute-name\"),t._currentToken.data.push({nodeName:i,nodeValue:\"\"}),t.setState(R)):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentToken.data.push({nodeName:\"\\ufffd\",nodeValue:\"\"})):(t._currentToken.data.push({nodeName:i,nodeValue:\"\"}),t.setState(R))}return!0}function R(e){var i=e.char(),u=!0,a=!1;i===r.EOF?(t._parseError(\"eof-in-attribute-name\"),e.unget(i),t.setState(n),a=!0):i===\"=\"?t.setState(z):o(i)?(t._currentAttribute().nodeName+=i.toLowerCase(),u=!1):i===\">\"?a=!0:s(i)?t.setState(U):i===\"/\"?t.setState(K):i===\"'\"||i==='\"'?(t._parseError(\"invalid-character-in-attribute-name\"),t._currentAttribute().nodeName+=i,u=!1):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentAttribute().nodeName+=\"\\ufffd\"):(t._currentAttribute().nodeName+=i,u=!1);if(u){var f=t._currentToken.data,l=f[f.length-1];for(var c=f.length-2;c>=0;c--)if(l.nodeName===f[c].nodeName){t._parseError(\"duplicate-attribute\",{name:l.nodeName}),l.nodeName=null;break}a&&t._emitCurrentToken()}else e.commit();return!0}function U(e){var i=e.char();if(i===r.EOF)t._parseError(\"expected-end-of-tag-but-got-eof\"),e.unget(i),t.setState(n);else{if(s(i))return!0;i===\"=\"?t.setState(z):i===\">\"?t._emitCurrentToken():o(i)?(t._currentToken.data.push({nodeName:i,nodeValue:\"\"}),t.setState(R)):i===\"/\"?t.setState(K):i===\"'\"||i==='\"'||i===\"<\"?(t._parseError(\"invalid-character-after-attribute-name\"),t._currentToken.data.push({nodeName:i,nodeValue:\"\"}),t.setState(R)):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentToken.data.push({nodeName:\"\\ufffd\",nodeValue:\"\"})):(t._currentToken.data.push({nodeName:i,nodeValue:\"\"}),t.setState(R))}return!0}function z(e){var i=e.char();if(i===r.EOF)t._parseError(\"expected-attribute-value-but-got-eof\"),e.unget(i),t.setState(n);else{if(s(i))return!0;i==='\"'?t.setState(W):i===\"&\"?(t.setState(V),e.unget(i)):i===\"'\"?t.setState(X):i===\">\"?(t._parseError(\"expected-attribute-value-but-got-right-bracket\"),t._emitCurrentToken()):i===\"=\"||i===\"<\"||i===\"`\"?(t._parseError(\"unexpected-character-in-unquoted-attribute-value\"),t._currentAttribute().nodeValue+=i,t.setState(V)):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentAttribute().nodeValue+=\"\\ufffd\"):(t._currentAttribute().nodeValue+=i,t.setState(V))}return!0}function W(e){var i=e.char();if(i===r.EOF)t._parseError(\"eof-in-attribute-value-double-quote\"),e.unget(i),t.setState(n);else if(i==='\"')t.setState(J);else if(i===\"&\")this._additionalAllowedCharacter='\"',t.setState($);else if(i===\"\\0\")t._parseError(\"invalid-codepoint\"),t._currentAttribute().nodeValue+=\"\\ufffd\";else{var s=e.matchUntil('[\\0\"&]');i+=s,t._currentAttribute().nodeValue+=i}return!0}function X(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-attribute-value-single-quote\"),e.unget(i),t.setState(n)):i===\"'\"?t.setState(J):i===\"&\"?(this._additionalAllowedCharacter=\"'\",t.setState($)):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentAttribute().nodeValue+=\"\\ufffd\"):t._currentAttribute().nodeValue+=i+e.matchUntil(\"\\0|['&]\"),!0}function V(e){var i=e.char();if(i===r.EOF)t._parseError(\"eof-after-attribute-value\"),e.unget(i),t.setState(n);else if(s(i))t.setState(q);else if(i===\"&\")this._additionalAllowedCharacter=\">\",t.setState($);else if(i===\">\")t._emitCurrentToken();else if(i==='\"'||i===\"'\"||i===\"=\"||i===\"`\"||i===\"<\")t._parseError(\"unexpected-character-in-unquoted-attribute-value\"),t._currentAttribute().nodeValue+=i,e.commit();else if(i===\"\\0\")t._parseError(\"invalid-codepoint\"),t._currentAttribute().nodeValue+=\"\\ufffd\";else{var o=e.matchUntil(\"\\0|[\t\\n\u000b\\f \\r&<>\\\"'=`]\");o===r.EOF&&(t._parseError(\"eof-in-attribute-value-no-quotes\"),t._emitCurrentToken()),e.commit(),t._currentAttribute().nodeValue+=i+o}return!0}function $(e){var n=i.consumeEntity(e,t,this._additionalAllowedCharacter);return this._currentAttribute().nodeValue+=n||\"&\",this._additionalAllowedCharacter==='\"'?t.setState(W):this._additionalAllowedCharacter===\"'\"?t.setState(X):this._additionalAllowedCharacter===\">\"&&t.setState(V),!0}function J(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-after-attribute-value\"),e.unget(i),t.setState(n)):s(i)?t.setState(q):i===\">\"?(t.setState(n),t._emitCurrentToken()):i===\"/\"?t.setState(K):(t._parseError(\"unexpected-character-after-attribute-value\"),e.unget(i),t.setState(q)),!0}function K(e){var i=e.char();return i===r.EOF?(t._parseError(\"unexpected-eof-after-solidus-in-tag\"),e.unget(i),t.setState(n)):i===\">\"?(t._currentToken.selfClosing=!0,t.setState(n),t._emitCurrentToken()):(t._parseError(\"unexpected-character-after-solidus-in-tag\"),e.unget(i),t.setState(q)),!0}function Q(e){var r=e.matchUntil(\">\");return r=r.replace(/\\u0000/g,\"\\ufffd\"),e.char(),t._emitToken({type:\"Comment\",data:r}),t.setState(n),!0}function G(e){var n=e.shift(2);if(n===\"--\")t._currentToken={type:\"Comment\",data:\"\"},t.setState(Z);else{var i=e.shift(5);if(i===r.EOF||n===r.EOF)return t._parseError(\"expected-dashes-or-doctype\"),t.setState(Q),e.unget(n),!0;n+=i,n.toUpperCase()===\"DOCTYPE\"?(t._currentToken={type:\"Doctype\",name:\"\",publicId:null,systemId:null,forceQuirks:!1},t.setState(st)):t._tokenHandler.isCdataSectionAllowed()&&n===\"[CDATA[\"?t.setState(Y):(t._parseError(\"expected-dashes-or-doctype\"),e.unget(n),t.setState(Q))}return!0}function Y(e){var r=e.matchUntil(\"]]>\");return e.shift(3),r&&t._emitToken({type:\"Characters\",data:r}),t.setState(n),!0}function Z(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-comment\"),t._emitToken(t._currentToken),e.unget(i),t.setState(n)):i===\"-\"?t.setState(et):i===\">\"?(t._parseError(\"incorrect-comment\"),t._emitToken(t._currentToken),t.setState(n)):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentToken.data+=\"\\ufffd\"):(t._currentToken.data+=i,t.setState(tt)),!0}function et(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-comment\"),t._emitToken(t._currentToken),e.unget(i),t.setState(n)):i===\"-\"?t.setState(rt):i===\">\"?(t._parseError(\"incorrect-comment\"),t._emitToken(t._currentToken),t.setState(n)):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentToken.data+=\"\\ufffd\"):(t._currentToken.data+=\"-\"+i,t.setState(tt)),!0}function tt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-comment\"),t._emitToken(t._currentToken),e.unget(i),t.setState(n)):i===\"-\"?t.setState(nt):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentToken.data+=\"\\ufffd\"):(t._currentToken.data+=i,e.commit()),!0}function nt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-comment-end-dash\"),t._emitToken(t._currentToken),e.unget(i),t.setState(n)):i===\"-\"?t.setState(rt):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentToken.data+=\"-\\ufffd\",t.setState(tt)):(t._currentToken.data+=\"-\"+i+e.matchUntil(\"\\0|-\"),e.char()),!0}function rt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-comment-double-dash\"),t._emitToken(t._currentToken),e.unget(i),t.setState(n)):i===\">\"?(t._emitToken(t._currentToken),t.setState(n)):i===\"!\"?(t._parseError(\"unexpected-bang-after-double-dash-in-comment\"),t.setState(it)):i===\"-\"?(t._parseError(\"unexpected-dash-after-double-dash-in-comment\"),t._currentToken.data+=i):i===\"\\0\"?(t._parseError(\"invalid-codepoint\"),t._currentToken.data+=\"--\\ufffd\",t.setState(tt)):(t._parseError(\"unexpected-char-in-comment\"),t._currentToken.data+=\"--\"+i,t.setState(tt)),!0}function it(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-comment-end-bang-state\"),t._emitToken(t._currentToken),e.unget(i),t.setState(n)):i===\">\"?(t._emitToken(t._currentToken),t.setState(n)):i===\"-\"?(t._currentToken.data+=\"--!\",t.setState(nt)):(t._currentToken.data+=\"--!\"+i,t.setState(tt)),!0}function st(e){var i=e.char();return i===r.EOF?(t._parseError(\"expected-doctype-name-but-got-eof\"),t._currentToken.forceQuirks=!0,e.unget(i),t.setState(n),t._emitCurrentToken()):s(i)?t.setState(ot):(t._parseError(\"need-space-after-doctype\"),e.unget(i),t.setState(ot)),!0}function ot(e){var i=e.char();return i===r.EOF?(t._parseError(\"expected-doctype-name-but-got-eof\"),t._currentToken.forceQuirks=!0,e.unget(i),t.setState(n),t._emitCurrentToken()):s(i)||(i===\">\"?(t._parseError(\"expected-doctype-name-but-got-right-bracket\"),t._currentToken.forceQuirks=!0,t.setState(n),t._emitCurrentToken()):(o(i)&&(i=i.toLowerCase()),t._currentToken.name=i,t.setState(ut))),!0}function ut(e){var i=e.char();return i===r.EOF?(t._currentToken.forceQuirks=!0,e.unget(i),t._parseError(\"eof-in-doctype-name\"),t.setState(n),t._emitCurrentToken()):s(i)?t.setState(at):i===\">\"?(t.setState(n),t._emitCurrentToken()):(o(i)&&(i=i.toLowerCase()),t._currentToken.name+=i,e.commit()),!0}function at(e){var i=e.char();if(i===r.EOF)t._currentToken.forceQuirks=!0,e.unget(i),t._parseError(\"eof-in-doctype\"),t.setState(n),t._emitCurrentToken();else if(!s(i))if(i===\">\")t.setState(n),t._emitCurrentToken();else{if([\"p\",\"P\"].indexOf(i)>-1){var o=[[\"u\",\"U\"],[\"b\",\"B\"],[\"l\",\"L\"],[\"i\",\"I\"],[\"c\",\"C\"]],u=o.every(function(t){return i=e.char(),t.indexOf(i)>-1});if(u)return t.setState(ft),!0}else if([\"s\",\"S\"].indexOf(i)>-1){var o=[[\"y\",\"Y\"],[\"s\",\"S\"],[\"t\",\"T\"],[\"e\",\"E\"],[\"m\",\"M\"]],u=o.every(function(t){return i=e.char(),t.indexOf(i)>-1});if(u)return t.setState(vt),!0}e.unget(i),t._currentToken.forceQuirks=!0,i===r.EOF?(t._parseError(\"eof-in-doctype\"),e.unget(i),t.setState(n),t._emitCurrentToken()):(t._parseError(\"expected-space-or-right-bracket-in-doctype\",{data:i}),t.setState(wt))}return!0}function ft(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,e.unget(i),t.setState(n),t._emitCurrentToken()):s(i)?t.setState(lt):i===\"'\"||i==='\"'?(t._parseError(\"unexpected-char-in-doctype\"),e.unget(i),t.setState(lt)):(e.unget(i),t.setState(lt)),!0}function lt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,e.unget(i),t.setState(n),t._emitCurrentToken()):s(i)||(i==='\"'?(t._currentToken.publicId=\"\",t.setState(ct)):i===\"'\"?(t._currentToken.publicId=\"\",t.setState(ht)):i===\">\"?(t._parseError(\"unexpected-end-of-doctype\"),t._currentToken.forceQuirks=!0,t.setState(n),t._emitCurrentToken()):(t._parseError(\"unexpected-char-in-doctype\"),t._currentToken.forceQuirks=!0,t.setState(wt))),!0}function ct(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,e.unget(i),t.setState(n),t._emitCurrentToken()):i==='\"'?t.setState(pt):i===\">\"?(t._parseError(\"unexpected-end-of-doctype\"),t._currentToken.forceQuirks=!0,t.setState(n),t._emitCurrentToken()):t._currentToken.publicId+=i,!0}function ht(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,e.unget(i),t.setState(n),t._emitCurrentToken()):i===\"'\"?t.setState(pt):i===\">\"?(t._parseError(\"unexpected-end-of-doctype\"),t._currentToken.forceQuirks=!0,t.setState(n),t._emitCurrentToken()):t._currentToken.publicId+=i,!0}function pt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,t._emitCurrentToken(),e.unget(i),t.setState(n)):s(i)?t.setState(dt):i===\">\"?(t.setState(n),t._emitCurrentToken()):i==='\"'?(t._parseError(\"unexpected-char-in-doctype\"),t._currentToken.systemId=\"\",t.setState(gt)):i===\"'\"?(t._parseError(\"unexpected-char-in-doctype\"),t._currentToken.systemId=\"\",t.setState(yt)):(t._parseError(\"unexpected-char-in-doctype\"),t._currentToken.forceQuirks=!0,t.setState(wt)),!0}function dt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,t._emitCurrentToken(),e.unget(i),t.setState(n)):s(i)||(i===\">\"?(t._emitCurrentToken(),t.setState(n)):i==='\"'?(t._currentToken.systemId=\"\",t.setState(gt)):i===\"'\"?(t._currentToken.systemId=\"\",t.setState(yt)):(t._parseError(\"unexpected-char-in-doctype\"),t._currentToken.forceQuirks=!0,t.setState(wt))),!0}function vt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,t._emitCurrentToken(),e.unget(i),t.setState(n)):s(i)?t.setState(mt):i===\"'\"||i==='\"'?(t._parseError(\"unexpected-char-in-doctype\"),e.unget(i),t.setState(mt)):(e.unget(i),t.setState(mt)),!0}function mt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,t._emitCurrentToken(),e.unget(i),t.setState(n)):s(i)||(i==='\"'?(t._currentToken.systemId=\"\",t.setState(gt)):i===\"'\"?(t._currentToken.systemId=\"\",t.setState(yt)):i===\">\"?(t._parseError(\"unexpected-end-of-doctype\"),t._currentToken.forceQuirks=!0,t._emitCurrentToken(),t.setState(n)):(t._parseError(\"unexpected-char-in-doctype\"),t._currentToken.forceQuirks=!0,t.setState(wt))),!0}function gt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,t._emitCurrentToken(),e.unget(i),t.setState(n)):i==='\"'?t.setState(bt):i===\">\"?(t._parseError(\"unexpected-end-of-doctype\"),t._currentToken.forceQuirks=!0,t._emitCurrentToken(),t.setState(n)):t._currentToken.systemId+=i,!0}function yt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,t._emitCurrentToken(),e.unget(i),t.setState(n)):i===\"'\"?t.setState(bt):i===\">\"?(t._parseError(\"unexpected-end-of-doctype\"),t._currentToken.forceQuirks=!0,t._emitCurrentToken(),t.setState(n)):t._currentToken.systemId+=i,!0}function bt(e){var i=e.char();return i===r.EOF?(t._parseError(\"eof-in-doctype\"),t._currentToken.forceQuirks=!0,t._emitCurrentToken(),e.unget(i),t.setState(n)):s(i)||(i===\">\"?(t._emitCurrentToken(),t.setState(n)):(t._parseError(\"unexpected-char-in-doctype\"),t.setState(wt))),!0}function wt(e){var i=e.char();return i===r.EOF?(e.unget(i),t._emitCurrentToken(),t.setState(n)):i===\">\"&&(t._emitCurrentToken(),t.setState(n)),!0}u.DATA=n,u.RCDATA=f,u.RAWTEXT=c,u.SCRIPT_DATA=p,u.PLAINTEXT=h,this._state=u.DATA,this._inputStream.append(e),this._tokenHandler.startTokenization(this),this._inputStream.eof=!0;var t=this;while(this._state.call(this,this._inputStream));},Object.defineProperty(u.prototype,\"lineNumber\",{get:function(){return this._inputStream.location().line}}),Object.defineProperty(u.prototype,\"columnNumber\",{get:function(){return this._inputStream.location().column}}),n.Tokenizer=u},{\"./EntityParser\":2,\"./InputStream\":3}],6:[function(e,t,n){function c(e){return e===\" \"||e===\"\\n\"||e===\"\t\"||e===\"\\r\"||e===\"\\f\"}function h(e){return c(e)||e===\"\\ufffd\"}function p(e){for(var t=0;t<e.length;t++){var n=e[t];if(!c(n))return!1}return!0}function d(e){for(var t=0;t<e.length;t++){var n=e[t];if(!h(n))return!1}return!0}function v(e,t){for(var n=0;n<e.attributes.length;n++){var r=e.attributes[n];if(r.nodeName===t)return r}return null}function m(e){this.characters=e,this.current=0,this.end=this.characters.length}function g(){this.tokenizer=null,this.errorHandler=null,this.scriptingEnabled=!1,this.document=null,this.head=null,this.form=null,this.openElements=new a,this.activeFormattingElements=[],this.insertionMode=null,this.insertionModeName=\"\",this.originalInsertionMode=\"\",this.inQuirksMode=!1,this.compatMode=\"no quirks\",this.framesetOk=!0,this.redirectAttachToFosterParent=!1,this.selfClosingFlagAcknowledged=!1,this.context=\"\",this.pendingTableCharacters=[],this.shouldSkipLeadingNewline=!1;var e=this,t=this.insertionModes={};t.base={end_tag_handlers:{\"-default\":\"endTagOther\"},start_tag_handlers:{\"-default\":\"startTagOther\"},processEOF:function(){e.generateImpliedEndTags(),e.openElements.length>2?e.parseError(\"expected-closing-tag-but-got-eof\"):e.openElements.length==2&&e.openElements.item(1).localName!=\"body\"?e.parseError(\"expected-closing-tag-but-got-eof\"):e.context&&e.openElements.length>1},processComment:function(t){e.insertComment(t,e.currentStackItem().node)},processDoctype:function(t,n,r,i){e.parseError(\"unexpected-doctype\")},processStartTag:function(e,t,n){if(this[this.start_tag_handlers[e]])this[this.start_tag_handlers[e]](e,t,n);else{if(!this[this.start_tag_handlers[\"-default\"]])throw new Error(\"No handler found for \"+e);this[this.start_tag_handlers[\"-default\"]](e,t,n)}},processEndTag:function(e){if(this[this.end_tag_handlers[e]])this[this.end_tag_handlers[e]](e);else{if(!this[this.end_tag_handlers[\"-default\"]])throw new Error(\"No handler found for \"+e);this[this.end_tag_handlers[\"-default\"]](e)}},startTagHtml:function(e,n){t.inBody.startTagHtml(e,n)}},t.initial=Object.create(t.base),t.initial.processEOF=function(){e.parseError(\"expected-doctype-but-got-eof\"),this.anythingElse(),e.insertionMode.processEOF()},t.initial.processComment=function(t){e.insertComment(t,e.document)},t.initial.processDoctype=function(t,n,r,i){function s(e){return n.toLowerCase().indexOf(e)===0}e.insertDoctype(t||\"\",n||\"\",r||\"\"),i||t!=\"html\"||n!=null&&([\"+//silmaril//dtd html pro v0r11 19970101//\",\"-//advasoft ltd//dtd html 3.0 aswedit + extensions//\",\"-//as//dtd html 3.0 aswedit + extensions//\",\"-//ietf//dtd html 2.0 level 1//\",\"-//ietf//dtd html 2.0 level 2//\",\"-//ietf//dtd html 2.0 strict level 1//\",\"-//ietf//dtd html 2.0 strict level 2//\",\"-//ietf//dtd html 2.0 strict//\",\"-//ietf//dtd html 2.0//\",\"-//ietf//dtd html 2.1e//\",\"-//ietf//dtd html 3.0//\",\"-//ietf//dtd html 3.0//\",\"-//ietf//dtd html 3.2 final//\",\"-//ietf//dtd html 3.2//\",\"-//ietf//dtd html 3//\",\"-//ietf//dtd html level 0//\",\"-//ietf//dtd html level 0//\",\"-//ietf//dtd html level 1//\",\"-//ietf//dtd html level 1//\",\"-//ietf//dtd html level 2//\",\"-//ietf//dtd html level 2//\",\"-//ietf//dtd html level 3//\",\"-//ietf//dtd html level 3//\",\"-//ietf//dtd html strict level 0//\",\"-//ietf//dtd html strict level 0//\",\"-//ietf//dtd html strict level 1//\",\"-//ietf//dtd html strict level 1//\",\"-//ietf//dtd html strict level 2//\",\"-//ietf//dtd html strict level 2//\",\"-//ietf//dtd html strict level 3//\",\"-//ietf//dtd html strict level 3//\",\"-//ietf//dtd html strict//\",\"-//ietf//dtd html strict//\",\"-//ietf//dtd html strict//\",\"-//ietf//dtd html//\",\"-//ietf//dtd html//\",\"-//ietf//dtd html//\",\"-//metrius//dtd metrius presentational//\",\"-//microsoft//dtd internet explorer 2.0 html strict//\",\"-//microsoft//dtd internet explorer 2.0 html//\",\"-//microsoft//dtd internet explorer 2.0 tables//\",\"-//microsoft//dtd internet explorer 3.0 html strict//\",\"-//microsoft//dtd internet explorer 3.0 html//\",\"-//microsoft//dtd internet explorer 3.0 tables//\",\"-//netscape comm. corp.//dtd html//\",\"-//netscape comm. corp.//dtd strict html//\",\"-//o'reilly and associates//dtd html 2.0//\",\"-//o'reilly and associates//dtd html extended 1.0//\",\"-//spyglass//dtd html 2.0 extended//\",\"-//sq//dtd html 2.0 hotmetal + extensions//\",\"-//sun microsystems corp.//dtd hotjava html//\",\"-//sun microsystems corp.//dtd hotjava strict html//\",\"-//w3c//dtd html 3 1995-03-24//\",\"-//w3c//dtd html 3.2 draft//\",\"-//w3c//dtd html 3.2 final//\",\"-//w3c//dtd html 3.2//\",\"-//w3c//dtd html 3.2s draft//\",\"-//w3c//dtd html 4.0 frameset//\",\"-//w3c//dtd html 4.0 transitional//\",\"-//w3c//dtd html experimental 19960712//\",\"-//w3c//dtd html experimental 970421//\",\"-//w3c//dtd w3 html//\",\"-//w3o//dtd w3 html 3.0//\",\"-//webtechs//dtd mozilla html 2.0//\",\"-//webtechs//dtd mozilla html//\",\"html\"].some(s)||[\"-//w3o//dtd w3 html strict 3.0//en//\",\"-/w3c/dtd html 4.0 transitional/en\",\"html\"].indexOf(n.toLowerCase())>-1||r==null&&[\"-//w3c//dtd html 4.01 transitional//\",\"-//w3c//dtd html 4.01 frameset//\"].some(s))||r!=null&&r.toLowerCase()==\"http://www.ibm.com/data/dtd/v11/ibmxhtml1-transitional.dtd\"?(e.compatMode=\"quirks\",e.parseError(\"quirky-doctype\")):n!=null&&([\"-//w3c//dtd xhtml 1.0 transitional//\",\"-//w3c//dtd xhtml 1.0 frameset//\"].some(s)||r!=null&&[\"-//w3c//dtd html 4.01 transitional//\",\"-//w3c//dtd html 4.01 frameset//\"].indexOf(n.toLowerCase())>-1)?(e.compatMode=\"limited quirks\",e.parseError(\"almost-standards-doctype\")):n==\"-//W3C//DTD HTML 4.0//EN\"&&(r==null||r==\"http://www.w3.org/TR/REC-html40/strict.dtd\")||n==\"-//W3C//DTD HTML 4.01//EN\"&&(r==null||r==\"http://www.w3.org/TR/html4/strict.dtd\")||n==\"-//W3C//DTD XHTML 1.0 Strict//EN\"&&r==\"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd\"||n==\"-//W3C//DTD XHTML 1.1//EN\"&&r==\"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd\"||(r!=null&&r!=\"about:legacy-compat\"||n!=null)&&e.parseError(\"unknown-doctype\"),e.setInsertionMode(\"beforeHTML\")},t.initial.processCharacters=function(t){t.skipLeadingWhitespace();if(!t.length)return;e.parseError(\"expected-doctype-but-got-chars\"),this.anythingElse(),e.insertionMode.processCharacters(t)},t.initial.processStartTag=function(t,n,r){e.parseError(\"expected-doctype-but-got-start-tag\",{name:t}),this.anythingElse(),e.insertionMode.processStartTag(t,n,r)},t.initial.processEndTag=function(t){e.parseError(\"expected-doctype-but-got-end-tag\",{name:t}),this.anythingElse(),e.insertionMode.processEndTag(t)},t.initial.anythingElse=function(){e.compatMode=\"quirks\",e.setInsertionMode(\"beforeHTML\")},t.beforeHTML=Object.create(t.base),t.beforeHTML.start_tag_handlers={html:\"startTagHtml\",\"-default\":\"startTagOther\"},t.beforeHTML.processEOF=function(){this.anythingElse(),e.insertionMode.processEOF()},t.beforeHTML.processComment=function(t){e.insertComment(t,e.document)},t.beforeHTML.processCharacters=function(t){t.skipLeadingWhitespace();if(!t.length)return;this.anythingElse(),e.insertionMode.processCharacters(t)},t.beforeHTML.startTagHtml=function(t,n,r){e.insertHtmlElement(n),e.setInsertionMode(\"beforeHead\")},t.beforeHTML.startTagOther=function(t,n,r){this.anythingElse(),e.insertionMode.processStartTag(t,n,r)},t.beforeHTML.processEndTag=function(t){this.anythingElse(),e.insertionMode.processEndTag(t)},t.beforeHTML.anythingElse=function(){e.insertHtmlElement(),e.setInsertionMode(\"beforeHead\")},t.afterAfterBody=Object.create(t.base),t.afterAfterBody.start_tag_handlers={html:\"startTagHtml\",\"-default\":\"startTagOther\"},t.afterAfterBody.processComment=function(t){e.insertComment(t,e.document)},t.afterAfterBody.processDoctype=function(e){t.inBody.processDoctype(e)},t.afterAfterBody.startTagHtml=function(e,n){t.inBody.startTagHtml(e,n)},t.afterAfterBody.startTagOther=function(t,n,r){e.parseError(\"unexpected-start-tag\",{name:t}),e.setInsertionMode(\"inBody\"),e.insertionMode.processStartTag(t,n,r)},t.afterAfterBody.endTagOther=function(t){e.parseError(\"unexpected-end-tag\",{name:t}),e.setInsertionMode(\"inBody\"),e.insertionMode.processEndTag(t)},t.afterAfterBody.processCharacters=function(n){if(!p(n.characters))return e.parseError(\"unexpected-char-after-body\"),e.setInsertionMode(\"inBody\"),e.insertionMode.processCharacters(n);t.inBody.processCharacters(n)},t.afterBody=Object.create(t.base),t.afterBody.end_tag_handlers={html:\"endTagHtml\",\"-default\":\"endTagOther\"},t.afterBody.processComment=function(t){e.insertComment(t,e.openElements.rootNode)},t.afterBody.processCharacters=function(n){if(!p(n.characters))return e.parseError(\"unexpected-char-after-body\"),e.setInsertionMode(\"inBody\"),e.insertionMode.processCharacters(n);t.inBody.processCharacters(n)},t.afterBody.processStartTag=function(t,n,r){e.parseError(\"unexpected-start-tag-after-body\",{name:t}),e.setInsertionMode(\"inBody\"),e.insertionMode.processStartTag(t,n,r)},t.afterBody.endTagHtml=function(t){e.context?e.parseError(\"end-html-in-innerhtml\"):e.setInsertionMode(\"afterAfterBody\")},t.afterBody.endTagOther=function(t){e.parseError(\"unexpected-end-tag-after-body\",{name:t}),e.setInsertionMode(\"inBody\"),e.insertionMode.processEndTag(t)},t.afterFrameset=Object.create(t.base),t.afterFrameset.start_tag_handlers={html:\"startTagHtml\",noframes:\"startTagNoframes\",\"-default\":\"startTagOther\"},t.afterFrameset.end_tag_handlers={html:\"endTagHtml\",\"-default\":\"endTagOther\"},t.afterFrameset.processCharacters=function(t){var n=t.takeRemaining(),r=\"\";for(var i=0;i<n.length;i++){var s=n[i];c(s)&&(r+=s)}r&&e.insertText(r),r.length<n.length&&e.parseError(\"expected-eof-but-got-char\")},t.afterFrameset.startTagNoframes=function(e,n){t.inHead.processStartTag(e,n)},t.afterFrameset.startTagOther=function(t,n){e.parseError(\"unexpected-start-tag-after-frameset\",{name:t})},t.afterFrameset.endTagHtml=function(t){e.setInsertionMode(\"afterAfterFrameset\")},t.afterFrameset.endTagOther=function(t){e.parseError(\"unexpected-end-tag-after-frameset\",{name:t})},t.beforeHead=Object.create(t.base),t.beforeHead.start_tag_handlers={html:\"startTagHtml\",head:\"startTagHead\",\"-default\":\"startTagOther\"},t.beforeHead.end_tag_handlers={html:\"endTagImplyHead\",head:\"endTagImplyHead\",body:\"endTagImplyHead\",br:\"endTagImplyHead\",\"-default\":\"endTagOther\"},t.beforeHead.processEOF=function(){this.startTagHead(\"head\",[]),e.insertionMode.processEOF()},t.beforeHead.processCharacters=function(t){t.skipLeadingWhitespace();if(!t.length)return;this.startTagHead(\"head\",[]),e.insertionMode.processCharacters(t)},t.beforeHead.startTagHead=function(t,n){e.insertHeadElement(n),e.setInsertionMode(\"inHead\")},t.beforeHead.startTagOther=function(t,n,r){this.startTagHead(\"head\",[]),e.insertionMode.processStartTag(t,n,r)},t.beforeHead.endTagImplyHead=function(t){this.startTagHead(\"head\",[]),e.insertionMode.processEndTag(t)},t.beforeHead.endTagOther=function(t){e.parseError(\"end-tag-after-implied-root\",{name:t})},t.inHead=Object.create(t.base),t.inHead.start_tag_handlers={html:\"startTagHtml\",head:\"startTagHead\",title:\"startTagTitle\",script:\"startTagScript\",style:\"startTagNoFramesStyle\",noscript:\"startTagNoScript\",noframes:\"startTagNoFramesStyle\",base:\"startTagBaseBasefontBgsoundLink\",basefont:\"startTagBaseBasefontBgsoundLink\",bgsound:\"startTagBaseBasefontBgsoundLink\",link:\"startTagBaseBasefontBgsoundLink\",meta:\"startTagMeta\",\"-default\":\"startTagOther\"},t.inHead.end_tag_handlers={head:\"endTagHead\",html:\"endTagHtmlBodyBr\",body:\"endTagHtmlBodyBr\",br:\"endTagHtmlBodyBr\",\"-default\":\"endTagOther\"},t.inHead.processEOF=function(){var t=e.currentStackItem().localName;[\"title\",\"style\",\"script\"].indexOf(t)!=-1&&(e.parseError(\"expected-named-closing-tag-but-got-eof\",{name:t}),e.popElement()),this.anythingElse(),e.insertionMode.processEOF()},t.inHead.processCharacters=function(t){var n=t.takeLeadingWhitespace();n&&e.insertText(n);if(!t.length)return;this.anythingElse(),e.insertionMode.processCharacters(t)},t.inHead.startTagHtml=function(e,n){t.inBody.processStartTag(e,n)},t.inHead.startTagHead=function(t,n){e.parseError(\"two-heads-are-not-better-than-one\")},t.inHead.startTagTitle=function(t,n){e.processGenericRCDATAStartTag(t,n)},t.inHead.startTagNoScript=function(t,n){if(e.scriptingEnabled)return e.processGenericRawTextStartTag(t,n);e.insertElement(t,n),e.setInsertionMode(\"inHeadNoscript\")},t.inHead.startTagNoFramesStyle=function(t,n){e.processGenericRawTextStartTag(t,n)},t.inHead.startTagScript=function(t,n){e.insertElement(t,n),e.tokenizer.setState(u.SCRIPT_DATA),e.originalInsertionMode=e.insertionModeName,e.setInsertionMode(\"text\")},t.inHead.startTagBaseBasefontBgsoundLink=function(t,n){e.insertSelfClosingElement(t,n)},t.inHead.startTagMeta=function(t,n){e.insertSelfClosingElement(t,n)},t.inHead.startTagOther=function(t,n,r){this.anythingElse(),e.insertionMode.processStartTag(t,n,r)},t.inHead.endTagHead=function(t){e.openElements.item(e.openElements.length-1).localName==\"head\"?e.openElements.pop():e.parseError(\"unexpected-end-tag\",{name:\"head\"}),e.setInsertionMode(\"afterHead\")},t.inHead.endTagHtmlBodyBr=function(t){this.anythingElse(),e.insertionMode.processEndTag(t)},t.inHead.endTagOther=function(t){e.parseError(\"unexpected-end-tag\",{name:t})},t.inHead.anythingElse=function(){this.endTagHead(\"head\")},t.afterHead=Object.create(t.base),t.afterHead.start_tag_handlers={html:\"startTagHtml\",head:\"startTagHead\",body:\"startTagBody\",frameset:\"startTagFrameset\",base:\"startTagFromHead\",link:\"startTagFromHead\",meta:\"startTagFromHead\",script:\"startTagFromHead\",style:\"startTagFromHead\",title:\"startTagFromHead\",\"-default\":\"startTagOther\"},t.afterHead.end_tag_handlers={body:\"endTagBodyHtmlBr\",html:\"endTagBodyHtmlBr\",br:\"endTagBodyHtmlBr\",\"-default\":\"endTagOther\"},t.afterHead.processEOF=function(){this.anythingElse(),e.insertionMode.processEOF()},t.afterHead.processCharacters=function(t){var n=t.takeLeadingWhitespace();n&&e.insertText(n);if(!t.length)return;this.anythingElse(),e.insertionMode.processCharacters(t)},t.afterHead.startTagHtml=function(e,n){t.inBody.processStartTag(e,n)},t.afterHead.startTagBody=function(t,n){e.framesetOk=!1,e.insertBodyElement(n),e.setInsertionMode(\"inBody\")},t.afterHead.startTagFrameset=function(t,n){e.insertElement(t,n),e.setInsertionMode(\"inFrameset\")},t.afterHead.startTagFromHead=function(n,r,i){e.parseError(\"unexpected-start-tag-out-of-my-head\",{name:n}),e.openElements.push(e.head),t.inHead.processStartTag(n,r,i),e.openElements.remove(e.head)},t.afterHead.startTagHead=function(t,n,r){e.parseError(\"unexpected-start-tag\",{name:t})},t.afterHead.startTagOther=function(t,n,r){this.anythingElse(),e.insertionMode.processStartTag(t,n,r)},t.afterHead.endTagBodyHtmlBr=function(t){this.anythingElse(),e.insertionMode.processEndTag(t)},t.afterHead.endTagOther=function(t){e.parseError(\"unexpected-end-tag\",{name:t})},t.afterHead.anythingElse=function(){e.insertBodyElement([]),e.setInsertionMode(\"inBody\"),e.framesetOk=!0},t.inBody=Object.create(t.base),t.inBody.start_tag_handlers={html:\"startTagHtml\",head:\"startTagMisplaced\",base:\"startTagProcessInHead\",basefont:\"startTagProcessInHead\",bgsound:\"startTagProcessInHead\",link:\"startTagProcessInHead\",meta:\"startTagProcessInHead\",noframes:\"startTagProcessInHead\",script:\"startTagProcessInHead\",style:\"startTagProcessInHead\",title:\"startTagProcessInHead\",body:\"startTagBody\",form:\"startTagForm\",plaintext:\"startTagPlaintext\",a:\"startTagA\",button:\"startTagButton\",xmp:\"startTagXmp\",table:\"startTagTable\",hr:\"startTagHr\",image:\"startTagImage\",input:\"startTagInput\",textarea:\"startTagTextarea\",select:\"startTagSelect\",isindex:\"startTagIsindex\",applet:\"startTagAppletMarqueeObject\",marquee:\"startTagAppletMarqueeObject\",object:\"startTagAppletMarqueeObject\",li:\"startTagListItem\",dd:\"startTagListItem\",dt:\"startTagListItem\",address:\"startTagCloseP\",article:\"startTagCloseP\",aside:\"startTagCloseP\",blockquote:\"startTagCloseP\",center:\"startTagCloseP\",details:\"startTagCloseP\",dir:\"startTagCloseP\",div:\"startTagCloseP\",dl:\"startTagCloseP\",fieldset:\"startTagCloseP\",figcaption:\"startTagCloseP\",figure:\"startTagCloseP\",footer:\"startTagCloseP\",header:\"startTagCloseP\",hgroup:\"startTagCloseP\",main:\"startTagCloseP\",menu:\"startTagCloseP\",nav:\"startTagCloseP\",ol:\"startTagCloseP\",p:\"startTagCloseP\",section:\"startTagCloseP\",summary:\"startTagCloseP\",ul:\"startTagCloseP\",listing:\"startTagPreListing\",pre:\"startTagPreListing\",b:\"startTagFormatting\",big:\"startTagFormatting\",code:\"startTagFormatting\",em:\"startTagFormatting\",font:\"startTagFormatting\",i:\"startTagFormatting\",s:\"startTagFormatting\",small:\"startTagFormatting\",strike:\"startTagFormatting\",strong:\"startTagFormatting\",tt:\"startTagFormatting\",u:\"startTagFormatting\",nobr:\"startTagNobr\",area:\"startTagVoidFormatting\",br:\"startTagVoidFormatting\",embed:\"startTagVoidFormatting\",img:\"startTagVoidFormatting\",keygen:\"startTagVoidFormatting\",wbr:\"startTagVoidFormatting\",param:\"startTagParamSourceTrack\",source:\"startTagParamSourceTrack\",track:\"startTagParamSourceTrack\",iframe:\"startTagIFrame\",noembed:\"startTagRawText\",noscript:\"startTagRawText\",h1:\"startTagHeading\",h2:\"startTagHeading\",h3:\"startTagHeading\",h4:\"startTagHeading\",h5:\"startTagHeading\",h6:\"startTagHeading\",caption:\"startTagMisplaced\",col:\"startTagMisplaced\",colgroup:\"startTagMisplaced\",frame:\"startTagMisplaced\",frameset:\"startTagFrameset\",tbody:\"startTagMisplaced\",td:\"startTagMisplaced\",tfoot:\"startTagMisplaced\",th:\"startTagMisplaced\",thead:\"startTagMisplaced\",tr:\"startTagMisplaced\",option:\"startTagOptionOptgroup\",optgroup:\"startTagOptionOptgroup\",math:\"startTagMath\",svg:\"startTagSVG\",rt:\"startTagRpRt\",rp:\"startTagRpRt\",\"-default\":\"startTagOther\"},t.inBody.end_tag_handlers={p:\"endTagP\",body:\"endTagBody\",html:\"endTagHtml\",address:\"endTagBlock\",article:\"endTagBlock\",aside:\"endTagBlock\",blockquote:\"endTagBlock\",button:\"endTagBlock\",center:\"endTagBlock\",details:\"endTagBlock\",dir:\"endTagBlock\",div:\"endTagBlock\",dl:\"endTagBlock\",fieldset:\"endTagBlock\",figcaption:\"endTagBlock\",figure:\"endTagBlock\",footer:\"endTagBlock\",header:\"endTagBlock\",hgroup:\"endTagBlock\",listing:\"endTagBlock\",main:\"endTagBlock\",menu:\"endTagBlock\",nav:\"endTagBlock\",ol:\"endTagBlock\",pre:\"endTagBlock\",section:\"endTagBlock\",summary:\"endTagBlock\",ul:\"endTagBlock\",form:\"endTagForm\",applet:\"endTagAppletMarqueeObject\",marquee:\"endTagAppletMarqueeObject\",object:\"endTagAppletMarqueeObject\",dd:\"endTagListItem\",dt:\"endTagListItem\",li:\"endTagListItem\",h1:\"endTagHeading\",h2:\"endTagHeading\",h3:\"endTagHeading\",h4:\"endTagHeading\",h5:\"endTagHeading\",h6:\"endTagHeading\",a:\"endTagFormatting\",b:\"endTagFormatting\",big:\"endTagFormatting\",code:\"endTagFormatting\",em:\"endTagFormatting\",font:\"endTagFormatting\",i:\"endTagFormatting\",nobr:\"endTagFormatting\",s:\"endTagFormatting\",small:\"endTagFormatting\",strike:\"endTagFormatting\",strong:\"endTagFormatting\",tt:\"endTagFormatting\",u:\"endTagFormatting\",br:\"endTagBr\",\"-default\":\"endTagOther\"},t.inBody.processCharacters=function(t){e.shouldSkipLeadingNewline&&(e.shouldSkipLeadingNewline=!1,t.skipAtMostOneLeadingNewline()),e.reconstructActiveFormattingElements();var n=t.takeRemaining();n=n.replace(/\\u0000/g,function(t,n){return e.parseError(\"invalid-codepoint\"),\"\"});if(!n)return;e.insertText(n),e.framesetOk&&!d(n)&&(e.framesetOk=!1)},t.inBody.startTagHtml=function(t,n){e.parseError(\"non-html-root\"),e.addAttributesToElement(e.openElements.rootNode,n)},t.inBody.startTagProcessInHead=function(e,n){t.inHead.processStartTag(e,n)},t.inBody.startTagBody=function(t,n){e.parseError(\"unexpected-start-tag\",{name:\"body\"}),e.openElements.length==1||e.openElements.item(1).localName!=\"body\"?r.ok(e.context):(e.framesetOk=!1,e.addAttributesToElement(e.openElements.bodyElement,n))},t.inBody.startTagFrameset=function(t,n){e.parseError(\"unexpected-start-tag\",{name:\"frameset\"});if(e.openElements.length==1||e.openElements.item(1).localName!=\"body\")r.ok(e.context);else if(e.framesetOk){e.detachFromParent(e.openElements.bodyElement);while(e.openElements.length>1)e.openElements.pop();e.insertElement(t,n),e.setInsertionMode(\"inFrameset\")}},t.inBody.startTagCloseP=function(t,n){e.openElements.inButtonScope(\"p\")&&this.endTagP(\"p\"),e.insertElement(t,n)},t.inBody.startTagPreListing=function(t,n){e.openElements.inButtonScope(\"p\")&&this.endTagP(\"p\"),e.insertElement(t,n),e.framesetOk=!1,e.shouldSkipLeadingNewline=!0},t.inBody.startTagForm=function(t,n){e.form?e.parseError(\"unexpected-start-tag\",{name:t}):(e.openElements.inButtonScope(\"p\")&&this.endTagP(\"p\"),e.insertElement(t,n),e.form=e.currentStackItem())},t.inBody.startTagRpRt=function(t,n){e.openElements.inScope(\"ruby\")&&(e.generateImpliedEndTags(),e.currentStackItem().localName!=\"ruby\"&&e.parseError(\"unexpected-start-tag\",{name:t})),e.insertElement(t,n)},t.inBody.startTagListItem=function(t,n){var r={li:[\"li\"],dd:[\"dd\",\"dt\"],dt:[\"dd\",\"dt\"]},i=r[t],s=e.openElements;for(var o=s.length-1;o>=0;o--){var u=s.item(o);if(i.indexOf(u.localName)!=-1){e.insertionMode.processEndTag(u.localName);break}if(u.isSpecial()&&u.localName!==\"p\"&&u.localName!==\"address\"&&u.localName!==\"div\")break}e.openElements.inButtonScope(\"p\")&&this.endTagP(\"p\"),e.insertElement(t,n),e.framesetOk=!1},t.inBody.startTagPlaintext=function(t,n){e.openElements.inButtonScope(\"p\")&&this.endTagP(\"p\"),e.insertElement(t,n),e.tokenizer.setState(u.PLAINTEXT)},t.inBody.startTagHeading=function(t,n){e.openElements.inButtonScope(\"p\")&&this.endTagP(\"p\"),e.currentStackItem().isNumberedHeader()&&(e.parseError(\"unexpected-start-tag\",{name:t}),e.popElement()),e.insertElement(t,n)},t.inBody.startTagA=function(t,n){var r=e.elementInActiveFormattingElements(\"a\");r&&(e.parseError(\"unexpected-start-tag-implies-end-tag\",{startName:\"a\",endName:\"a\"}),e.adoptionAgencyEndTag(\"a\"),e.openElements.contains(r)&&e.openElements.remove(r),e.removeElementFromActiveFormattingElements(r)),e.reconstructActiveFormattingElements(),e.insertFormattingElement(t,n)},t.inBody.startTagFormatting=function(t,n){e.reconstructActiveFormattingElements(),e.insertFormattingElement(t,n)},t.inBody.startTagNobr=function(t,n){e.reconstructActiveFormattingElements(),e.openElements.inScope(\"nobr\")&&(e.parseError(\"unexpected-start-tag-implies-end-tag\",{startName:\"nobr\",endName:\"nobr\"}),this.processEndTag(\"nobr\"),e.reconstructActiveFormattingElements()),e.insertFormattingElement(t,n)},t.inBody.startTagButton=function(t,n){e.openElements.inScope(\"button\")?(e.parseError(\"unexpected-start-tag-implies-end-tag\",{startName:\"button\",endName:\"button\"}),this.processEndTag(\"button\"),e.insertionMode.processStartTag(t,n)):(e.framesetOk=!1,e.reconstructActiveFormattingElements(),e.insertElement(t,n))},t.inBody.startTagAppletMarqueeObject=function(t,n){e.reconstructActiveFormattingElements(),e.insertElement(t,n),e.activeFormattingElements.push(l),e.framesetOk=!1},t.inBody.endTagAppletMarqueeObject=function(t){e.openElements.inScope(t)?(e.generateImpliedEndTags(),e.currentStackItem().localName!=t&&e.parseError(\"end-tag-too-early\",{name:t}),e.openElements.popUntilPopped(t),e.clearActiveFormattingElements()):e.parseError(\"unexpected-end-tag\",{name:t})},t.inBody.startTagXmp=function(t,n){e.openElements.inButtonScope(\"p\")&&this.processEndTag(\"p\"),e.reconstructActiveFormattingElements(),e.processGenericRawTextStartTag(t,n),e.framesetOk=!1},t.inBody.startTagTable=function(t,n){e.compatMode!==\"quirks\"&&e.openElements.inButtonScope(\"p\")&&this.processEndTag(\"p\"),e.insertElement(t,n),e.setInsertionMode(\"inTable\"),e.framesetOk=!1},t.inBody.startTagVoidFormatting=function(t,n){e.reconstructActiveFormattingElements(),e.insertSelfClosingElement(t,n),e.framesetOk=!1},t.inBody.startTagParamSourceTrack=function(t,n){e.insertSelfClosingElement(t,n)},t.inBody.startTagHr=function(t,n){e.openElements.inButtonScope(\"p\")&&this.endTagP(\"p\"),e.insertSelfClosingElement(t,n),e.framesetOk=!1},t.inBody.startTagImage=function(t,n){e.parseError(\"unexpected-start-tag-treated-as\",{originalName:\"image\",newName:\"img\"}),this.processStartTag(\"img\",n)},t.inBody.startTagInput=function(t,n){var r=e.framesetOk;this.startTagVoidFormatting(t,n);for(var i in n)if(n[i].nodeName==\"type\"){n[i].nodeValue.toLowerCase()==\"hidden\"&&(e.framesetOk=r);break}},t.inBody.startTagIsindex=function(t,n){e.parseError(\"deprecated-tag\",{name:\"isindex\"}),e.selfClosingFlagAcknowledged=!0;if(e.form)return;var r=[],i=[],s=\"This is a searchable index. Enter search keywords: \";for(var o in n)switch(n[o].nodeName){case\"action\":r.push({nodeName:\"action\",nodeValue:n[o].nodeValue});break;case\"prompt\":s=n[o].nodeValue;break;case\"name\":break;default:i.push({nodeName:n[o].nodeName,nodeValue:n[o].nodeValue})}i.push({nodeName:\"name\",nodeValue:\"isindex\"}),this.processStartTag(\"form\",r),this.processStartTag(\"hr\"),this.processStartTag(\"label\"),this.processCharacters(new m(s)),this.processStartTag(\"input\",i),this.processEndTag(\"label\"),this.processStartTag(\"hr\"),this.processEndTag(\"form\")},t.inBody.startTagTextarea=function(t,n){e.insertElement(t,n),e.tokenizer.setState(u.RCDATA),e.originalInsertionMode=e.insertionModeName,e.shouldSkipLeadingNewline=!0,e.framesetOk=!1,e.setInsertionMode(\"text\")},t.inBody.startTagIFrame=function(t,n){e.framesetOk=!1,this.startTagRawText(t,n)},t.inBody.startTagRawText=function(t,n){e.processGenericRawTextStartTag(t,n)},t.inBody.startTagSelect=function(t,n){e.reconstructActiveFormattingElements(),e.insertElement(t,n),e.framesetOk=!1;var r=e.insertionModeName;r==\"inTable\"||r==\"inCaption\"||r==\"inColumnGroup\"||r==\"inTableBody\"||r==\"inRow\"||r==\"inCell\"?e.setInsertionMode(\"inSelectInTable\"):e.setInsertionMode(\"inSelect\")},t.inBody.startTagMisplaced=function(t,n){e.parseError(\"unexpected-start-tag-ignored\",{name:t})},t.inBody.endTagMisplaced=function(t){e.parseError(\"unexpected-end-tag\",{name:t})},t.inBody.endTagBr=function(t){e.parseError(\"unexpected-end-tag-treated-as\",{originalName:\"br\",newName:\"br element\"}),e.reconstructActiveFormattingElements(),e.insertElement(t,[]),e.popElement()},t.inBody.startTagOptionOptgroup=function(t,n){e.currentStackItem().localName==\"option\"&&e.popElement(),e.reconstructActiveFormattingElements(),e.insertElement(t,n)},t.inBody.startTagOther=function(t,n){e.reconstructActiveFormattingElements(),e.insertElement(t,n)},t.inBody.endTagOther=function(t){var n;for(var r=e.openElements.length-1;r>0;r--){n=e.openElements.item(r);if(n.localName==t){e.generateImpliedEndTags(t),e.currentStackItem().localName!=t&&e.parseError(\"unexpected-end-tag\",{name:t}),e.openElements.remove_openElements_until(function(e){return e===n});break}if(n.isSpecial()){e.parseError(\"unexpected-end-tag\",{name:t});break}}},t.inBody.startTagMath=function(t,n,r){e.reconstructActiveFormattingElements(),n=e.adjustMathMLAttributes(n),n=e.adjustForeignAttributes(n),e.insertForeignElement(t,n,\"http://www.w3.org/1998/Math/MathML\",r)},t.inBody.startTagSVG=function(t,n,r){e.reconstructActiveFormattingElements(),n=e.adjustSVGAttributes(n),n=e.adjustForeignAttributes(n),e.insertForeignElement(t,n,\"http://www.w3.org/2000/svg\",r)},t.inBody.endTagP=function(t){e.openElements.inButtonScope(\"p\")?(e.generateImpliedEndTags(\"p\"),e.currentStackItem().localName!=\"p\"&&e.parseError(\"unexpected-implied-end-tag\",{name:\"p\"}),e.openElements.popUntilPopped(t)):(e.parseError(\"unexpected-end-tag\",{name:\"p\"}),this.startTagCloseP(\"p\",[]),this.endTagP(\"p\"))},t.inBody.endTagBody=function(t){if(!e.openElements.inScope(\"body\")){e.parseError(\"unexpected-end-tag\",{name:t});return}e.currentStackItem().localName!=\"body\"&&e.parseError(\"expected-one-end-tag-but-got-another\",{expectedName:e.currentStackItem().localName,gotName:t}),e.setInsertionMode(\"afterBody\")},t.inBody.endTagHtml=function(t){if(!e.openElements.inScope(\"body\")){e.parseError(\"unexpected-end-tag\",{name:t});return}e.currentStackItem().localName!=\"body\"&&e.parseError(\"expected-one-end-tag-but-got-another\",{expectedName:e.currentStackItem().localName,gotName:t}),e.setInsertionMode(\"afterBody\"),e.insertionMode.processEndTag(t)},t.inBody.endTagBlock=function(t){e.openElements.inScope(t)?(e.generateImpliedEndTags(),e.currentStackItem().localName!=t&&e.parseError(\"end-tag-too-early\",{name:t}),e.openElements.popUntilPopped(t)):e.parseError(\"unexpected-end-tag\",{name:t})},t.inBody.endTagForm=function(t){var n=e.form;e.form=null,!n||!e.openElements.inScope(t)?e.parseError(\"unexpected-end-tag\",{name:t}):(e.generateImpliedEndTags(),e.currentStackItem()!=n&&e.parseError(\"end-tag-too-early-ignored\",{name:\"form\"}),e.openElements.remove(n))},t.inBody.endTagListItem=function(t){e.openElements.inListItemScope(t)?(e.generateImpliedEndTags(t),e.currentStackItem().localName!=t&&e.parseError(\"end-tag-too-early\",{name:t}),e.openElements.popUntilPopped(t)):e.parseError(\"unexpected-end-tag\",{name:t})},t.inBody.endTagHeading=function(t){if(!e.openElements.hasNumberedHeaderElementInScope()){e.parseError(\"unexpected-end-tag\",{name:t});return}e.generateImpliedEndTags(),e.currentStackItem().localName!=t&&e.parseError(\"end-tag-too-early\",{name:t}),e.openElements.remove_openElements_until(function(e){return e.isNumberedHeader()})},t.inBody.endTagFormatting=function(t,n){e.adoptionAgencyEndTag(t)||this.endTagOther(t,n)},t.inCaption=Object.create(t.base),t.inCaption.start_tag_handlers={html:\"startTagHtml\",caption:\"startTagTableElement\",col:\"startTagTableElement\",colgroup:\"startTagTableElement\",tbody:\"startTagTableElement\",td:\"startTagTableElement\",tfoot:\"startTagTableElement\",thead:\"startTagTableElement\",tr:\"startTagTableElement\",\"-default\":\"startTagOther\"},t.inCaption.end_tag_handlers={caption:\"endTagCaption\",table:\"endTagTable\",body:\"endTagIgnore\",col:\"endTagIgnore\",colgroup:\"endTagIgnore\",html:\"endTagIgnore\",tbody:\"endTagIgnore\",td:\"endTagIgnore\",tfood:\"endTagIgnore\",thead:\"endTagIgnore\",tr:\"endTagIgnore\",\"-default\":\"endTagOther\"},t.inCaption.processCharacters=function(e){t.inBody.processCharacters(e)},t.inCaption.startTagTableElement=function(t,n){e.parseError(\"unexpected-end-tag\",{name:t});var r=!e.openElements.inTableScope(\"caption\");e.insertionMode.processEndTag(\"caption\"),r||e.insertionMode.processStartTag(t,n)},t.inCaption.startTagOther=function(e,n,r){t.inBody.processStartTag(e,n,r)},t.inCaption.endTagCaption=function(t){e.openElements.inTableScope(\"caption\")?(e.generateImpliedEndTags(),e.currentStackItem().localName!=\"caption\"&&e.parseError(\"expected-one-end-tag-but-got-another\",{gotName:\"caption\",expectedName:e.currentStackItem().localName}),e.openElements.popUntilPopped(\"caption\"),e.clearActiveFormattingElements(),e.setInsertionMode(\"inTable\")):(r.ok(e.context),e.parseError(\"unexpected-end-tag\",{name:t}))},t.inCaption.endTagTable=function(t){e.parseError(\"unexpected-end-table-in-caption\");var n=!e.openElements.inTableScope(\"caption\");e.insertionMode.processEndTag(\"caption\"),n||e.insertionMode.processEndTag(t)},t.inCaption.endTagIgnore=function(t){e.parseError(\"unexpected-end-tag\",{name:t})},t.inCaption.endTagOther=function(e){t.inBody.processEndTag(e)},t.inCell=Object.create(t.base),t.inCell.start_tag_handlers={html:\"startTagHtml\",caption:\"startTagTableOther\",col:\"startTagTableOther\",colgroup:\"startTagTableOther\",tbody:\"startTagTableOther\",td:\"startTagTableOther\",tfoot:\"startTagTableOther\",th:\"startTagTableOther\",thead:\"startTagTableOther\",tr:\"startTagTableOther\",\"-default\":\"startTagOther\"},t.inCell.end_tag_handlers={td:\"endTagTableCell\",th:\"endTagTableCell\",body:\"endTagIgnore\",caption:\"endTagIgnore\",col:\"endTagIgnore\",colgroup:\"endTagIgnore\",html:\"endTagIgnore\",table:\"endTagImply\",tbody:\"endTagImply\",tfoot:\"endTagImply\",thead:\"endTagImply\",tr:\"endTagImply\",\"-default\":\"endTagOther\"},t.inCell.processCharacters=function(e){t.inBody.processCharacters(e)},t.inCell.startTagTableOther=function(t,n,r){e.openElements.inTableScope(\"td\")||e.openElements.inTableScope(\"th\")?(this.closeCell(),e.insertionMode.processStartTag(t,n,r)):e.parseError(\"unexpected-start-tag\",{name:t})},t.inCell.startTagOther=function(e,n,r){t.inBody.processStartTag(e,n,r)},t.inCell.endTagTableCell=function(t){e.openElements.inTableScope(t)?(e.generateImpliedEndTags(t),e.currentStackItem().localName!=t.toLowerCase()?(e.parseError(\"unexpected-cell-end-tag\",{name:t}),e.openElements.popUntilPopped(t)):e.popElement(),e.clearActiveFormattingElements(),e.setInsertionMode(\"inRow\")):e.parseError(\"unexpected-end-tag\",{name:t})},t.inCell.endTagIgnore=function(t){e.parseError(\"unexpected-end-tag\",{name:t})},t.inCell.endTagImply=function(t){e.openElements.inTableScope(t)?(this.closeCell(),e.insertionMode.processEndTag(t)):e.parseError(\"unexpected-end-tag\",{name:t})},t.inCell.endTagOther=function(e){t.inBody.processEndTag(e)},t.inCell.closeCell=function(){e.openElements.inTableScope(\"td\")?this.endTagTableCell(\"td\"):e.openElements.inTableScope(\"th\")&&this.endTagTableCell(\"th\")},t.inColumnGroup=Object.create(t.base),t.inColumnGroup.start_tag_handlers={html:\"startTagHtml\",col:\"startTagCol\",\"-default\":\"startTagOther\"},t.inColumnGroup.end_tag_handlers={colgroup:\"endTagColgroup\",col:\"endTagCol\",\"-default\":\"endTagOther\"},t.inColumnGroup.ignoreEndTagColgroup=function(){return e.currentStackItem().localName==\"html\"},t.inColumnGroup.processCharacters=function(t){var n=t.takeLeadingWhitespace();n&&e.insertText(n);if(!t.length)return;var r=this.ignoreEndTagColgroup();this.endTagColgroup(\"colgroup\"),r||e.insertionMode.processCharacters(t)},t.inColumnGroup.startTagCol=function(t,n){e.insertSelfClosingElement(t,n)},t.inColumnGroup.startTagOther=function(t,n,r){var i=this.ignoreEndTagColgroup();this.endTagColgroup(\"colgroup\"),i||e.insertionMode.processStartTag(t,n,r)},t.inColumnGroup.endTagColgroup=function(t){this.ignoreEndTagColgroup()?(r.ok(e.context),e.parseError(\"unexpected-end-tag\",{name:t})):(e.popElement(),e.setInsertionMode(\"inTable\"))},t.inColumnGroup.endTagCol=function(t){e.parseError(\"no-end-tag\",{name:\"col\"})},t.inColumnGroup.endTagOther=function(t){var n=this.ignoreEndTagColgroup();this.endTagColgroup(\"colgroup\"),n||e.insertionMode.processEndTag(t)},t.inForeignContent=Object.create(t.base),t.inForeignContent.processStartTag=function(t,n,r){if([\"b\",\"big\",\"blockquote\",\"body\",\"br\",\"center\",\"code\",\"dd\",\"div\",\"dl\",\"dt\",\"em\",\"embed\",\"h1\",\"h2\",\"h3\",\"h4\",\"h5\",\"h6\",\"head\",\"hr\",\"i\",\"img\",\"li\",\"listing\",\"menu\",\"meta\",\"nobr\",\"ol\",\"p\",\"pre\",\"ruby\",\"s\",\"small\",\"span\",\"strong\",\"strike\",\"sub\",\"sup\",\"table\",\"tt\",\"u\",\"ul\",\"var\"].indexOf(t)!=-1||t==\"font\"&&n.some(function(e){return[\"color\",\"face\",\"size\"].indexOf(e.nodeName)>=0})){e.parseError(\"unexpected-html-element-in-foreign-content\",{name:t});while(e.currentStackItem().isForeign()&&!e.currentStackItem().isHtmlIntegrationPoint()&&!e.currentStackItem().isMathMLTextIntegrationPoint())e.openElements.pop();e.insertionMode.processStartTag(t,n,r);return}e.currentStackItem().namespaceURI==\"http://www.w3.org/1998/Math/MathML\"&&(n=e.adjustMathMLAttributes(n)),e.currentStackItem().namespaceURI==\"http://www.w3.org/2000/svg\"&&(t=e.adjustSVGTagNameCase(t),n=e.adjustSVGAttributes(n)),n=e.adjustForeignAttributes(n),e.insertForeignElement(t,n,e.currentStackItem().namespaceURI,r)},t.inForeignContent.processEndTag=function(t){var n=e.currentStackItem(),r=e.openElements.length-1;n.localName.toLowerCase()!=t&&e.parseError(\"unexpected-end-tag\",{name:t});for(;;){if(r===0)break;if(n.localName.toLowerCase()==t){while(e.openElements.pop()!=n);break}r-=1,n=e.openElements.item(r);if(n.isForeign())continue;e.insertionMode.processEndTag(t);break}},t.inForeignContent.processCharacters=function(t){var n=t.takeRemaining();n=n.replace(/\\u0000/g,function(t,n){return e.parseError(\"invalid-codepoint\"),\"\\ufffd\"}),e.framesetOk&&!d(n)&&(e.framesetOk=!1),e.insertText(n)},t.inHeadNoscript=Object.create(t.base),t.inHeadNoscript.start_tag_handlers={html:\"startTagHtml\",basefont:\"startTagBasefontBgsoundLinkMetaNoframesStyle\",bgsound:\"startTagBasefontBgsoundLinkMetaNoframesStyle\",link:\"startTagBasefontBgsoundLinkMetaNoframesStyle\",meta:\"startTagBasefontBgsoundLinkMetaNoframesStyle\",noframes:\"startTagBasefontBgsoundLinkMetaNoframesStyle\",style:\"startTagBasefontBgsoundLinkMetaNoframesStyle\",head:\"startTagHeadNoscript\",noscript:\"startTagHeadNoscript\",\"-default\":\"startTagOther\"},t.inHeadNoscript.end_tag_handlers={noscript:\"endTagNoscript\",br:\"endTagBr\",\"-default\":\"endTagOther\"},t.inHeadNoscript.processCharacters=function(t){var n=t.takeLeadingWhitespace();n&&e.insertText(n);if(!t.length)return;e.parseError(\"unexpected-char-in-frameset\"),this.anythingElse(),e.insertionMode.processCharacters(t)},t.inHeadNoscript.processComment=function(e){t.inHead.processComment(e)},t.inHeadNoscript.startTagBasefontBgsoundLinkMetaNoframesStyle=function(e,n){t.inHead.processStartTag(e,n)},t.inHeadNoscript.startTagHeadNoscript=function(t,n){e.parseError(\"unexpected-start-tag-in-frameset\",{name:t})},t.inHeadNoscript.startTagOther=function(t,n){e.parseError(\"unexpected-start-tag-in-frameset\",{name:t}),this.anythingElse(),e.insertionMode.processStartTag(t,n)},t.inHeadNoscript.endTagBr=function(t,n){e.parseError(\"unexpected-end-tag-in-frameset\",{name:t}),this.anythingElse(),e.insertionMode.processEndTag(t,n)},t.inHeadNoscript.endTagNoscript=function(t,n){e.popElement(),e.setInsertionMode(\"inHead\")},t.inHeadNoscript.endTagOther=function(t,n){e.parseError(\"unexpected-end-tag-in-frameset\",{name:t})},t.inHeadNoscript.anythingElse=function(){e.popElement(),e.setInsertionMode(\"inHead\")},t.inFrameset=Object.create(t.base),t.inFrameset.start_tag_handlers={html:\"startTagHtml\",frameset:\"startTagFrameset\",frame:\"startTagFrame\",noframes:\"startTagNoframes\",\"-default\":\"startTagOther\"},t.inFrameset.end_tag_handlers={frameset:\"endTagFrameset\",noframes:\"endTagNoframes\",\"-default\":\"endTagOther\"},t.inFrameset.processCharacters=function(t){e.parseError(\"unexpected-char-in-frameset\")},t.inFrameset.startTagFrameset=function(t,n){e.insertElement(t,n)},t.inFrameset.startTagFrame=function(t,n){e.insertSelfClosingElement(t,n)},t.inFrameset.startTagNoframes=function(e,n){t.inBody.processStartTag(e,n)},t.inFrameset.startTagOther=function(t,n){e.parseError(\"unexpected-start-tag-in-frameset\",{name:t})},t.inFrameset.endTagFrameset=function(t,n){e.currentStackItem().localName==\"html\"?e.parseError(\"unexpected-frameset-in-frameset-innerhtml\"):e.popElement(),!e.context&&e.currentStackItem().localName!=\"frameset\"&&e.setInsertionMode(\"afterFrameset\")},t.inFrameset.endTagNoframes=function(e){t.inBody.processEndTag(e)},t.inFrameset.endTagOther=function(t){e.parseError(\"unexpected-end-tag-in-frameset\",{name:t})},t.inTable=Object.create(t.base),t.inTable.start_tag_handlers={html:\"startTagHtml\",caption:\"startTagCaption\",colgroup:\"startTagColgroup\",col:\"startTagCol\",table:\"startTagTable\",tbody:\"startTagRowGroup\",tfoot:\"startTagRowGroup\",thead:\"startTagRowGroup\",td:\"startTagImplyTbody\",th:\"startTagImplyTbody\",tr:\"startTagImplyTbody\",style:\"startTagStyleScript\",script:\"startTagStyleScript\",input:\"startTagInput\",form:\"startTagForm\",\"-default\":\"startTagOther\"},t.inTable.end_tag_handlers={table:\"endTagTable\",body:\"endTagIgnore\",caption:\"endTagIgnore\",col:\"endTagIgnore\",colgroup:\"endTagIgnore\",html:\"endTagIgnore\",tbody:\"endTagIgnore\",td:\"endTagIgnore\",tfoot:\"endTagIgnore\",th:\"endTagIgnore\",thead:\"endTagIgnore\",tr:\"endTagIgnore\",\"-default\":\"endTagOther\"},t.inTable.processCharacters=function(n){if(e.currentStackItem().isFosterParenting()){var r=e.insertionModeName;e.setInsertionMode(\"inTableText\"),e.originalInsertionMode=r,e.insertionMode.processCharacters(n)}else e.redirectAttachToFosterParent=!0,t.inBody.processCharacters(n),e.redirectAttachToFosterParent=!1},t.inTable.startTagCaption=function(t,n){e.openElements.popUntilTableScopeMarker(),e.activeFormattingElements.push(l),e.insertElement(t,n),e.setInsertionMode(\"inCaption\")},t.inTable.startTagColgroup=function(t,n){e.openElements.popUntilTableScopeMarker(),e.insertElement(t,n),e.setInsertionMode(\"inColumnGroup\")},t.inTable.startTagCol=function(t,n){this.startTagColgroup(\"colgroup\",[]),e.insertionMode.processStartTag(t,n)},t.inTable.startTagRowGroup=function(t,n){e.openElements.popUntilTableScopeMarker(),e.insertElement(t,n),e.setInsertionMode(\"inTableBody\")},t.inTable.startTagImplyTbody=function(t,n){this.startTagRowGroup(\"tbody\",[]),e.insertionMode.processStartTag(t,n)},t.inTable.startTagTable=function(t,n){e.parseError(\"unexpected-start-tag-implies-end-tag\",{startName:\"table\",endName:\"table\"}),e.insertionMode.processEndTag(\"table\"),e.context||e.insertionMode.processStartTag(t,n)},t.inTable.startTagStyleScript=function(e,n){t.inHead.processStartTag(e,n)},t.inTable.startTagInput=function(t,n){for(var r in n)if(n[r].nodeName.toLowerCase()==\"type\"){if(n[r].nodeValue.toLowerCase()==\"hidden\"){e.parseError(\"unexpected-hidden-input-in-table\"),e.insertElement(t,n),e.openElements.pop();return}break}this.startTagOther(t,n)},t.inTable.startTagForm=function(t,n){e.parseError(\"unexpected-form-in-table\"),e.form||(e.insertElement(t,n),e.form=e.currentStackItem(),e.openElements.pop())},t.inTable.startTagOther=function(n,r,i){e.parseError(\"unexpected-start-tag-implies-table-voodoo\",{name:n}),e.redirectAttachToFosterParent=!0,t.inBody.processStartTag(n,r,i),e.redirectAttachToFosterParent=!1},t.inTable.endTagTable=function(t){e.openElements.inTableScope(t)?(e.generateImpliedEndTags(),e.currentStackItem().localName!=t&&e.parseError(\"end-tag-too-early-named\",{gotName:\"table\",expectedName:e.currentStackItem().localName}),e.openElements.popUntilPopped(\"table\"),e.resetInsertionMode()):(r.ok(e.context),e.parseError(\"unexpected-end-tag\",{name:t}))},t.inTable.endTagIgnore=function(t){e.parseError(\"unexpected-end-tag\",{name:t})},t.inTable.endTagOther=function(n){e.parseError(\"unexpected-end-tag-implies-table-voodoo\",{name:n}),e.redirectAttachToFosterParent=!0,t.inBody.processEndTag(n),e.redirectAttachToFosterParent=!1},t.inTableText=Object.create(t.base),t.inTableText.flushCharacters=function(){var t=e.pendingTableCharacters.join(\"\");p(t)?e.insertText(t):(e.redirectAttachToFosterParent=!0,e.reconstructActiveFormattingElements(),e.insertText(t),e.framesetOk=!1,e.redirectAttachToFosterParent=!1),e.pendingTableCharacters=[]},t.inTableText.processComment=function(t){this.flushCharacters(),e.setInsertionMode(e.originalInsertionMode),e.insertionMode.processComment(t)},t.inTableText.processEOF=function(t){this.flushCharacters(),e.setInsertionMode(e.originalInsertionMode),e.insertionMode.processEOF()},t.inTableText.processCharacters=function(t){var n=t.takeRemaining();n=n.replace(/\\u0000/g,function(t,n){return e.parseError(\"invalid-codepoint\"),\"\"});if(!n)return;e.pendingTableCharacters.push(n)},t.inTableText.processStartTag=function(t,n,r){this.flushCharacters(),e.setInsertionMode(e.originalInsertionMode),e.insertionMode.processStartTag(t,n,r)},t.inTableText.processEndTag=function(t,n){this.flushCharacters(),e.setInsertionMode(e.originalInsertionMode),e.insertionMode.processEndTag(t,n)},t.inTableBody=Object.create(t.base),t.inTableBody.start_tag_handlers={html:\"startTagHtml\",tr:\"startTagTr\",td:\"startTagTableCell\",th:\"startTagTableCell\",caption:\"startTagTableOther\",col:\"startTagTableOther\",colgroup:\"startTagTableOther\",tbody:\"startTagTableOther\",tfoot:\"startTagTableOther\",thead:\"startTagTableOther\",\"-default\":\"startTagOther\"},t.inTableBody.end_tag_handlers={table:\"endTagTable\",tbody:\"endTagTableRowGroup\",tfoot:\"endTagTableRowGroup\",thead:\"endTagTableRowGroup\",body:\"endTagIgnore\",caption:\"endTagIgnore\",col:\"endTagIgnore\",colgroup:\"endTagIgnore\",html:\"endTagIgnore\",td:\"endTagIgnore\",th:\"endTagIgnore\",tr:\"endTagIgnore\",\"-default\":\"endTagOther\"},t.inTableBody.processCharacters=function(e){t.inTable.processCharacters(e)},t.inTableBody.startTagTr=function(t,n){e.openElements.popUntilTableBodyScopeMarker(),e.insertElement(t,n),e.setInsertionMode(\"inRow\")},t.inTableBody.startTagTableCell=function(t,n){e.parseError(\"unexpected-cell-in-table-body\",{name:t}),this.startTagTr(\"tr\",[]),e.insertionMode.processStartTag(t,n)},t.inTableBody.startTagTableOther=function(t,n){e.openElements.inTableScope(\"tbody\")||e.openElements.inTableScope(\"thead\")||e.openElements.inTableScope(\"tfoot\")?(e.openElements.popUntilTableBodyScopeMarker(),this.endTagTableRowGroup(e.currentStackItem().localName),e.insertionMode.processStartTag(t,n)):e.parseError(\"unexpected-start-tag\",{name:t})},t.inTableBody.startTagOther=function(e,n){t.inTable.processStartTag(e,n)},t.inTableBody.endTagTableRowGroup=function(t){e.openElements.inTableScope(t)?(e.openElements.popUntilTableBodyScopeMarker(),e.popElement(),e.setInsertionMode(\"inTable\")):e.parseError(\"unexpected-end-tag-in-table-body\",{name:t})},t.inTableBody.endTagTable=function(t){e.openElements.inTableScope(\"tbody\")||e.openElements.inTableScope(\"thead\")||e.openElements.inTableScope(\"tfoot\")?(e.openElements.popUntilTableBodyScopeMarker(),this.endTagTableRowGroup(e.currentStackItem().localName),e.insertionMode.processEndTag(t)):e.parseError(\"unexpected-end-tag\",{name:t})},t.inTableBody.endTagIgnore=function(t){e.parseError(\"unexpected-end-tag-in-table-body\",{name:t})},t.inTableBody.endTagOther=function(e){t.inTable.processEndTag(e)},t.inSelect=Object.create(t.base),t.inSelect.start_tag_handlers={html:\"startTagHtml\",option:\"startTagOption\",optgroup:\"startTagOptgroup\",select:\"startTagSelect\",input:\"startTagInput\",keygen:\"startTagInput\",textarea:\"startTagInput\",script:\"startTagScript\",\"-default\":\"startTagOther\"},t.inSelect.end_tag_handlers={option:\"endTagOption\",optgroup:\"endTagOptgroup\",select:\"endTagSelect\",caption:\"endTagTableElements\",table:\"endTagTableElements\",tbody:\"endTagTableElements\",tfoot:\"endTagTableElements\",thead:\"endTagTableElements\",tr:\"endTagTableElements\",td:\"endTagTableElements\",th:\"endTagTableElements\",\"-default\":\"endTagOther\"},t.inSelect.processCharacters=function(t){var n=t.takeRemaining();n=n.replace(/\\u0000/g,function(t,n){return e.parseError(\"invalid-codepoint\"),\"\"});if(!n)return;e.insertText(n)},t.inSelect.startTagOption=function(t,n){e.currentStackItem().localName==\"option\"&&e.popElement(),e.insertElement(t,n)},t.inSelect.startTagOptgroup=function(t,n){e.currentStackItem().localName==\"option\"&&e.popElement(),e.currentStackItem().localName==\"optgroup\"&&e.popElement(),e.insertElement(t,n)},t.inSelect.endTagOption=function(t){if(e.currentStackItem().localName!==\"option\"){e.parseError(\"unexpected-end-tag-in-select\",{name:t});return}e.popElement()},t.inSelect.endTagOptgroup=function(t){e.currentStackItem().localName==\"option\"&&e.openElements.item(e.openElements.length-2).localName==\"optgroup\"&&e.popElement(),e.currentStackItem().localName==\"optgroup\"?e.popElement():e.parseError(\"unexpected-end-tag-in-select\",{name:\"optgroup\"})},t.inSelect.startTagSelect=function(t){e.parseError(\"unexpected-select-in-select\"),this.endTagSelect(\"select\")},t.inSelect.endTagSelect=function(t){e.openElements.inTableScope(\"select\")?(e.openElements.popUntilPopped(\"select\"),e.resetInsertionMode()):e.parseError(\"unexpected-end-tag\",{name:t})},t.inSelect.startTagInput=function(t,n){e.parseError(\"unexpected-input-in-select\"),e.openElements.inSelectScope(\"select\")&&(this.endTagSelect(\"select\"),e.insertionMode.processStartTag(t,n))},t.inSelect.startTagScript=function(e,n){t.inHead.processStartTag(e,n)},t.inSelect.endTagTableElements=function(t){e.parseError(\"unexpected-end-tag-in-select\",{name:t}),e.openElements.inTableScope(t)&&(this.endTagSelect(\"select\"),e.insertionMode.processEndTag(t))},t.inSelect.startTagOther=function(t,n){e.parseError(\"unexpected-start-tag-in-select\",{name:t})},t.inSelect.endTagOther=function(t){e.parseError(\"unexpected-end-tag-in-select\",{name:t})},t.inSelectInTable=Object.create(t.base),t.inSelectInTable.start_tag_handlers={caption:\"startTagTable\",table:\"startTagTable\",tbody:\"startTagTable\",tfoot:\"startTagTable\",thead:\"startTagTable\",tr:\"startTagTable\",td:\"startTagTable\",th:\"startTagTable\",\"-default\":\"startTagOther\"},t.inSelectInTable.end_tag_handlers={caption:\"endTagTable\",table:\"endTagTable\",tbody:\"endTagTable\",tfoot:\"endTagTable\",thead:\"endTagTable\",tr:\"endTagTable\",td:\"endTagTable\",th:\"endTagTable\",\"-default\":\"endTagOther\"},t.inSelectInTable.processCharacters=function(e){t.inSelect.processCharacters(e)},t.inSelectInTable.startTagTable=function(t,n){e.parseError(\"unexpected-table-element-start-tag-in-select-in-table\",{name:t}),this.endTagOther(\"select\"),e.insertionMode.processStartTag(t,n)},t.inSelectInTable.startTagOther=function(e,n,r){t.inSelect.processStartTag(e,n,r)},t.inSelectInTable.endTagTable=function(t){e.parseError(\"unexpected-table-element-end-tag-in-select-in-table\",{name:t}),e.openElements.inTableScope(t)&&(this.endTagOther(\"select\"),e.insertionMode.processEndTag(t))},t.inSelectInTable.endTagOther=function(e){t.inSelect.processEndTag(e)},t.inRow=Object.create(t.base),t.inRow.start_tag_handlers={html:\"startTagHtml\",td:\"startTagTableCell\",th:\"startTagTableCell\",caption:\"startTagTableOther\",col:\"startTagTableOther\",colgroup:\"startTagTableOther\",tbody:\"startTagTableOther\",tfoot:\"startTagTableOther\",thead:\"startTagTableOther\",tr:\"startTagTableOther\",\"-default\":\"startTagOther\"},t.inRow.end_tag_handlers={tr:\"endTagTr\",table:\"endTagTable\",tbody:\"endTagTableRowGroup\",tfoot:\"endTagTableRowGroup\",thead:\"endTagTableRowGroup\",body:\"endTagIgnore\",caption:\"endTagIgnore\",col:\"endTagIgnore\",colgroup:\"endTagIgnore\",html:\"endTagIgnore\",td:\"endTagIgnore\",th:\"endTagIgnore\",\"-default\":\"endTagOther\"},t.inRow.processCharacters=function(e){t.inTable.processCharacters(e)},t.inRow.startTagTableCell=function(t,n){e.openElements.popUntilTableRowScopeMarker(),e.insertElement(t,n),e.setInsertionMode(\"inCell\"),e.activeFormattingElements.push(l)},t.inRow.startTagTableOther=function(t,n){var r=this.ignoreEndTagTr();this.endTagTr(\"tr\"),r||e.insertionMode.processStartTag(t,n)},t.inRow.startTagOther=function(e,n,r){t.inTable.processStartTag(e,n,r)},t.inRow.endTagTr=function(t){this.ignoreEndTagTr()?(r.ok(e.context),e.parseError(\"unexpected-end-tag\",{name:t})):(e.openElements.popUntilTableRowScopeMarker(),e.popElement(),e.setInsertionMode(\"inTableBody\"))},t.inRow.endTagTable=function(t){var n=this.ignoreEndTagTr();this.endTagTr(\"tr\"),n||e.insertionMode.processEndTag(t)},t.inRow.endTagTableRowGroup=function(t){e.openElements.inTableScope(t)?(this.endTagTr(\"tr\"),e.insertionMode.processEndTag(t)):e.parseError(\"unexpected-end-tag\",{name:t})},t.inRow.endTagIgnore=function(t){e.parseError(\"unexpected-end-tag-in-table-row\",{name:t})},t.inRow.endTagOther=function(e){t.inTable.processEndTag(e)},t.inRow.ignoreEndTagTr=function(){return!e.openElements.inTableScope(\"tr\")},t.afterAfterFrameset=Object.create(t.base),t.afterAfterFrameset.start_tag_handlers={html:\"startTagHtml\",noframes:\"startTagNoFrames\",\"-default\":\"startTagOther\"},t.afterAfterFrameset.processEOF=function(){},t.afterAfterFrameset.processComment=function(t){e.insertComment(t,e.document)},t.afterAfterFrameset.processCharacters=function(t){var n=t.takeRemaining(),r=\"\";for(var i=0;i<n.length;i++){var s=n[i];c(s)&&(r+=s)}r&&(e.reconstructActiveFormattingElements(),e.insertText(r)),r.length<n.length&&e.parseError(\"expected-eof-but-got-char\")},t.afterAfterFrameset.startTagNoFrames=function(e,n){t.inHead.processStartTag(e,n)},t.afterAfterFrameset.startTagOther=function(t,n,r){e.parseError(\"expected-eof-but-got-start-tag\",{name:t})},t.afterAfterFrameset.processEndTag=function(t,n){e.parseError(\"expected-eof-but-got-end-tag\",{name:t})},t.text=Object.create(t.base),t.text.start_tag_handlers={\"-default\":\"startTagOther\"},t.text.end_tag_handlers={script:\"endTagScript\",\"-default\":\"endTagOther\"},t.text.processCharacters=function(t){e.shouldSkipLeadingNewline&&(e.shouldSkipLeadingNewline=!1,t.skipAtMostOneLeadingNewline());var n=t.takeRemaining();if(!n)return;e.insertText(n)},t.text.processEOF=function(){e.parseError(\"expected-named-closing-tag-but-got-eof\",{name:e.currentStackItem().localName}),e.openElements.pop(),e.setInsertionMode(e.originalInsertionMode),e.insertionMode.processEOF()},t.text.startTagOther=function(e){throw\"Tried to process start tag \"+e+\" in RCDATA/RAWTEXT mode\"},t.text.endTagScript=function(t){var n=e.openElements.pop();r.ok(n.localName==\"script\"),e.setInsertionMode(e.originalInsertionMode)},t.text.endTagOther=function(t){e.openElements.pop(),e.setInsertionMode(e.originalInsertionMode)}}function y(e,t){return e.replace(new RegExp(\"{[0-9a-z-]+}\",\"gi\"),function(e){return t[e.slice(1,-1)]||e})}var r=e(\"assert\"),i=e(\"./messages.json\"),s=e(\"./constants\"),o=e(\"events\").EventEmitter,u=e(\"./Tokenizer\").Tokenizer,a=e(\"./ElementStack\").ElementStack,f=e(\"./StackItem\").StackItem,l={};m.prototype.skipAtMostOneLeadingNewline=function(){this.characters[this.current]===\"\\n\"&&this.current++},m.prototype.skipLeadingWhitespace=function(){while(c(this.characters[this.current]))if(++this.current==this.end)return},m.prototype.skipLeadingNonWhitespace=function(){while(!c(this.characters[this.current]))if(++this.current==this.end)return},m.prototype.takeRemaining=function(){return this.characters.substring(this.current)},m.prototype.takeLeadingWhitespace=function(){var e=this.current;return this.skipLeadingWhitespace(),e===this.current?\"\":this.characters.substring(e,this.current-e)},Object.defineProperty(m.prototype,\"length\",{get:function(){return this.end-this.current}}),g.prototype.setInsertionMode=function(e){this.insertionMode=this.insertionModes[e],this.insertionModeName=e},g.prototype.adoptionAgencyEndTag=function(e){function i(e){return e===r}var t=8,n=3,r,s=0;while(s++<t){r=this.elementInActiveFormattingElements(e);if(!r||this.openElements.contains(r)&&!this.openElements.inScope(r.localName))return this.parseError(\"adoption-agency-1.1\",{name:e}),!1;if(!this.openElements.contains(r))return this.parseError(\"adoption-agency-1.2\",{name:e}),this.removeElementFromActiveFormattingElements(r),!0;this.openElements.inScope(r.localName)||this.parseError(\"adoption-agency-4.4\",{name:e}),r!=this.currentStackItem()&&this.parseError(\"adoption-agency-1.3\",{name:e});var o=this.openElements.furthestBlockForFormattingElement(r.node);if(!o)return this.openElements.remove_openElements_until(i),this.removeElementFromActiveFormattingElements(r),!0;var u=this.openElements.elements.indexOf(r),a=this.openElements.item(u-1),l=this.activeFormattingElements.indexOf(r),c=o,h=o,p=this.openElements.elements.indexOf(c),d=0;while(d++<n){p-=1,c=this.openElements.item(p);if(this.activeFormattingElements.indexOf(c)<0){this.openElements.elements.splice(p,1);continue}if(c==r)break;h==o&&(l=this.activeFormattingElements.indexOf(c)+1);var v=this.createElement(c.namespaceURI,c.localName,c.attributes),m=new f(c.namespaceURI,c.localName,c.attributes,v);this.activeFormattingElements[this.activeFormattingElements.indexOf(c)]=m,this.openElements.elements[this.openElements.elements.indexOf(c)]=m,c=m,this.detachFromParent(h.node),this.attachNode(h.node,c.node),h=c}this.detachFromParent(h.node),a.isFosterParenting()?this.insertIntoFosterParent(h.node):this.attachNode(h.node,a.node);var v=this.createElement(\"http://www.w3.org/1999/xhtml\",r.localName,r.attributes),g=new f(r.namespaceURI,r.localName,r.attributes,v);this.reparentChildren(o.node,v),this.attachNode(v,o.node),this.removeElementFromActiveFormattingElements(r),this.activeFormattingElements.splice(Math.min(l,this.activeFormattingElements.length),0,g),this.openElements.remove(r),this.openElements.elements.splice(this.openElements.elements.indexOf(o)+1,0,g)}return!0},g.prototype.start=function(){throw\"Not mplemented\"},g.prototype.startTokenization=function(e){this.tokenizer=e,this.compatMode=\"no quirks\",this.originalInsertionMode=\"initial\",this.framesetOk=!0,this.openElements=new a,this.activeFormattingElements=[],this.start();if(this.context){switch(this.context){case\"title\":case\"textarea\":this.tokenizer.setState(u.RCDATA);break;case\"style\":case\"xmp\":case\"iframe\":case\"noembed\":case\"noframes\":this.tokenizer.setState(u.RAWTEXT);break;case\"script\":this.tokenizer.setState(u.SCRIPT_DATA);break;case\"noscript\":this.scriptingEnabled&&this.tokenizer.setState(u.RAWTEXT);break;case\"plaintext\":this.tokenizer.setState(u.PLAINTEXT)}this.insertHtmlElement(),this.resetInsertionMode()}else this.setInsertionMode(\"initial\")},g.prototype.processToken=function(e){this.selfClosingFlagAcknowledged=!1;var t=this.openElements.top||null,n;!t||!t.isForeign()||t.isMathMLTextIntegrationPoint()&&(e.type==\"StartTag\"&&!(e.name in{mglyph:0,malignmark:0})||e.type===\"Characters\")||t.namespaceURI==\"http://www.w3.org/1998/Math/MathML\"&&t.localName==\"annotation-xml\"&&e.type==\"StartTag\"&&e.name==\"svg\"||t.isHtmlIntegrationPoint()&&e.type in{StartTag:0,Characters:0}||e.type==\"EOF\"?n=this.insertionMode:n=this.insertionModes.inForeignContent;switch(e.type){case\"Characters\":var r=new m(e.data);n.processCharacters(r);break;case\"Comment\":n.processComment(e.data);break;case\"StartTag\":n.processStartTag(e.name,e.data,e.selfClosing);break;case\"EndTag\":n.processEndTag(e.name);break;case\"Doctype\":n.processDoctype(e.name,e.publicId,e.systemId,e.forceQuirks);break;case\"EOF\":n.processEOF()}},g.prototype.isCdataSectionAllowed=function(){return this.openElements.length>0&&this.currentStackItem().isForeign()},g.prototype.isSelfClosingFlagAcknowledged=function(){return this.selfClosingFlagAcknowledged},g.prototype.createElement=function(e,t,n){throw new Error(\"Not implemented\")},g.prototype.attachNode=function(e,t){throw new Error(\"Not implemented\")},g.prototype.attachNodeToFosterParent=function(e,t,n){throw new Error(\"Not implemented\")},g.prototype.detachFromParent=function(e){throw new Error(\"Not implemented\")},g.prototype.addAttributesToElement=function(e,t){throw new Error(\"Not implemented\")},g.prototype.insertHtmlElement=function(e){var t=this.createElement(\"http://www.w3.org/1999/xhtml\",\"html\",e);return this.attachNode(t,this.document),this.openElements.pushHtmlElement(new f(\"http://www.w3.org/1999/xhtml\",\"html\",e,t)),t},g.prototype.insertHeadElement=function(e){var t=this.createElement(\"http://www.w3.org/1999/xhtml\",\"head\",e);return this.head=new f(\"http://www.w3.org/1999/xhtml\",\"head\",e,t),this.attachNode(t,this.openElements.top.node),this.openElements.pushHeadElement(this.head),t},g.prototype.insertBodyElement=function(e){var t=this.createElement(\"http://www.w3.org/1999/xhtml\",\"body\",e);return this.attachNode(t,this.openElements.top.node),this.openElements.pushBodyElement(new f(\"http://www.w3.org/1999/xhtml\",\"body\",e,t)),t},g.prototype.insertIntoFosterParent=function(e){var t=this.openElements.findIndex(\"table\"),n=this.openElements.item(t).node;if(t===0)return this.attachNode(e,n);this.attachNodeToFosterParent(e,n,this.openElements.item(t-1).node)},g.prototype.insertElement=function(e,t,n,r){n||(n=\"http://www.w3.org/1999/xhtml\");var i=this.createElement(n,e,t);this.shouldFosterParent()?this.insertIntoFosterParent(i):this.attachNode(i,this.openElements.top.node),r||this.openElements.push(new f(n,e,t,i))},g.prototype.insertFormattingElement=function(e,t){this.insertElement(e,t,\"http://www.w3.org/1999/xhtml\"),this.appendElementToActiveFormattingElements(this.currentStackItem())},g.prototype.insertSelfClosingElement=function(e,t){this.selfClosingFlagAcknowledged=!0,this.insertElement(e,t,\"http://www.w3.org/1999/xhtml\",!0)},g.prototype.insertForeignElement=function(e,t,n,r){r&&(this.selfClosingFlagAcknowledged=!0),this.insertElement(e,t,n,r)},g.prototype.insertComment=function(e,t){throw new Error(\"Not implemented\")},g.prototype.insertDoctype=function(e,t,n){throw new Error(\"Not implemented\")},g.prototype.insertText=function(e){throw new Error(\"Not implemented\")},g.prototype.currentStackItem=function(){return this.openElements.top},g.prototype.popElement=function(){return this.openElements.pop()},g.prototype.shouldFosterParent=function(){return this.redirectAttachToFosterParent&&this.currentStackItem().isFosterParenting()},g.prototype.generateImpliedEndTags=function(e){var t=this.openElements.top.localName;[\"dd\",\"dt\",\"li\",\"option\",\"optgroup\",\"p\",\"rp\",\"rt\"].indexOf(t)!=-1&&t!=e&&(this.popElement(),this.generateImpliedEndTags(e))},g.prototype.reconstructActiveFormattingElements=function(){if(this.activeFormattingElements.length===0)return;var e=this.activeFormattingElements.length-1,t=this.activeFormattingElements[e];if(t==l||this.openElements.contains(t))return;while(t!=l&&!this.openElements.contains(t)){e-=1,t=this.activeFormattingElements[e];if(!t)break}for(;;){e+=1,t=this.activeFormattingElements[e],this.insertElement(t.localName,t.attributes);var n=this.currentStackItem();this.activeFormattingElements[e]=n;if(n==this.activeFormattingElements[this.activeFormattingElements.length-1])break}},g.prototype.ensureNoahsArkCondition=function(e){var t=3;if(this.activeFormattingElements.length<t)return;var n=[],r=e.attributes.length;for(var i=this.activeFormattingElements.length-1;i>=0;i--){var s=this.activeFormattingElements[i];if(s===l)break;if(e.localName!==s.localName||e.namespaceURI!==s.namespaceURI)continue;if(s.attributes.length!=r)continue;n.push(s)}if(n.length<t)return;var o=[],u=e.attributes;for(var i=0;i<u.length;i++){var a=u[i];for(var f=0;f<n.length;f++){var s=n[f],c=v(s,a.nodeName);c&&c.nodeValue===a.nodeValue&&o.push(s)}if(o.length<t)return;n=o,o=[]}for(var i=t-1;i<n.length;i++)this.removeElementFromActiveFormattingElements(n[i])},g.prototype.appendElementToActiveFormattingElements=function(e){this.ensureNoahsArkCondition(e),this.activeFormattingElements.push(e)},g.prototype.removeElementFromActiveFormattingElements=function(e){var t=this.activeFormattingElements.indexOf(e);t>=0&&this.activeFormattingElements.splice(t,1)},g.prototype.elementInActiveFormattingElements=function(e){var t=this.activeFormattingElements;for(var n=t.length-1;n>=0;n--){if(t[n]==l)break;if(t[n].localName==e)return t[n]}return!1},g.prototype.clearActiveFormattingElements=function(){while(this.activeFormattingElements.length!==0&&this.activeFormattingElements.pop()!=l);},g.prototype.reparentChildren=function(e,t){throw new Error(\"Not implemented\")},g.prototype.setFragmentContext=function(e){this.context=e},g.prototype.parseError=function(e,t){if(!this.errorHandler)return;var n=y(i[e],t);this.errorHandler.error(n,this.tokenizer._inputStream.location(),e)},g.prototype.resetInsertionMode=function(){var e=!1,t=null;for(var n=this.openElements.length-1;n>=0;n--){t=this.openElements.item(n),n===0&&(r.ok(this.context),e=!0,t=new f(\"http://www.w3.org/1999/xhtml\",this.context,[],null));if(t.namespaceURI===\"http://www.w3.org/1999/xhtml\"){if(t.localName===\"select\")return this.setInsertionMode(\"inSelect\");if(t.localName===\"td\"||t.localName===\"th\")return this.setInsertionMode(\"inCell\");if(t.localName===\"tr\")return this.setInsertionMode(\"inRow\");if(t.localName===\"tbody\"||t.localName===\"thead\"||t.localName===\"tfoot\")return this.setInsertionMode(\"inTableBody\");if(t.localName===\"caption\")return this.setInsertionMode(\"inCaption\");if(t.localName===\"colgroup\")return this.setInsertionMode(\"inColumnGroup\");if(t.localName===\"table\")return this.setInsertionMode(\"inTable\");if(t.localName===\"head\"&&!e)return this.setInsertionMode(\"inHead\");if(t.localName===\"body\")return this.setInsertionMode(\"inBody\");if(t.localName===\"frameset\")return this.setInsertionMode(\"inFrameset\");if(t.localName===\"html\")return this.openElements.headElement?this.setInsertionMode(\"afterHead\"):this.setInsertionMode(\"beforeHead\")}if(e)return this.setInsertionMode(\"inBody\")}},g.prototype.processGenericRCDATAStartTag=function(e,t){this.insertElement(e,t),this.tokenizer.setState(u.RCDATA),this.originalInsertionMode=this.insertionModeName,this.setInsertionMode(\"text\")},g.prototype.processGenericRawTextStartTag=function(e,t){this.insertElement(e,t),this.tokenizer.setState(u.RAWTEXT),this.originalInsertionMode=this.insertionModeName,this.setInsertionMode(\"text\")},g.prototype.adjustMathMLAttributes=function(e){return e.forEach(function(e){e.namespaceURI=\"http://www.w3.org/1998/Math/MathML\",s.MATHMLAttributeMap[e.nodeName]&&(e.nodeName=s.MATHMLAttributeMap[e.nodeName])}),e},g.prototype.adjustSVGTagNameCase=function(e){return s.SVGTagMap[e]||e},g.prototype.adjustSVGAttributes=function(e){return e.forEach(function(e){e.namespaceURI=\"http://www.w3.org/2000/svg\",s.SVGAttributeMap[e.nodeName]&&(e.nodeName=s.SVGAttributeMap[e.nodeName])}),e},g.prototype.adjustForeignAttributes=function(e){for(var t=0;t<e.length;t++){var n=e[t],r=s.ForeignAttributeMap[n.nodeName];r&&(n.nodeName=r.localName,n.prefix=r.prefix,n.namespaceURI=r.namespaceURI)}return e},n.TreeBuilder=g},{\"./ElementStack\":1,\"./StackItem\":4,\"./Tokenizer\":5,\"./constants\":7,\"./messages.json\":8,assert:13,events:16}],7:[function(e,t,n){n.SVGTagMap={altglyph:\"altGlyph\",altglyphdef:\"altGlyphDef\",altglyphitem:\"altGlyphItem\",animatecolor:\"animateColor\",animatemotion:\"animateMotion\",animatetransform:\"animateTransform\",clippath:\"clipPath\",feblend:\"feBlend\",fecolormatrix:\"feColorMatrix\",fecomponenttransfer:\"feComponentTransfer\",fecomposite:\"feComposite\",feconvolvematrix:\"feConvolveMatrix\",fediffuselighting:\"feDiffuseLighting\",fedisplacementmap:\"feDisplacementMap\",fedistantlight:\"feDistantLight\",feflood:\"feFlood\",fefunca:\"feFuncA\",fefuncb:\"feFuncB\",fefuncg:\"feFuncG\",fefuncr:\"feFuncR\",fegaussianblur:\"feGaussianBlur\",feimage:\"feImage\",femerge:\"feMerge\",femergenode:\"feMergeNode\",femorphology:\"feMorphology\",feoffset:\"feOffset\",fepointlight:\"fePointLight\",fespecularlighting:\"feSpecularLighting\",fespotlight:\"feSpotLight\",fetile:\"feTile\",feturbulence:\"feTurbulence\",foreignobject:\"foreignObject\",glyphref:\"glyphRef\",lineargradient:\"linearGradient\",radialgradient:\"radialGradient\",textpath:\"textPath\"},n.MATHMLAttributeMap={definitionurl:\"definitionURL\"},n.SVGAttributeMap={attributename:\"attributeName\",attributetype:\"attributeType\",basefrequency:\"baseFrequency\",baseprofile:\"baseProfile\",calcmode:\"calcMode\",clippathunits:\"clipPathUnits\",contentscripttype:\"contentScriptType\",contentstyletype:\"contentStyleType\",diffuseconstant:\"diffuseConstant\",edgemode:\"edgeMode\",externalresourcesrequired:\"externalResourcesRequired\",filterres:\"filterRes\",filterunits:\"filterUnits\",glyphref:\"glyphRef\",gradienttransform:\"gradientTransform\",gradientunits:\"gradientUnits\",kernelmatrix:\"kernelMatrix\",kernelunitlength:\"kernelUnitLength\",keypoints:\"keyPoints\",keysplines:\"keySplines\",keytimes:\"keyTimes\",lengthadjust:\"lengthAdjust\",limitingconeangle:\"limitingConeAngle\",markerheight:\"markerHeight\",markerunits:\"markerUnits\",markerwidth:\"markerWidth\",maskcontentunits:\"maskContentUnits\",maskunits:\"maskUnits\",numoctaves:\"numOctaves\",pathlength:\"pathLength\",patterncontentunits:\"patternContentUnits\",patterntransform:\"patternTransform\",patternunits:\"patternUnits\",pointsatx:\"pointsAtX\",pointsaty:\"pointsAtY\",pointsatz:\"pointsAtZ\",preservealpha:\"preserveAlpha\",preserveaspectratio:\"preserveAspectRatio\",primitiveunits:\"primitiveUnits\",refx:\"refX\",refy:\"refY\",repeatcount:\"repeatCount\",repeatdur:\"repeatDur\",requiredextensions:\"requiredExtensions\",requiredfeatures:\"requiredFeatures\",specularconstant:\"specularConstant\",specularexponent:\"specularExponent\",spreadmethod:\"spreadMethod\",startoffset:\"startOffset\",stddeviation:\"stdDeviation\",stitchtiles:\"stitchTiles\",surfacescale:\"surfaceScale\",systemlanguage:\"systemLanguage\",tablevalues:\"tableValues\",targetx:\"targetX\",targety:\"targetY\",textlength:\"textLength\",viewbox:\"viewBox\",viewtarget:\"viewTarget\",xchannelselector:\"xChannelSelector\",ychannelselector:\"yChannelSelector\",zoomandpan:\"zoomAndPan\"},n.ForeignAttributeMap={\"xlink:actuate\":{prefix:\"xlink\",localName:\"actuate\",namespaceURI:\"http://www.w3.org/1999/xlink\"},\"xlink:arcrole\":{prefix:\"xlink\",localName:\"arcrole\",namespaceURI:\"http://www.w3.org/1999/xlink\"},\"xlink:href\":{prefix:\"xlink\",localName:\"href\",namespaceURI:\"http://www.w3.org/1999/xlink\"},\"xlink:role\":{prefix:\"xlink\",localName:\"role\",namespaceURI:\"http://www.w3.org/1999/xlink\"},\"xlink:show\":{prefix:\"xlink\",localName:\"show\",namespaceURI:\"http://www.w3.org/1999/xlink\"},\"xlink:title\":{prefix:\"xlink\",localName:\"title\",namespaceURI:\"http://www.w3.org/1999/xlink\"},\"xlink:type\":{prefix:\"xlink\",localName:\"title\",namespaceURI:\"http://www.w3.org/1999/xlink\"},\"xml:base\":{prefix:\"xml\",localName:\"base\",namespaceURI:\"http://www.w3.org/XML/1998/namespace\"},\"xml:lang\":{prefix:\"xml\",localName:\"lang\",namespaceURI:\"http://www.w3.org/XML/1998/namespace\"},\"xml:space\":{prefix:\"xml\",localName:\"space\",namespaceURI:\"http://www.w3.org/XML/1998/namespace\"},xmlns:{prefix:null,localName:\"xmlns\",namespaceURI:\"http://www.w3.org/2000/xmlns/\"},\"xmlns:xlink\":{prefix:\"xmlns\",localName:\"xlink\",namespaceURI:\"http://www.w3.org/2000/xmlns/\"}}},{}],8:[function(e,t,n){t.exports={\"null-character\":\"Null character in input stream, replaced with U+FFFD.\",\"invalid-codepoint\":\"Invalid codepoint in stream\",\"incorrectly-placed-solidus\":\"Solidus (/) incorrectly placed in tag.\",\"incorrect-cr-newline-entity\":\"Incorrect CR newline entity, replaced with LF.\",\"illegal-windows-1252-entity\":\"Entity used with illegal number (windows-1252 reference).\",\"cant-convert-numeric-entity\":\"Numeric entity couldn't be converted to character (codepoint U+{charAsInt}).\",\"invalid-numeric-entity-replaced\":\"Numeric entity represents an illegal codepoint. Expanded to the C1 controls range.\",\"numeric-entity-without-semicolon\":\"Numeric entity didn't end with ';'.\",\"expected-numeric-entity-but-got-eof\":\"Numeric entity expected. Got end of file instead.\",\"expected-numeric-entity\":\"Numeric entity expected but none found.\",\"named-entity-without-semicolon\":\"Named entity didn't end with ';'.\",\"expected-named-entity\":\"Named entity expected. Got none.\",\"attributes-in-end-tag\":\"End tag contains unexpected attributes.\",\"self-closing-flag-on-end-tag\":\"End tag contains unexpected self-closing flag.\",\"bare-less-than-sign-at-eof\":\"End of file after <.\",\"expected-tag-name-but-got-right-bracket\":\"Expected tag name. Got '>' instead.\",\"expected-tag-name-but-got-question-mark\":\"Expected tag name. Got '?' instead. (HTML doesn't support processing instructions.)\",\"expected-tag-name\":\"Expected tag name. Got something else instead.\",\"expected-closing-tag-but-got-right-bracket\":\"Expected closing tag. Got '>' instead. Ignoring '</>'.\",\"expected-closing-tag-but-got-eof\":\"Expected closing tag. Unexpected end of file.\",\"expected-closing-tag-but-got-char\":\"Expected closing tag. Unexpected character '{data}' found.\",\"eof-in-tag-name\":\"Unexpected end of file in the tag name.\",\"expected-attribute-name-but-got-eof\":\"Unexpected end of file. Expected attribute name instead.\",\"eof-in-attribute-name\":\"Unexpected end of file in attribute name.\",\"invalid-character-in-attribute-name\":\"Invalid character in attribute name.\",\"duplicate-attribute\":\"Dropped duplicate attribute '{name}' on tag.\",\"expected-end-of-tag-but-got-eof\":\"Unexpected end of file. Expected = or end of tag.\",\"expected-attribute-value-but-got-eof\":\"Unexpected end of file. Expected attribute value.\",\"expected-attribute-value-but-got-right-bracket\":\"Expected attribute value. Got '>' instead.\",\"unexpected-character-in-unquoted-attribute-value\":\"Unexpected character in unquoted attribute\",\"invalid-character-after-attribute-name\":\"Unexpected character after attribute name.\",\"unexpected-character-after-attribute-value\":\"Unexpected character after attribute value.\",\"eof-in-attribute-value-double-quote\":'Unexpected end of file in attribute value (\").',\"eof-in-attribute-value-single-quote\":\"Unexpected end of file in attribute value (').\",\"eof-in-attribute-value-no-quotes\":\"Unexpected end of file in attribute value.\",\"eof-after-attribute-value\":\"Unexpected end of file after attribute value.\",\"unexpected-eof-after-solidus-in-tag\":\"Unexpected end of file in tag. Expected >.\",\"unexpected-character-after-solidus-in-tag\":\"Unexpected character after / in tag. Expected >.\",\"expected-dashes-or-doctype\":\"Expected '--' or 'DOCTYPE'. Not found.\",\"unexpected-bang-after-double-dash-in-comment\":\"Unexpected ! after -- in comment.\",\"incorrect-comment\":\"Incorrect comment.\",\"eof-in-comment\":\"Unexpected end of file in comment.\",\"eof-in-comment-end-dash\":\"Unexpected end of file in comment (-).\",\"unexpected-dash-after-double-dash-in-comment\":\"Unexpected '-' after '--' found in comment.\",\"eof-in-comment-double-dash\":\"Unexpected end of file in comment (--).\",\"eof-in-comment-end-bang-state\":\"Unexpected end of file in comment.\",\"unexpected-char-in-comment\":\"Unexpected character in comment found.\",\"need-space-after-doctype\":\"No space after literal string 'DOCTYPE'.\",\"expected-doctype-name-but-got-right-bracket\":\"Unexpected > character. Expected DOCTYPE name.\",\"expected-doctype-name-but-got-eof\":\"Unexpected end of file. Expected DOCTYPE name.\",\"eof-in-doctype-name\":\"Unexpected end of file in DOCTYPE name.\",\"eof-in-doctype\":\"Unexpected end of file in DOCTYPE.\",\"expected-space-or-right-bracket-in-doctype\":\"Expected space or '>'. Got '{data}'.\",\"unexpected-end-of-doctype\":\"Unexpected end of DOCTYPE.\",\"unexpected-char-in-doctype\":\"Unexpected character in DOCTYPE.\",\"eof-in-bogus-doctype\":\"Unexpected end of file in bogus doctype.\",\"eof-in-innerhtml\":\"Unexpected EOF in inner html mode.\",\"unexpected-doctype\":\"Unexpected DOCTYPE. Ignored.\",\"non-html-root\":\"html needs to be the first start tag.\",\"expected-doctype-but-got-eof\":\"Unexpected End of file. Expected DOCTYPE.\",\"unknown-doctype\":\"Erroneous DOCTYPE. Expected <!DOCTYPE html>.\",\"quirky-doctype\":\"Quirky doctype. Expected <!DOCTYPE html>.\",\"almost-standards-doctype\":\"Almost standards mode doctype. Expected <!DOCTYPE html>.\",\"obsolete-doctype\":\"Obsolete doctype. Expected <!DOCTYPE html>.\",\"expected-doctype-but-got-chars\":\"Non-space characters found without seeing a doctype first. Expected e.g. <!DOCTYPE html>.\",\"expected-doctype-but-got-start-tag\":\"Start tag seen without seeing a doctype first. Expected e.g. <!DOCTYPE html>.\",\"expected-doctype-but-got-end-tag\":\"End tag seen without seeing a doctype first. Expected e.g. <!DOCTYPE html>.\",\"end-tag-after-implied-root\":\"Unexpected end tag ({name}) after the (implied) root element.\",\"expected-named-closing-tag-but-got-eof\":\"Unexpected end of file. Expected end tag ({name}).\",\"two-heads-are-not-better-than-one\":\"Unexpected start tag head in existing head. Ignored.\",\"unexpected-end-tag\":\"Unexpected end tag ({name}). Ignored.\",\"unexpected-implied-end-tag\":\"End tag {name} implied, but there were open elements.\",\"unexpected-start-tag-out-of-my-head\":\"Unexpected start tag ({name}) that can be in head. Moved.\",\"unexpected-start-tag\":\"Unexpected start tag ({name}).\",\"missing-end-tag\":\"Missing end tag ({name}).\",\"missing-end-tags\":\"Missing end tags ({name}).\",\"unexpected-start-tag-implies-end-tag\":\"Unexpected start tag ({startName}) implies end tag ({endName}).\",\"unexpected-start-tag-treated-as\":\"Unexpected start tag ({originalName}). Treated as {newName}.\",\"deprecated-tag\":\"Unexpected start tag {name}. Don't use it!\",\"unexpected-start-tag-ignored\":\"Unexpected start tag {name}. Ignored.\",\"expected-one-end-tag-but-got-another\":\"Unexpected end tag ({gotName}). Missing end tag ({expectedName}).\",\"end-tag-too-early\":\"End tag ({name}) seen too early. Expected other end tag.\",\"end-tag-too-early-named\":\"Unexpected end tag ({gotName}). Expected end tag ({expectedName}.\",\"end-tag-too-early-ignored\":\"End tag ({name}) seen too early. Ignored.\",\"adoption-agency-1.1\":\"End tag ({name}) violates step 1, paragraph 1 of the adoption agency algorithm.\",\"adoption-agency-1.2\":\"End tag ({name}) violates step 1, paragraph 2 of the adoption agency algorithm.\",\"adoption-agency-1.3\":\"End tag ({name}) violates step 1, paragraph 3 of the adoption agency algorithm.\",\"adoption-agency-4.4\":\"End tag ({name}) violates step 4, paragraph 4 of the adoption agency algorithm.\",\"unexpected-end-tag-treated-as\":\"Unexpected end tag ({originalName}). Treated as {newName}.\",\"no-end-tag\":\"This element ({name}) has no end tag.\",\"unexpected-implied-end-tag-in-table\":\"Unexpected implied end tag ({name}) in the table phase.\",\"unexpected-implied-end-tag-in-table-body\":\"Unexpected implied end tag ({name}) in the table body phase.\",\"unexpected-char-implies-table-voodoo\":\"Unexpected non-space characters in table context caused voodoo mode.\",\"unexpected-hidden-input-in-table\":\"Unexpected input with type hidden in table context.\",\"unexpected-form-in-table\":\"Unexpected form in table context.\",\"unexpected-start-tag-implies-table-voodoo\":\"Unexpected start tag ({name}) in table context caused voodoo mode.\",\"unexpected-end-tag-implies-table-voodoo\":\"Unexpected end tag ({name}) in table context caused voodoo mode.\",\"unexpected-cell-in-table-body\":\"Unexpected table cell start tag ({name}) in the table body phase.\",\"unexpected-cell-end-tag\":\"Got table cell end tag ({name}) while required end tags are missing.\",\"unexpected-end-tag-in-table-body\":\"Unexpected end tag ({name}) in the table body phase. Ignored.\",\"unexpected-implied-end-tag-in-table-row\":\"Unexpected implied end tag ({name}) in the table row phase.\",\"unexpected-end-tag-in-table-row\":\"Unexpected end tag ({name}) in the table row phase. Ignored.\",\"unexpected-select-in-select\":\"Unexpected select start tag in the select phase treated as select end tag.\",\"unexpected-input-in-select\":\"Unexpected input start tag in the select phase.\",\"unexpected-start-tag-in-select\":\"Unexpected start tag token ({name}) in the select phase. Ignored.\",\"unexpected-end-tag-in-select\":\"Unexpected end tag ({name}) in the select phase. Ignored.\",\"unexpected-table-element-start-tag-in-select-in-table\":\"Unexpected table element start tag ({name}) in the select in table phase.\",\"unexpected-table-element-end-tag-in-select-in-table\":\"Unexpected table element end tag ({name}) in the select in table phase.\",\"unexpected-char-after-body\":\"Unexpected non-space characters in the after body phase.\",\"unexpected-start-tag-after-body\":\"Unexpected start tag token ({name}) in the after body phase.\",\"unexpected-end-tag-after-body\":\"Unexpected end tag token ({name}) in the after body phase.\",\"unexpected-char-in-frameset\":\"Unepxected characters in the frameset phase. Characters ignored.\",\"unexpected-start-tag-in-frameset\":\"Unexpected start tag token ({name}) in the frameset phase. Ignored.\",\"unexpected-frameset-in-frameset-innerhtml\":\"Unexpected end tag token (frameset in the frameset phase (innerHTML).\",\"unexpected-end-tag-in-frameset\":\"Unexpected end tag token ({name}) in the frameset phase. Ignored.\",\"unexpected-char-after-frameset\":\"Unexpected non-space characters in the after frameset phase. Ignored.\",\"unexpected-start-tag-after-frameset\":\"Unexpected start tag ({name}) in the after frameset phase. Ignored.\",\"unexpected-end-tag-after-frameset\":\"Unexpected end tag ({name}) in the after frameset phase. Ignored.\",\"expected-eof-but-got-char\":\"Unexpected non-space characters. Expected end of file.\",\"expected-eof-but-got-start-tag\":\"Unexpected start tag ({name}). Expected end of file.\",\"expected-eof-but-got-end-tag\":\"Unexpected end tag ({name}). Expected end of file.\",\"unexpected-end-table-in-caption\":\"Unexpected end table tag in caption. Generates implied end caption.\",\"end-html-in-innerhtml\":\"Unexpected html end tag in inner html mode.\",\"eof-in-table\":\"Unexpected end of file. Expected table content.\",\"eof-in-script\":\"Unexpected end of file. Expected script content.\",\"non-void-element-with-trailing-solidus\":\"Trailing solidus not allowed on element {name}.\",\"unexpected-html-element-in-foreign-content\":'HTML start tag \"{name}\" in a foreign namespace context.',\"unexpected-start-tag-in-table\":\"Unexpected {name}. Expected table content.\"}},{}],9:[function(e,t,n){function o(){this.contentHandler=null,this._errorHandler=null,this._treeBuilder=new r,this._tokenizer=new i(this._treeBuilder),this._scriptingEnabled=!1}var r=e(\"./SAXTreeBuilder\").SAXTreeBuilder,i=e(\"../Tokenizer\").Tokenizer,s=e(\"./TreeParser\").TreeParser;o.prototype.parse=function(e){this._tokenizer.tokenize(e);var t=this._treeBuilder.document;t&&(new s(this.contentHandler)).parse(t)},o.prototype.parseFragment=function(e,t){this._treeBuilder.setFragmentContext(t),this._tokenizer.tokenize(e);var n=this._treeBuilder.getFragment();n&&(new s(this.contentHandler)).parse(n)},Object.defineProperty(o.prototype,\"scriptingEnabled\",{get:function(){return this._scriptingEnabled},set:function(e){this._scriptingEnabled=e,this._treeBuilder.scriptingEnabled=e}}),Object.defineProperty(o.prototype,\"errorHandler\",{get:function(){return this._errorHandler},set:function(e){this._errorHandler=e,this._treeBuilder.errorHandler=e}}),n.SAXParser=o},{\"../Tokenizer\":5,\"./SAXTreeBuilder\":10,\"./TreeParser\":11}],10:[function(e,t,n){function s(){i.call(this)}function o(e,t){for(var n=0;n<e.attributes.length;n++){var r=e.attributes[n];if(r.nodeName===t)return r.nodeValue}}function a(e){e?(this.columnNumber=e.columnNumber,this.lineNumber=e.lineNumber):(this.columnNumber=-1,this.lineNumber=-1),this.parentNode=null,this.nextSibling=null,this.firstChild=null}function f(e){a.call(this,e),this.lastChild=null,this._endLocator=null}function l(e){f.call(this,e),this.nodeType=u.DOCUMENT}function c(){f.call(this,new Locator),this.nodeType=u.DOCUMENT_FRAGMENT}function h(e,t,n,r,i,s){f.call(this,e),this.uri=t,this.localName=n,this.qName=r,this.attributes=i,this.prefixMappings=s,this.nodeType=u.ELEMENT}function p(e,t){a.call(this,e),this.data=t,this.nodeType=u.CHARACTERS}function d(e,t){a.call(this,e),this.data=t,this.nodeType=u.IGNORABLE_WHITESPACE}function v(e,t){a.call(this,e),this.data=t,this.nodeType=u.COMMENT}function m(e){f.call(this,e),this.nodeType=u.CDATA}function g(e){f.call(this),this.name=e,this.nodeType=u.ENTITY}function y(e){a.call(this),this.name=e,this.nodeType=u.SKIPPED_ENTITY}function b(e,t){a.call(this),this.target=e,this.data=t}function w(e,t,n){f.call(this),this.name=e,this.publicIdentifier=t,this.systemIdentifier=n,this.nodeType=u.DTD}var r=e(\"util\"),i=e(\"../TreeBuilder\").TreeBuilder;r.inherits(s,i),s.prototype.start=function(e){this.document=new l(this.tokenizer)},s.prototype.end=function(){this.document.endLocator=this.tokenizer},s.prototype.insertDoctype=function(e,t,n){var r=new w(this.tokenizer,e,t,n);r.endLocator=this.tokenizer,this.document.appendChild(r)},s.prototype.createElement=function(e,t,n){var r=new h(this.tokenizer,e,t,t,n||[]);return r},s.prototype.insertComment=function(e,t){t||(t=this.currentStackItem());var n=new v(this.tokenizer,e);t.appendChild(n)},s.prototype.appendCharacters=function(e,t){var n=new p(this.tokenizer,t);e.appendChild(n)},s.prototype.insertText=function(e){if(this.redirectAttachToFosterParent&&this.openElements.top.isFosterParenting()){var t=this.openElements.findIndex(\"table\"),n=this.openElements.item(t),r=n.node;if(t===0)return this.appendCharacters(r,e);var i=new p(this.tokenizer,e),s=r.parentNode;if(s){s.insertBetween(i,r.previousSibling,r);return}var o=this.openElements.item(t-1).node;o.appendChild(i);return}this.appendCharacters(this.currentStackItem().node,e)},s.prototype.attachNode=function(e,t){t.appendChild(e)},s.prototype.attachNodeToFosterParent=function(e,t,n){var r=t.parentNode;r?r.insertBetween(e,t.previousSibling,t):n.appendChild(e)},s.prototype.detachFromParent=function(e){e.detach()},s.prototype.reparentChildren=function(e,t){t.appendChildren(e.firstChild)},s.prototype.getFragment=function(){var e=new c;return this.reparentChildren(this.openElements.rootNode,e),e},s.prototype.addAttributesToElement=function(e,t){for(var n=0;n<t.length;n++){var r=t[n];o(e,r.nodeName)||e.attributes.push(r)}};var u={CDATA:1,CHARACTERS:2,COMMENT:3,DOCUMENT:4,DOCUMENT_FRAGMENT:5,DTD:6,ELEMENT:7,ENTITY:8,IGNORABLE_WHITESPACE:9,PROCESSING_INSTRUCTION:10,SKIPPED_ENTITY:11};a.prototype.visit=function(e){throw new Error(\"Not Implemented\")},a.prototype.revisit=function(e){return},a.prototype.detach=function(){this.parentNode!==null&&(this.parentNode.removeChild(this),this.parentNode=null)},Object.defineProperty(a.prototype,\"previousSibling\",{get:function(){var e=null,t=this.parentNode.firstChild;for(;;){if(this==t)return e;e=t,t=t.nextSibling}}}),f.prototype=Object.create(a.prototype),f.prototype.insertBefore=function(e,t){if(!t)return this.appendChild(e);e.detach(),e.parentNode=this;if(this.firstChild==t)e.nextSibling=t,this.firstChild=e;else{var n=this.firstChild,r=this.firstChild.nextSibling;while(r!=t)n=r,r=r.nextSibling;n.nextSibling=e,e.nextSibling=r}return e},f.prototype.insertBetween=function(e,t,n){return n?(e.detach(),e.parentNode=this,e.nextSibling=n,t?t.nextSibling=e:firstChild=e,e):this.appendChild(e)},f.prototype.appendChild=function(e){return e.detach(),e.parentNode=this,this.firstChild?this.lastChild.nextSibling=e:this.firstChild=e,this.lastChild=e,e},f.prototype.appendChildren=function(e){var t=e.firstChild;if(!t)return;var n=e;this.firstChild?this.lastChild.nextSibling=t:this.firstChild=t,this.lastChild=n.lastChild;do t.parentNode=this;while(t=t.nextSibling);n.firstChild=null,n.lastChild=null},f.prototype.removeChild=function(e){if(this.firstChild==e)this.firstChild=e.nextSibling,this.lastChild==e&&(this.lastChild=null);else{var t=this.firstChild,n=this.firstChild.nextSibling;while(n!=e)t=n,n=n.nextSibling;t.nextSibling=e.nextSibling,this.lastChild==e&&(this.lastChild=t)}return e.parentNode=null,e},Object.defineProperty(f.prototype,\"endLocator\",{get:function(){return this._endLocator},set:function(e){this._endLocator={lineNumber:e.lineNumber,columnNumber:e.columnNumber}}}),l.prototype=Object.create(f.prototype),l.prototype.visit=function(e){e.startDocument(this)},l.prototype.revisit=function(e){e.endDocument(this.endLocator)},c.prototype=Object.create(f.prototype),c.prototype.visit=function(e){},h.prototype=Object.create(f.prototype),h.prototype.visit=function(e){if(this.prefixMappings)for(var t in prefixMappings){var n=prefixMappings[t];e.startPrefixMapping(n.getPrefix(),n.getUri(),this)}e.startElement(this.uri,this.localName,this.qName,this.attributes,this)},h.prototype.revisit=function(e){e.endElement(this.uri,this.localName,this.qName,this.endLocator);if(this.prefixMappings)for(var t in prefixMappings){var n=prefixMappings[t];e.endPrefixMapping(n.getPrefix(),this.endLocator)}},p.prototype=Object.create(a.prototype),p.prototype.visit=function(e){e.characters(this.data,0,this.data.length,this)},d.prototype=Object.create(a.prototype),d.prototype.visit=function(e){e.ignorableWhitespace(this.data,0,this.data.length,this)},v.prototype=Object.create(a.prototype),v.prototype.visit=function(e){e.comment(this.data,0,this.data.length,this)},m.prototype=Object.create(f.prototype),m.prototype.visit=function(e){e.startCDATA(this)},m.prototype.revisit=function(e){e.endCDATA(this.endLocator)},g.prototype=Object.create(f.prototype),g.prototype.visit=function(e){e.startEntity(this.name,this)},g.prototype.revisit=function(e){e.endEntity(this.name)},y.prototype=Object.create(a.prototype),y.prototype.visit=function(e){e.skippedEntity(this.name,this)},b.prototype=Object.create(a.prototype),b.prototype.visit=function(e){e.processingInstruction(this.target,this.data,this)},b.prototype.getNodeType=function(){return u.PROCESSING_INSTRUCTION},w.prototype=Object.create(f.prototype),w.prototype.visit=function(e){e.startDTD(this.name,this.publicIdentifier,this.systemIdentifier,this)},w.prototype.revisit=function(e){e.endDTD()},n.SAXTreeBuilder=s},{\"../TreeBuilder\":6,util:20}],11:[function(e,t,n){function r(e,t){this.contentHandler,this.lexicalHandler,this.locatorDelegate;if(!e)throw new IllegalArgumentException(\"contentHandler was null.\");this.contentHandler=e,t?this.lexicalHandler=t:this.lexicalHandler=new i}function i(){}r.prototype.parse=function(e){this.contentHandler.documentLocator=this;var t=e,n;for(;;){t.visit(this);if(n=t.firstChild){t=n;continue}for(;;){t.revisit(this);if(t==e)return;if(n=t.nextSibling){t=n;break}t=t.parentNode}}},r.prototype.characters=function(e,t,n,r){this.locatorDelegate=r,this.contentHandler.characters(e,t,n)},r.prototype.endDocument=function(e){this.locatorDelegate=e,this.contentHandler.endDocument()},r.prototype.endElement=function(e,t,n,r){this.locatorDelegate=r,this.contentHandler.endElement(e,t,n)},r.prototype.endPrefixMapping=function(e,t){this.locatorDelegate=t,this.contentHandler.endPrefixMapping(e)},r.prototype.ignorableWhitespace=function(e,t,n,r){this.locatorDelegate=r,this.contentHandler.ignorableWhitespace(e,t,n)},r.prototype.processingInstruction=function(e,t,n){this.locatorDelegate=n,this.contentHandler.processingInstruction(e,t)},r.prototype.skippedEntity=function(e,t){this.locatorDelegate=t,this.contentHandler.skippedEntity(e)},r.prototype.startDocument=function(e){this.locatorDelegate=e,this.contentHandler.startDocument()},r.prototype.startElement=function(e,t,n,r,i){this.locatorDelegate=i,this.contentHandler.startElement(e,t,n,r)},r.prototype.startPrefixMapping=function(e,t,n){this.locatorDelegate=n,this.contentHandler.startPrefixMapping(e,t)},r.prototype.comment=function(e,t,n,r){this.locatorDelegate=r,this.lexicalHandler.comment(e,t,n)},r.prototype.endCDATA=function(e){this.locatorDelegate=e,this.lexicalHandler.endCDATA()},r.prototype.endDTD=function(e){this.locatorDelegate=e,this.lexicalHandler.endDTD()},r.prototype.endEntity=function(e,t){this.locatorDelegate=t,this.lexicalHandler.endEntity(e)},r.prototype.startCDATA=function(e){this.locatorDelegate=e,this.lexicalHandler.startCDATA()},r.prototype.startDTD=function(e,t,n,r){this.locatorDelegate=r,this.lexicalHandler.startDTD(e,t,n)},r.prototype.startEntity=function(e,t){this.locatorDelegate=t,this.lexicalHandler.startEntity(e)},Object.defineProperty(r.prototype,\"columnNumber\",{get:function(){return this.locatorDelegate?this.locatorDelegate.columnNumber:-1}}),Object.defineProperty(r.prototype,\"lineNumber\",{get:function(){return this.locatorDelegate?this.locatorDelegate.lineNumber:-1}}),i.prototype.comment=function(){},i.prototype.endCDATA=function(){},i.prototype.endDTD=function(){},i.prototype.endEntity=function(){},i.prototype.startCDATA=function(){},i.prototype.startDTD=function(){},i.prototype.startEntity=function(){},n.TreeParser=r},{}],12:[function(e,t,n){t.exports={\"Aacute;\":\"\\u00c1\",Aacute:\"\\u00c1\",\"aacute;\":\"\\u00e1\",aacute:\"\\u00e1\",\"Abreve;\":\"\\u0102\",\"abreve;\":\"\\u0103\",\"ac;\":\"\\u223e\",\"acd;\":\"\\u223f\",\"acE;\":\"\\u223e\\u0333\",\"Acirc;\":\"\\u00c2\",Acirc:\"\\u00c2\",\"acirc;\":\"\\u00e2\",acirc:\"\\u00e2\",\"acute;\":\"\\u00b4\",acute:\"\\u00b4\",\"Acy;\":\"\\u0410\",\"acy;\":\"\\u0430\",\"AElig;\":\"\\u00c6\",AElig:\"\\u00c6\",\"aelig;\":\"\\u00e6\",aelig:\"\\u00e6\",\"af;\":\"\\u2061\",\"Afr;\":\"\\ud835\\udd04\",\"afr;\":\"\\ud835\\udd1e\",\"Agrave;\":\"\\u00c0\",Agrave:\"\\u00c0\",\"agrave;\":\"\\u00e0\",agrave:\"\\u00e0\",\"alefsym;\":\"\\u2135\",\"aleph;\":\"\\u2135\",\"Alpha;\":\"\\u0391\",\"alpha;\":\"\\u03b1\",\"Amacr;\":\"\\u0100\",\"amacr;\":\"\\u0101\",\"amalg;\":\"\\u2a3f\",\"amp;\":\"&\",amp:\"&\",\"AMP;\":\"&\",AMP:\"&\",\"andand;\":\"\\u2a55\",\"And;\":\"\\u2a53\",\"and;\":\"\\u2227\",\"andd;\":\"\\u2a5c\",\"andslope;\":\"\\u2a58\",\"andv;\":\"\\u2a5a\",\"ang;\":\"\\u2220\",\"ange;\":\"\\u29a4\",\"angle;\":\"\\u2220\",\"angmsdaa;\":\"\\u29a8\",\"angmsdab;\":\"\\u29a9\",\"angmsdac;\":\"\\u29aa\",\"angmsdad;\":\"\\u29ab\",\"angmsdae;\":\"\\u29ac\",\"angmsdaf;\":\"\\u29ad\",\"angmsdag;\":\"\\u29ae\",\"angmsdah;\":\"\\u29af\",\"angmsd;\":\"\\u2221\",\"angrt;\":\"\\u221f\",\"angrtvb;\":\"\\u22be\",\"angrtvbd;\":\"\\u299d\",\"angsph;\":\"\\u2222\",\"angst;\":\"\\u00c5\",\"angzarr;\":\"\\u237c\",\"Aogon;\":\"\\u0104\",\"aogon;\":\"\\u0105\",\"Aopf;\":\"\\ud835\\udd38\",\"aopf;\":\"\\ud835\\udd52\",\"apacir;\":\"\\u2a6f\",\"ap;\":\"\\u2248\",\"apE;\":\"\\u2a70\",\"ape;\":\"\\u224a\",\"apid;\":\"\\u224b\",\"apos;\":\"'\",\"ApplyFunction;\":\"\\u2061\",\"approx;\":\"\\u2248\",\"approxeq;\":\"\\u224a\",\"Aring;\":\"\\u00c5\",Aring:\"\\u00c5\",\"aring;\":\"\\u00e5\",aring:\"\\u00e5\",\"Ascr;\":\"\\ud835\\udc9c\",\"ascr;\":\"\\ud835\\udcb6\",\"Assign;\":\"\\u2254\",\"ast;\":\"*\",\"asymp;\":\"\\u2248\",\"asympeq;\":\"\\u224d\",\"Atilde;\":\"\\u00c3\",Atilde:\"\\u00c3\",\"atilde;\":\"\\u00e3\",atilde:\"\\u00e3\",\"Auml;\":\"\\u00c4\",Auml:\"\\u00c4\",\"auml;\":\"\\u00e4\",auml:\"\\u00e4\",\"awconint;\":\"\\u2233\",\"awint;\":\"\\u2a11\",\"backcong;\":\"\\u224c\",\"backepsilon;\":\"\\u03f6\",\"backprime;\":\"\\u2035\",\"backsim;\":\"\\u223d\",\"backsimeq;\":\"\\u22cd\",\"Backslash;\":\"\\u2216\",\"Barv;\":\"\\u2ae7\",\"barvee;\":\"\\u22bd\",\"barwed;\":\"\\u2305\",\"Barwed;\":\"\\u2306\",\"barwedge;\":\"\\u2305\",\"bbrk;\":\"\\u23b5\",\"bbrktbrk;\":\"\\u23b6\",\"bcong;\":\"\\u224c\",\"Bcy;\":\"\\u0411\",\"bcy;\":\"\\u0431\",\"bdquo;\":\"\\u201e\",\"becaus;\":\"\\u2235\",\"because;\":\"\\u2235\",\"Because;\":\"\\u2235\",\"bemptyv;\":\"\\u29b0\",\"bepsi;\":\"\\u03f6\",\"bernou;\":\"\\u212c\",\"Bernoullis;\":\"\\u212c\",\"Beta;\":\"\\u0392\",\"beta;\":\"\\u03b2\",\"beth;\":\"\\u2136\",\"between;\":\"\\u226c\",\"Bfr;\":\"\\ud835\\udd05\",\"bfr;\":\"\\ud835\\udd1f\",\"bigcap;\":\"\\u22c2\",\"bigcirc;\":\"\\u25ef\",\"bigcup;\":\"\\u22c3\",\"bigodot;\":\"\\u2a00\",\"bigoplus;\":\"\\u2a01\",\"bigotimes;\":\"\\u2a02\",\"bigsqcup;\":\"\\u2a06\",\"bigstar;\":\"\\u2605\",\"bigtriangledown;\":\"\\u25bd\",\"bigtriangleup;\":\"\\u25b3\",\"biguplus;\":\"\\u2a04\",\"bigvee;\":\"\\u22c1\",\"bigwedge;\":\"\\u22c0\",\"bkarow;\":\"\\u290d\",\"blacklozenge;\":\"\\u29eb\",\"blacksquare;\":\"\\u25aa\",\"blacktriangle;\":\"\\u25b4\",\"blacktriangledown;\":\"\\u25be\",\"blacktriangleleft;\":\"\\u25c2\",\"blacktriangleright;\":\"\\u25b8\",\"blank;\":\"\\u2423\",\"blk12;\":\"\\u2592\",\"blk14;\":\"\\u2591\",\"blk34;\":\"\\u2593\",\"block;\":\"\\u2588\",\"bne;\":\"=\\u20e5\",\"bnequiv;\":\"\\u2261\\u20e5\",\"bNot;\":\"\\u2aed\",\"bnot;\":\"\\u2310\",\"Bopf;\":\"\\ud835\\udd39\",\"bopf;\":\"\\ud835\\udd53\",\"bot;\":\"\\u22a5\",\"bottom;\":\"\\u22a5\",\"bowtie;\":\"\\u22c8\",\"boxbox;\":\"\\u29c9\",\"boxdl;\":\"\\u2510\",\"boxdL;\":\"\\u2555\",\"boxDl;\":\"\\u2556\",\"boxDL;\":\"\\u2557\",\"boxdr;\":\"\\u250c\",\"boxdR;\":\"\\u2552\",\"boxDr;\":\"\\u2553\",\"boxDR;\":\"\\u2554\",\"boxh;\":\"\\u2500\",\"boxH;\":\"\\u2550\",\"boxhd;\":\"\\u252c\",\"boxHd;\":\"\\u2564\",\"boxhD;\":\"\\u2565\",\"boxHD;\":\"\\u2566\",\"boxhu;\":\"\\u2534\",\"boxHu;\":\"\\u2567\",\"boxhU;\":\"\\u2568\",\"boxHU;\":\"\\u2569\",\"boxminus;\":\"\\u229f\",\"boxplus;\":\"\\u229e\",\"boxtimes;\":\"\\u22a0\",\"boxul;\":\"\\u2518\",\"boxuL;\":\"\\u255b\",\"boxUl;\":\"\\u255c\",\"boxUL;\":\"\\u255d\",\"boxur;\":\"\\u2514\",\"boxuR;\":\"\\u2558\",\"boxUr;\":\"\\u2559\",\"boxUR;\":\"\\u255a\",\"boxv;\":\"\\u2502\",\"boxV;\":\"\\u2551\",\"boxvh;\":\"\\u253c\",\"boxvH;\":\"\\u256a\",\"boxVh;\":\"\\u256b\",\"boxVH;\":\"\\u256c\",\"boxvl;\":\"\\u2524\",\"boxvL;\":\"\\u2561\",\"boxVl;\":\"\\u2562\",\"boxVL;\":\"\\u2563\",\"boxvr;\":\"\\u251c\",\"boxvR;\":\"\\u255e\",\"boxVr;\":\"\\u255f\",\"boxVR;\":\"\\u2560\",\"bprime;\":\"\\u2035\",\"breve;\":\"\\u02d8\",\"Breve;\":\"\\u02d8\",\"brvbar;\":\"\\u00a6\",brvbar:\"\\u00a6\",\"bscr;\":\"\\ud835\\udcb7\",\"Bscr;\":\"\\u212c\",\"bsemi;\":\"\\u204f\",\"bsim;\":\"\\u223d\",\"bsime;\":\"\\u22cd\",\"bsolb;\":\"\\u29c5\",\"bsol;\":\"\\\\\",\"bsolhsub;\":\"\\u27c8\",\"bull;\":\"\\u2022\",\"bullet;\":\"\\u2022\",\"bump;\":\"\\u224e\",\"bumpE;\":\"\\u2aae\",\"bumpe;\":\"\\u224f\",\"Bumpeq;\":\"\\u224e\",\"bumpeq;\":\"\\u224f\",\"Cacute;\":\"\\u0106\",\"cacute;\":\"\\u0107\",\"capand;\":\"\\u2a44\",\"capbrcup;\":\"\\u2a49\",\"capcap;\":\"\\u2a4b\",\"cap;\":\"\\u2229\",\"Cap;\":\"\\u22d2\",\"capcup;\":\"\\u2a47\",\"capdot;\":\"\\u2a40\",\"CapitalDifferentialD;\":\"\\u2145\",\"caps;\":\"\\u2229\\ufe00\",\"caret;\":\"\\u2041\",\"caron;\":\"\\u02c7\",\"Cayleys;\":\"\\u212d\",\"ccaps;\":\"\\u2a4d\",\"Ccaron;\":\"\\u010c\",\"ccaron;\":\"\\u010d\",\"Ccedil;\":\"\\u00c7\",Ccedil:\"\\u00c7\",\"ccedil;\":\"\\u00e7\",ccedil:\"\\u00e7\",\"Ccirc;\":\"\\u0108\",\"ccirc;\":\"\\u0109\",\"Cconint;\":\"\\u2230\",\"ccups;\":\"\\u2a4c\",\"ccupssm;\":\"\\u2a50\",\"Cdot;\":\"\\u010a\",\"cdot;\":\"\\u010b\",\"cedil;\":\"\\u00b8\",cedil:\"\\u00b8\",\"Cedilla;\":\"\\u00b8\",\"cemptyv;\":\"\\u29b2\",\"cent;\":\"\\u00a2\",cent:\"\\u00a2\",\"centerdot;\":\"\\u00b7\",\"CenterDot;\":\"\\u00b7\",\"cfr;\":\"\\ud835\\udd20\",\"Cfr;\":\"\\u212d\",\"CHcy;\":\"\\u0427\",\"chcy;\":\"\\u0447\",\"check;\":\"\\u2713\",\"checkmark;\":\"\\u2713\",\"Chi;\":\"\\u03a7\",\"chi;\":\"\\u03c7\",\"circ;\":\"\\u02c6\",\"circeq;\":\"\\u2257\",\"circlearrowleft;\":\"\\u21ba\",\"circlearrowright;\":\"\\u21bb\",\"circledast;\":\"\\u229b\",\"circledcirc;\":\"\\u229a\",\"circleddash;\":\"\\u229d\",\"CircleDot;\":\"\\u2299\",\"circledR;\":\"\\u00ae\",\"circledS;\":\"\\u24c8\",\"CircleMinus;\":\"\\u2296\",\"CirclePlus;\":\"\\u2295\",\"CircleTimes;\":\"\\u2297\",\"cir;\":\"\\u25cb\",\"cirE;\":\"\\u29c3\",\"cire;\":\"\\u2257\",\"cirfnint;\":\"\\u2a10\",\"cirmid;\":\"\\u2aef\",\"cirscir;\":\"\\u29c2\",\"ClockwiseContourIntegral;\":\"\\u2232\",\"CloseCurlyDoubleQuote;\":\"\\u201d\",\"CloseCurlyQuote;\":\"\\u2019\",\"clubs;\":\"\\u2663\",\"clubsuit;\":\"\\u2663\",\"colon;\":\":\",\"Colon;\":\"\\u2237\",\"Colone;\":\"\\u2a74\",\"colone;\":\"\\u2254\",\"coloneq;\":\"\\u2254\",\"comma;\":\",\",\"commat;\":\"@\",\"comp;\":\"\\u2201\",\"compfn;\":\"\\u2218\",\"complement;\":\"\\u2201\",\"complexes;\":\"\\u2102\",\"cong;\":\"\\u2245\",\"congdot;\":\"\\u2a6d\",\"Congruent;\":\"\\u2261\",\"conint;\":\"\\u222e\",\"Conint;\":\"\\u222f\",\"ContourIntegral;\":\"\\u222e\",\"copf;\":\"\\ud835\\udd54\",\"Copf;\":\"\\u2102\",\"coprod;\":\"\\u2210\",\"Coproduct;\":\"\\u2210\",\"copy;\":\"\\u00a9\",copy:\"\\u00a9\",\"COPY;\":\"\\u00a9\",COPY:\"\\u00a9\",\"copysr;\":\"\\u2117\",\"CounterClockwiseContourIntegral;\":\"\\u2233\",\"crarr;\":\"\\u21b5\",\"cross;\":\"\\u2717\",\"Cross;\":\"\\u2a2f\",\"Cscr;\":\"\\ud835\\udc9e\",\"cscr;\":\"\\ud835\\udcb8\",\"csub;\":\"\\u2acf\",\"csube;\":\"\\u2ad1\",\"csup;\":\"\\u2ad0\",\"csupe;\":\"\\u2ad2\",\"ctdot;\":\"\\u22ef\",\"cudarrl;\":\"\\u2938\",\"cudarrr;\":\"\\u2935\",\"cuepr;\":\"\\u22de\",\"cuesc;\":\"\\u22df\",\"cularr;\":\"\\u21b6\",\"cularrp;\":\"\\u293d\",\"cupbrcap;\":\"\\u2a48\",\"cupcap;\":\"\\u2a46\",\"CupCap;\":\"\\u224d\",\"cup;\":\"\\u222a\",\"Cup;\":\"\\u22d3\",\"cupcup;\":\"\\u2a4a\",\"cupdot;\":\"\\u228d\",\"cupor;\":\"\\u2a45\",\"cups;\":\"\\u222a\\ufe00\",\"curarr;\":\"\\u21b7\",\"curarrm;\":\"\\u293c\",\"curlyeqprec;\":\"\\u22de\",\"curlyeqsucc;\":\"\\u22df\",\"curlyvee;\":\"\\u22ce\",\"curlywedge;\":\"\\u22cf\",\"curren;\":\"\\u00a4\",curren:\"\\u00a4\",\"curvearrowleft;\":\"\\u21b6\",\"curvearrowright;\":\"\\u21b7\",\"cuvee;\":\"\\u22ce\",\"cuwed;\":\"\\u22cf\",\"cwconint;\":\"\\u2232\",\"cwint;\":\"\\u2231\",\"cylcty;\":\"\\u232d\",\"dagger;\":\"\\u2020\",\"Dagger;\":\"\\u2021\",\"daleth;\":\"\\u2138\",\"darr;\":\"\\u2193\",\"Darr;\":\"\\u21a1\",\"dArr;\":\"\\u21d3\",\"dash;\":\"\\u2010\",\"Dashv;\":\"\\u2ae4\",\"dashv;\":\"\\u22a3\",\"dbkarow;\":\"\\u290f\",\"dblac;\":\"\\u02dd\",\"Dcaron;\":\"\\u010e\",\"dcaron;\":\"\\u010f\",\"Dcy;\":\"\\u0414\",\"dcy;\":\"\\u0434\",\"ddagger;\":\"\\u2021\",\"ddarr;\":\"\\u21ca\",\"DD;\":\"\\u2145\",\"dd;\":\"\\u2146\",\"DDotrahd;\":\"\\u2911\",\"ddotseq;\":\"\\u2a77\",\"deg;\":\"\\u00b0\",deg:\"\\u00b0\",\"Del;\":\"\\u2207\",\"Delta;\":\"\\u0394\",\"delta;\":\"\\u03b4\",\"demptyv;\":\"\\u29b1\",\"dfisht;\":\"\\u297f\",\"Dfr;\":\"\\ud835\\udd07\",\"dfr;\":\"\\ud835\\udd21\",\"dHar;\":\"\\u2965\",\"dharl;\":\"\\u21c3\",\"dharr;\":\"\\u21c2\",\"DiacriticalAcute;\":\"\\u00b4\",\"DiacriticalDot;\":\"\\u02d9\",\"DiacriticalDoubleAcute;\":\"\\u02dd\",\"DiacriticalGrave;\":\"`\",\"DiacriticalTilde;\":\"\\u02dc\",\"diam;\":\"\\u22c4\",\"diamond;\":\"\\u22c4\",\"Diamond;\":\"\\u22c4\",\"diamondsuit;\":\"\\u2666\",\"diams;\":\"\\u2666\",\"die;\":\"\\u00a8\",\"DifferentialD;\":\"\\u2146\",\"digamma;\":\"\\u03dd\",\"disin;\":\"\\u22f2\",\"div;\":\"\\u00f7\",\"divide;\":\"\\u00f7\",divide:\"\\u00f7\",\"divideontimes;\":\"\\u22c7\",\"divonx;\":\"\\u22c7\",\"DJcy;\":\"\\u0402\",\"djcy;\":\"\\u0452\",\"dlcorn;\":\"\\u231e\",\"dlcrop;\":\"\\u230d\",\"dollar;\":\"$\",\"Dopf;\":\"\\ud835\\udd3b\",\"dopf;\":\"\\ud835\\udd55\",\"Dot;\":\"\\u00a8\",\"dot;\":\"\\u02d9\",\"DotDot;\":\"\\u20dc\",\"doteq;\":\"\\u2250\",\"doteqdot;\":\"\\u2251\",\"DotEqual;\":\"\\u2250\",\"dotminus;\":\"\\u2238\",\"dotplus;\":\"\\u2214\",\"dotsquare;\":\"\\u22a1\",\"doublebarwedge;\":\"\\u2306\",\"DoubleContourIntegral;\":\"\\u222f\",\"DoubleDot;\":\"\\u00a8\",\"DoubleDownArrow;\":\"\\u21d3\",\"DoubleLeftArrow;\":\"\\u21d0\",\"DoubleLeftRightArrow;\":\"\\u21d4\",\"DoubleLeftTee;\":\"\\u2ae4\",\"DoubleLongLeftArrow;\":\"\\u27f8\",\"DoubleLongLeftRightArrow;\":\"\\u27fa\",\"DoubleLongRightArrow;\":\"\\u27f9\",\"DoubleRightArrow;\":\"\\u21d2\",\"DoubleRightTee;\":\"\\u22a8\",\"DoubleUpArrow;\":\"\\u21d1\",\"DoubleUpDownArrow;\":\"\\u21d5\",\"DoubleVerticalBar;\":\"\\u2225\",\"DownArrowBar;\":\"\\u2913\",\"downarrow;\":\"\\u2193\",\"DownArrow;\":\"\\u2193\",\"Downarrow;\":\"\\u21d3\",\"DownArrowUpArrow;\":\"\\u21f5\",\"DownBreve;\":\"\\u0311\",\"downdownarrows;\":\"\\u21ca\",\"downharpoonleft;\":\"\\u21c3\",\"downharpoonright;\":\"\\u21c2\",\"DownLeftRightVector;\":\"\\u2950\",\"DownLeftTeeVector;\":\"\\u295e\",\"DownLeftVectorBar;\":\"\\u2956\",\"DownLeftVector;\":\"\\u21bd\",\"DownRightTeeVector;\":\"\\u295f\",\"DownRightVectorBar;\":\"\\u2957\",\"DownRightVector;\":\"\\u21c1\",\"DownTeeArrow;\":\"\\u21a7\",\"DownTee;\":\"\\u22a4\",\"drbkarow;\":\"\\u2910\",\"drcorn;\":\"\\u231f\",\"drcrop;\":\"\\u230c\",\"Dscr;\":\"\\ud835\\udc9f\",\"dscr;\":\"\\ud835\\udcb9\",\"DScy;\":\"\\u0405\",\"dscy;\":\"\\u0455\",\"dsol;\":\"\\u29f6\",\"Dstrok;\":\"\\u0110\",\"dstrok;\":\"\\u0111\",\"dtdot;\":\"\\u22f1\",\"dtri;\":\"\\u25bf\",\"dtrif;\":\"\\u25be\",\"duarr;\":\"\\u21f5\",\"duhar;\":\"\\u296f\",\"dwangle;\":\"\\u29a6\",\"DZcy;\":\"\\u040f\",\"dzcy;\":\"\\u045f\",\"dzigrarr;\":\"\\u27ff\",\"Eacute;\":\"\\u00c9\",Eacute:\"\\u00c9\",\"eacute;\":\"\\u00e9\",eacute:\"\\u00e9\",\"easter;\":\"\\u2a6e\",\"Ecaron;\":\"\\u011a\",\"ecaron;\":\"\\u011b\",\"Ecirc;\":\"\\u00ca\",Ecirc:\"\\u00ca\",\"ecirc;\":\"\\u00ea\",ecirc:\"\\u00ea\",\"ecir;\":\"\\u2256\",\"ecolon;\":\"\\u2255\",\"Ecy;\":\"\\u042d\",\"ecy;\":\"\\u044d\",\"eDDot;\":\"\\u2a77\",\"Edot;\":\"\\u0116\",\"edot;\":\"\\u0117\",\"eDot;\":\"\\u2251\",\"ee;\":\"\\u2147\",\"efDot;\":\"\\u2252\",\"Efr;\":\"\\ud835\\udd08\",\"efr;\":\"\\ud835\\udd22\",\"eg;\":\"\\u2a9a\",\"Egrave;\":\"\\u00c8\",Egrave:\"\\u00c8\",\"egrave;\":\"\\u00e8\",egrave:\"\\u00e8\",\"egs;\":\"\\u2a96\",\"egsdot;\":\"\\u2a98\",\"el;\":\"\\u2a99\",\"Element;\":\"\\u2208\",\"elinters;\":\"\\u23e7\",\"ell;\":\"\\u2113\",\"els;\":\"\\u2a95\",\"elsdot;\":\"\\u2a97\",\"Emacr;\":\"\\u0112\",\"emacr;\":\"\\u0113\",\"empty;\":\"\\u2205\",\"emptyset;\":\"\\u2205\",\"EmptySmallSquare;\":\"\\u25fb\",\"emptyv;\":\"\\u2205\",\"EmptyVerySmallSquare;\":\"\\u25ab\",\"emsp13;\":\"\\u2004\",\"emsp14;\":\"\\u2005\",\"emsp;\":\"\\u2003\",\"ENG;\":\"\\u014a\",\"eng;\":\"\\u014b\",\"ensp;\":\"\\u2002\",\"Eogon;\":\"\\u0118\",\"eogon;\":\"\\u0119\",\"Eopf;\":\"\\ud835\\udd3c\",\"eopf;\":\"\\ud835\\udd56\",\"epar;\":\"\\u22d5\",\"eparsl;\":\"\\u29e3\",\"eplus;\":\"\\u2a71\",\"epsi;\":\"\\u03b5\",\"Epsilon;\":\"\\u0395\",\"epsilon;\":\"\\u03b5\",\"epsiv;\":\"\\u03f5\",\"eqcirc;\":\"\\u2256\",\"eqcolon;\":\"\\u2255\",\"eqsim;\":\"\\u2242\",\"eqslantgtr;\":\"\\u2a96\",\"eqslantless;\":\"\\u2a95\",\"Equal;\":\"\\u2a75\",\"equals;\":\"=\",\"EqualTilde;\":\"\\u2242\",\"equest;\":\"\\u225f\",\"Equilibrium;\":\"\\u21cc\",\"equiv;\":\"\\u2261\",\"equivDD;\":\"\\u2a78\",\"eqvparsl;\":\"\\u29e5\",\"erarr;\":\"\\u2971\",\"erDot;\":\"\\u2253\",\"escr;\":\"\\u212f\",\"Escr;\":\"\\u2130\",\"esdot;\":\"\\u2250\",\"Esim;\":\"\\u2a73\",\"esim;\":\"\\u2242\",\"Eta;\":\"\\u0397\",\"eta;\":\"\\u03b7\",\"ETH;\":\"\\u00d0\",ETH:\"\\u00d0\",\"eth;\":\"\\u00f0\",eth:\"\\u00f0\",\"Euml;\":\"\\u00cb\",Euml:\"\\u00cb\",\"euml;\":\"\\u00eb\",euml:\"\\u00eb\",\"euro;\":\"\\u20ac\",\"excl;\":\"!\",\"exist;\":\"\\u2203\",\"Exists;\":\"\\u2203\",\"expectation;\":\"\\u2130\",\"exponentiale;\":\"\\u2147\",\"ExponentialE;\":\"\\u2147\",\"fallingdotseq;\":\"\\u2252\",\"Fcy;\":\"\\u0424\",\"fcy;\":\"\\u0444\",\"female;\":\"\\u2640\",\"ffilig;\":\"\\ufb03\",\"fflig;\":\"\\ufb00\",\"ffllig;\":\"\\ufb04\",\"Ffr;\":\"\\ud835\\udd09\",\"ffr;\":\"\\ud835\\udd23\",\"filig;\":\"\\ufb01\",\"FilledSmallSquare;\":\"\\u25fc\",\"FilledVerySmallSquare;\":\"\\u25aa\",\"fjlig;\":\"fj\",\"flat;\":\"\\u266d\",\"fllig;\":\"\\ufb02\",\"fltns;\":\"\\u25b1\",\"fnof;\":\"\\u0192\",\"Fopf;\":\"\\ud835\\udd3d\",\"fopf;\":\"\\ud835\\udd57\",\"forall;\":\"\\u2200\",\"ForAll;\":\"\\u2200\",\"fork;\":\"\\u22d4\",\"forkv;\":\"\\u2ad9\",\"Fouriertrf;\":\"\\u2131\",\"fpartint;\":\"\\u2a0d\",\"frac12;\":\"\\u00bd\",frac12:\"\\u00bd\",\"frac13;\":\"\\u2153\",\"frac14;\":\"\\u00bc\",frac14:\"\\u00bc\",\"frac15;\":\"\\u2155\",\"frac16;\":\"\\u2159\",\"frac18;\":\"\\u215b\",\"frac23;\":\"\\u2154\",\"frac25;\":\"\\u2156\",\"frac34;\":\"\\u00be\",frac34:\"\\u00be\",\"frac35;\":\"\\u2157\",\"frac38;\":\"\\u215c\",\"frac45;\":\"\\u2158\",\"frac56;\":\"\\u215a\",\"frac58;\":\"\\u215d\",\"frac78;\":\"\\u215e\",\"frasl;\":\"\\u2044\",\"frown;\":\"\\u2322\",\"fscr;\":\"\\ud835\\udcbb\",\"Fscr;\":\"\\u2131\",\"gacute;\":\"\\u01f5\",\"Gamma;\":\"\\u0393\",\"gamma;\":\"\\u03b3\",\"Gammad;\":\"\\u03dc\",\"gammad;\":\"\\u03dd\",\"gap;\":\"\\u2a86\",\"Gbreve;\":\"\\u011e\",\"gbreve;\":\"\\u011f\",\"Gcedil;\":\"\\u0122\",\"Gcirc;\":\"\\u011c\",\"gcirc;\":\"\\u011d\",\"Gcy;\":\"\\u0413\",\"gcy;\":\"\\u0433\",\"Gdot;\":\"\\u0120\",\"gdot;\":\"\\u0121\",\"ge;\":\"\\u2265\",\"gE;\":\"\\u2267\",\"gEl;\":\"\\u2a8c\",\"gel;\":\"\\u22db\",\"geq;\":\"\\u2265\",\"geqq;\":\"\\u2267\",\"geqslant;\":\"\\u2a7e\",\"gescc;\":\"\\u2aa9\",\"ges;\":\"\\u2a7e\",\"gesdot;\":\"\\u2a80\",\"gesdoto;\":\"\\u2a82\",\"gesdotol;\":\"\\u2a84\",\"gesl;\":\"\\u22db\\ufe00\",\"gesles;\":\"\\u2a94\",\"Gfr;\":\"\\ud835\\udd0a\",\"gfr;\":\"\\ud835\\udd24\",\"gg;\":\"\\u226b\",\"Gg;\":\"\\u22d9\",\"ggg;\":\"\\u22d9\",\"gimel;\":\"\\u2137\",\"GJcy;\":\"\\u0403\",\"gjcy;\":\"\\u0453\",\"gla;\":\"\\u2aa5\",\"gl;\":\"\\u2277\",\"glE;\":\"\\u2a92\",\"glj;\":\"\\u2aa4\",\"gnap;\":\"\\u2a8a\",\"gnapprox;\":\"\\u2a8a\",\"gne;\":\"\\u2a88\",\"gnE;\":\"\\u2269\",\"gneq;\":\"\\u2a88\",\"gneqq;\":\"\\u2269\",\"gnsim;\":\"\\u22e7\",\"Gopf;\":\"\\ud835\\udd3e\",\"gopf;\":\"\\ud835\\udd58\",\"grave;\":\"`\",\"GreaterEqual;\":\"\\u2265\",\"GreaterEqualLess;\":\"\\u22db\",\"GreaterFullEqual;\":\"\\u2267\",\"GreaterGreater;\":\"\\u2aa2\",\"GreaterLess;\":\"\\u2277\",\"GreaterSlantEqual;\":\"\\u2a7e\",\"GreaterTilde;\":\"\\u2273\",\"Gscr;\":\"\\ud835\\udca2\",\"gscr;\":\"\\u210a\",\"gsim;\":\"\\u2273\",\"gsime;\":\"\\u2a8e\",\"gsiml;\":\"\\u2a90\",\"gtcc;\":\"\\u2aa7\",\"gtcir;\":\"\\u2a7a\",\"gt;\":\">\",gt:\">\",\"GT;\":\">\",GT:\">\",\"Gt;\":\"\\u226b\",\"gtdot;\":\"\\u22d7\",\"gtlPar;\":\"\\u2995\",\"gtquest;\":\"\\u2a7c\",\"gtrapprox;\":\"\\u2a86\",\"gtrarr;\":\"\\u2978\",\"gtrdot;\":\"\\u22d7\",\"gtreqless;\":\"\\u22db\",\"gtreqqless;\":\"\\u2a8c\",\"gtrless;\":\"\\u2277\",\"gtrsim;\":\"\\u2273\",\"gvertneqq;\":\"\\u2269\\ufe00\",\"gvnE;\":\"\\u2269\\ufe00\",\"Hacek;\":\"\\u02c7\",\"hairsp;\":\"\\u200a\",\"half;\":\"\\u00bd\",\"hamilt;\":\"\\u210b\",\"HARDcy;\":\"\\u042a\",\"hardcy;\":\"\\u044a\",\"harrcir;\":\"\\u2948\",\"harr;\":\"\\u2194\",\"hArr;\":\"\\u21d4\",\"harrw;\":\"\\u21ad\",\"Hat;\":\"^\",\"hbar;\":\"\\u210f\",\"Hcirc;\":\"\\u0124\",\"hcirc;\":\"\\u0125\",\"hearts;\":\"\\u2665\",\"heartsuit;\":\"\\u2665\",\"hellip;\":\"\\u2026\",\"hercon;\":\"\\u22b9\",\"hfr;\":\"\\ud835\\udd25\",\"Hfr;\":\"\\u210c\",\"HilbertSpace;\":\"\\u210b\",\"hksearow;\":\"\\u2925\",\"hkswarow;\":\"\\u2926\",\"hoarr;\":\"\\u21ff\",\"homtht;\":\"\\u223b\",\"hookleftarrow;\":\"\\u21a9\",\"hookrightarrow;\":\"\\u21aa\",\"hopf;\":\"\\ud835\\udd59\",\"Hopf;\":\"\\u210d\",\"horbar;\":\"\\u2015\",\"HorizontalLine;\":\"\\u2500\",\"hscr;\":\"\\ud835\\udcbd\",\"Hscr;\":\"\\u210b\",\"hslash;\":\"\\u210f\",\"Hstrok;\":\"\\u0126\",\"hstrok;\":\"\\u0127\",\"HumpDownHump;\":\"\\u224e\",\"HumpEqual;\":\"\\u224f\",\"hybull;\":\"\\u2043\",\"hyphen;\":\"\\u2010\",\"Iacute;\":\"\\u00cd\",Iacute:\"\\u00cd\",\"iacute;\":\"\\u00ed\",iacute:\"\\u00ed\",\"ic;\":\"\\u2063\",\"Icirc;\":\"\\u00ce\",Icirc:\"\\u00ce\",\"icirc;\":\"\\u00ee\",icirc:\"\\u00ee\",\"Icy;\":\"\\u0418\",\"icy;\":\"\\u0438\",\"Idot;\":\"\\u0130\",\"IEcy;\":\"\\u0415\",\"iecy;\":\"\\u0435\",\"iexcl;\":\"\\u00a1\",iexcl:\"\\u00a1\",\"iff;\":\"\\u21d4\",\"ifr;\":\"\\ud835\\udd26\",\"Ifr;\":\"\\u2111\",\"Igrave;\":\"\\u00cc\",Igrave:\"\\u00cc\",\"igrave;\":\"\\u00ec\",igrave:\"\\u00ec\",\"ii;\":\"\\u2148\",\"iiiint;\":\"\\u2a0c\",\"iiint;\":\"\\u222d\",\"iinfin;\":\"\\u29dc\",\"iiota;\":\"\\u2129\",\"IJlig;\":\"\\u0132\",\"ijlig;\":\"\\u0133\",\"Imacr;\":\"\\u012a\",\"imacr;\":\"\\u012b\",\"image;\":\"\\u2111\",\"ImaginaryI;\":\"\\u2148\",\"imagline;\":\"\\u2110\",\"imagpart;\":\"\\u2111\",\"imath;\":\"\\u0131\",\"Im;\":\"\\u2111\",\"imof;\":\"\\u22b7\",\"imped;\":\"\\u01b5\",\"Implies;\":\"\\u21d2\",\"incare;\":\"\\u2105\",\"in;\":\"\\u2208\",\"infin;\":\"\\u221e\",\"infintie;\":\"\\u29dd\",\"inodot;\":\"\\u0131\",\"intcal;\":\"\\u22ba\",\"int;\":\"\\u222b\",\"Int;\":\"\\u222c\",\"integers;\":\"\\u2124\",\"Integral;\":\"\\u222b\",\"intercal;\":\"\\u22ba\",\"Intersection;\":\"\\u22c2\",\"intlarhk;\":\"\\u2a17\",\"intprod;\":\"\\u2a3c\",\"InvisibleComma;\":\"\\u2063\",\"InvisibleTimes;\":\"\\u2062\",\"IOcy;\":\"\\u0401\",\"iocy;\":\"\\u0451\",\"Iogon;\":\"\\u012e\",\"iogon;\":\"\\u012f\",\"Iopf;\":\"\\ud835\\udd40\",\"iopf;\":\"\\ud835\\udd5a\",\"Iota;\":\"\\u0399\",\"iota;\":\"\\u03b9\",\"iprod;\":\"\\u2a3c\",\"iquest;\":\"\\u00bf\",iquest:\"\\u00bf\",\"iscr;\":\"\\ud835\\udcbe\",\"Iscr;\":\"\\u2110\",\"isin;\":\"\\u2208\",\"isindot;\":\"\\u22f5\",\"isinE;\":\"\\u22f9\",\"isins;\":\"\\u22f4\",\"isinsv;\":\"\\u22f3\",\"isinv;\":\"\\u2208\",\"it;\":\"\\u2062\",\"Itilde;\":\"\\u0128\",\"itilde;\":\"\\u0129\",\"Iukcy;\":\"\\u0406\",\"iukcy;\":\"\\u0456\",\"Iuml;\":\"\\u00cf\",Iuml:\"\\u00cf\",\"iuml;\":\"\\u00ef\",iuml:\"\\u00ef\",\"Jcirc;\":\"\\u0134\",\"jcirc;\":\"\\u0135\",\"Jcy;\":\"\\u0419\",\"jcy;\":\"\\u0439\",\"Jfr;\":\"\\ud835\\udd0d\",\"jfr;\":\"\\ud835\\udd27\",\"jmath;\":\"\\u0237\",\"Jopf;\":\"\\ud835\\udd41\",\"jopf;\":\"\\ud835\\udd5b\",\"Jscr;\":\"\\ud835\\udca5\",\"jscr;\":\"\\ud835\\udcbf\",\"Jsercy;\":\"\\u0408\",\"jsercy;\":\"\\u0458\",\"Jukcy;\":\"\\u0404\",\"jukcy;\":\"\\u0454\",\"Kappa;\":\"\\u039a\",\"kappa;\":\"\\u03ba\",\"kappav;\":\"\\u03f0\",\"Kcedil;\":\"\\u0136\",\"kcedil;\":\"\\u0137\",\"Kcy;\":\"\\u041a\",\"kcy;\":\"\\u043a\",\"Kfr;\":\"\\ud835\\udd0e\",\"kfr;\":\"\\ud835\\udd28\",\"kgreen;\":\"\\u0138\",\"KHcy;\":\"\\u0425\",\"khcy;\":\"\\u0445\",\"KJcy;\":\"\\u040c\",\"kjcy;\":\"\\u045c\",\"Kopf;\":\"\\ud835\\udd42\",\"kopf;\":\"\\ud835\\udd5c\",\"Kscr;\":\"\\ud835\\udca6\",\"kscr;\":\"\\ud835\\udcc0\",\"lAarr;\":\"\\u21da\",\"Lacute;\":\"\\u0139\",\"lacute;\":\"\\u013a\",\"laemptyv;\":\"\\u29b4\",\"lagran;\":\"\\u2112\",\"Lambda;\":\"\\u039b\",\"lambda;\":\"\\u03bb\",\"lang;\":\"\\u27e8\",\"Lang;\":\"\\u27ea\",\"langd;\":\"\\u2991\",\"langle;\":\"\\u27e8\",\"lap;\":\"\\u2a85\",\"Laplacetrf;\":\"\\u2112\",\"laquo;\":\"\\u00ab\",laquo:\"\\u00ab\",\"larrb;\":\"\\u21e4\",\"larrbfs;\":\"\\u291f\",\"larr;\":\"\\u2190\",\"Larr;\":\"\\u219e\",\"lArr;\":\"\\u21d0\",\"larrfs;\":\"\\u291d\",\"larrhk;\":\"\\u21a9\",\"larrlp;\":\"\\u21ab\",\"larrpl;\":\"\\u2939\",\"larrsim;\":\"\\u2973\",\"larrtl;\":\"\\u21a2\",\"latail;\":\"\\u2919\",\"lAtail;\":\"\\u291b\",\"lat;\":\"\\u2aab\",\"late;\":\"\\u2aad\",\"lates;\":\"\\u2aad\\ufe00\",\"lbarr;\":\"\\u290c\",\"lBarr;\":\"\\u290e\",\"lbbrk;\":\"\\u2772\",\"lbrace;\":\"{\",\"lbrack;\":\"[\",\"lbrke;\":\"\\u298b\",\"lbrksld;\":\"\\u298f\",\"lbrkslu;\":\"\\u298d\",\"Lcaron;\":\"\\u013d\",\"lcaron;\":\"\\u013e\",\"Lcedil;\":\"\\u013b\",\"lcedil;\":\"\\u013c\",\"lceil;\":\"\\u2308\",\"lcub;\":\"{\",\"Lcy;\":\"\\u041b\",\"lcy;\":\"\\u043b\",\"ldca;\":\"\\u2936\",\"ldquo;\":\"\\u201c\",\"ldquor;\":\"\\u201e\",\"ldrdhar;\":\"\\u2967\",\"ldrushar;\":\"\\u294b\",\"ldsh;\":\"\\u21b2\",\"le;\":\"\\u2264\",\"lE;\":\"\\u2266\",\"LeftAngleBracket;\":\"\\u27e8\",\"LeftArrowBar;\":\"\\u21e4\",\"leftarrow;\":\"\\u2190\",\"LeftArrow;\":\"\\u2190\",\"Leftarrow;\":\"\\u21d0\",\"LeftArrowRightArrow;\":\"\\u21c6\",\"leftarrowtail;\":\"\\u21a2\",\"LeftCeiling;\":\"\\u2308\",\"LeftDoubleBracket;\":\"\\u27e6\",\"LeftDownTeeVector;\":\"\\u2961\",\"LeftDownVectorBar;\":\"\\u2959\",\"LeftDownVector;\":\"\\u21c3\",\"LeftFloor;\":\"\\u230a\",\"leftharpoondown;\":\"\\u21bd\",\"leftharpoonup;\":\"\\u21bc\",\"leftleftarrows;\":\"\\u21c7\",\"leftrightarrow;\":\"\\u2194\",\"LeftRightArrow;\":\"\\u2194\",\"Leftrightarrow;\":\"\\u21d4\",\"leftrightarrows;\":\"\\u21c6\",\"leftrightharpoons;\":\"\\u21cb\",\"leftrightsquigarrow;\":\"\\u21ad\",\"LeftRightVector;\":\"\\u294e\",\"LeftTeeArrow;\":\"\\u21a4\",\"LeftTee;\":\"\\u22a3\",\"LeftTeeVector;\":\"\\u295a\",\"leftthreetimes;\":\"\\u22cb\",\"LeftTriangleBar;\":\"\\u29cf\",\"LeftTriangle;\":\"\\u22b2\",\"LeftTriangleEqual;\":\"\\u22b4\",\"LeftUpDownVector;\":\"\\u2951\",\"LeftUpTeeVector;\":\"\\u2960\",\"LeftUpVectorBar;\":\"\\u2958\",\"LeftUpVector;\":\"\\u21bf\",\"LeftVectorBar;\":\"\\u2952\",\"LeftVector;\":\"\\u21bc\",\"lEg;\":\"\\u2a8b\",\"leg;\":\"\\u22da\",\"leq;\":\"\\u2264\",\"leqq;\":\"\\u2266\",\"leqslant;\":\"\\u2a7d\",\"lescc;\":\"\\u2aa8\",\"les;\":\"\\u2a7d\",\"lesdot;\":\"\\u2a7f\",\"lesdoto;\":\"\\u2a81\",\"lesdotor;\":\"\\u2a83\",\"lesg;\":\"\\u22da\\ufe00\",\"lesges;\":\"\\u2a93\",\"lessapprox;\":\"\\u2a85\",\"lessdot;\":\"\\u22d6\",\"lesseqgtr;\":\"\\u22da\",\"lesseqqgtr;\":\"\\u2a8b\",\"LessEqualGreater;\":\"\\u22da\",\"LessFullEqual;\":\"\\u2266\",\"LessGreater;\":\"\\u2276\",\"lessgtr;\":\"\\u2276\",\"LessLess;\":\"\\u2aa1\",\"lesssim;\":\"\\u2272\",\"LessSlantEqual;\":\"\\u2a7d\",\"LessTilde;\":\"\\u2272\",\"lfisht;\":\"\\u297c\",\"lfloor;\":\"\\u230a\",\"Lfr;\":\"\\ud835\\udd0f\",\"lfr;\":\"\\ud835\\udd29\",\"lg;\":\"\\u2276\",\"lgE;\":\"\\u2a91\",\"lHar;\":\"\\u2962\",\"lhard;\":\"\\u21bd\",\"lharu;\":\"\\u21bc\",\"lharul;\":\"\\u296a\",\"lhblk;\":\"\\u2584\",\"LJcy;\":\"\\u0409\",\"ljcy;\":\"\\u0459\",\"llarr;\":\"\\u21c7\",\"ll;\":\"\\u226a\",\"Ll;\":\"\\u22d8\",\"llcorner;\":\"\\u231e\",\"Lleftarrow;\":\"\\u21da\",\"llhard;\":\"\\u296b\",\"lltri;\":\"\\u25fa\",\"Lmidot;\":\"\\u013f\",\"lmidot;\":\"\\u0140\",\"lmoustache;\":\"\\u23b0\",\"lmoust;\":\"\\u23b0\",\"lnap;\":\"\\u2a89\",\"lnapprox;\":\"\\u2a89\",\"lne;\":\"\\u2a87\",\"lnE;\":\"\\u2268\",\"lneq;\":\"\\u2a87\",\"lneqq;\":\"\\u2268\",\"lnsim;\":\"\\u22e6\",\"loang;\":\"\\u27ec\",\"loarr;\":\"\\u21fd\",\"lobrk;\":\"\\u27e6\",\"longleftarrow;\":\"\\u27f5\",\"LongLeftArrow;\":\"\\u27f5\",\"Longleftarrow;\":\"\\u27f8\",\"longleftrightarrow;\":\"\\u27f7\",\"LongLeftRightArrow;\":\"\\u27f7\",\"Longleftrightarrow;\":\"\\u27fa\",\"longmapsto;\":\"\\u27fc\",\"longrightarrow;\":\"\\u27f6\",\"LongRightArrow;\":\"\\u27f6\",\"Longrightarrow;\":\"\\u27f9\",\"looparrowleft;\":\"\\u21ab\",\"looparrowright;\":\"\\u21ac\",\"lopar;\":\"\\u2985\",\"Lopf;\":\"\\ud835\\udd43\",\"lopf;\":\"\\ud835\\udd5d\",\"loplus;\":\"\\u2a2d\",\"lotimes;\":\"\\u2a34\",\"lowast;\":\"\\u2217\",\"lowbar;\":\"_\",\"LowerLeftArrow;\":\"\\u2199\",\"LowerRightArrow;\":\"\\u2198\",\"loz;\":\"\\u25ca\",\"lozenge;\":\"\\u25ca\",\"lozf;\":\"\\u29eb\",\"lpar;\":\"(\",\"lparlt;\":\"\\u2993\",\"lrarr;\":\"\\u21c6\",\"lrcorner;\":\"\\u231f\",\"lrhar;\":\"\\u21cb\",\"lrhard;\":\"\\u296d\",\"lrm;\":\"\\u200e\",\"lrtri;\":\"\\u22bf\",\"lsaquo;\":\"\\u2039\",\"lscr;\":\"\\ud835\\udcc1\",\"Lscr;\":\"\\u2112\",\"lsh;\":\"\\u21b0\",\"Lsh;\":\"\\u21b0\",\"lsim;\":\"\\u2272\",\"lsime;\":\"\\u2a8d\",\"lsimg;\":\"\\u2a8f\",\"lsqb;\":\"[\",\"lsquo;\":\"\\u2018\",\"lsquor;\":\"\\u201a\",\"Lstrok;\":\"\\u0141\",\"lstrok;\":\"\\u0142\",\"ltcc;\":\"\\u2aa6\",\"ltcir;\":\"\\u2a79\",\"lt;\":\"<\",lt:\"<\",\"LT;\":\"<\",LT:\"<\",\"Lt;\":\"\\u226a\",\"ltdot;\":\"\\u22d6\",\"lthree;\":\"\\u22cb\",\"ltimes;\":\"\\u22c9\",\"ltlarr;\":\"\\u2976\",\"ltquest;\":\"\\u2a7b\",\"ltri;\":\"\\u25c3\",\"ltrie;\":\"\\u22b4\",\"ltrif;\":\"\\u25c2\",\"ltrPar;\":\"\\u2996\",\"lurdshar;\":\"\\u294a\",\"luruhar;\":\"\\u2966\",\"lvertneqq;\":\"\\u2268\\ufe00\",\"lvnE;\":\"\\u2268\\ufe00\",\"macr;\":\"\\u00af\",macr:\"\\u00af\",\"male;\":\"\\u2642\",\"malt;\":\"\\u2720\",\"maltese;\":\"\\u2720\",\"Map;\":\"\\u2905\",\"map;\":\"\\u21a6\",\"mapsto;\":\"\\u21a6\",\"mapstodown;\":\"\\u21a7\",\"mapstoleft;\":\"\\u21a4\",\"mapstoup;\":\"\\u21a5\",\"marker;\":\"\\u25ae\",\"mcomma;\":\"\\u2a29\",\"Mcy;\":\"\\u041c\",\"mcy;\":\"\\u043c\",\"mdash;\":\"\\u2014\",\"mDDot;\":\"\\u223a\",\"measuredangle;\":\"\\u2221\",\"MediumSpace;\":\"\\u205f\",\"Mellintrf;\":\"\\u2133\",\"Mfr;\":\"\\ud835\\udd10\",\"mfr;\":\"\\ud835\\udd2a\",\"mho;\":\"\\u2127\",\"micro;\":\"\\u00b5\",micro:\"\\u00b5\",\"midast;\":\"*\",\"midcir;\":\"\\u2af0\",\"mid;\":\"\\u2223\",\"middot;\":\"\\u00b7\",middot:\"\\u00b7\",\"minusb;\":\"\\u229f\",\"minus;\":\"\\u2212\",\"minusd;\":\"\\u2238\",\"minusdu;\":\"\\u2a2a\",\"MinusPlus;\":\"\\u2213\",\"mlcp;\":\"\\u2adb\",\"mldr;\":\"\\u2026\",\"mnplus;\":\"\\u2213\",\"models;\":\"\\u22a7\",\"Mopf;\":\"\\ud835\\udd44\",\"mopf;\":\"\\ud835\\udd5e\",\"mp;\":\"\\u2213\",\"mscr;\":\"\\ud835\\udcc2\",\"Mscr;\":\"\\u2133\",\"mstpos;\":\"\\u223e\",\"Mu;\":\"\\u039c\",\"mu;\":\"\\u03bc\",\"multimap;\":\"\\u22b8\",\"mumap;\":\"\\u22b8\",\"nabla;\":\"\\u2207\",\"Nacute;\":\"\\u0143\",\"nacute;\":\"\\u0144\",\"nang;\":\"\\u2220\\u20d2\",\"nap;\":\"\\u2249\",\"napE;\":\"\\u2a70\\u0338\",\"napid;\":\"\\u224b\\u0338\",\"napos;\":\"\\u0149\",\"napprox;\":\"\\u2249\",\"natural;\":\"\\u266e\",\"naturals;\":\"\\u2115\",\"natur;\":\"\\u266e\",\"nbsp;\":\"\\u00a0\",nbsp:\"\\u00a0\",\"nbump;\":\"\\u224e\\u0338\",\"nbumpe;\":\"\\u224f\\u0338\",\"ncap;\":\"\\u2a43\",\"Ncaron;\":\"\\u0147\",\"ncaron;\":\"\\u0148\",\"Ncedil;\":\"\\u0145\",\"ncedil;\":\"\\u0146\",\"ncong;\":\"\\u2247\",\"ncongdot;\":\"\\u2a6d\\u0338\",\"ncup;\":\"\\u2a42\",\"Ncy;\":\"\\u041d\",\"ncy;\":\"\\u043d\",\"ndash;\":\"\\u2013\",\"nearhk;\":\"\\u2924\",\"nearr;\":\"\\u2197\",\"neArr;\":\"\\u21d7\",\"nearrow;\":\"\\u2197\",\"ne;\":\"\\u2260\",\"nedot;\":\"\\u2250\\u0338\",\"NegativeMediumSpace;\":\"\\u200b\",\"NegativeThickSpace;\":\"\\u200b\",\"NegativeThinSpace;\":\"\\u200b\",\"NegativeVeryThinSpace;\":\"\\u200b\",\"nequiv;\":\"\\u2262\",\"nesear;\":\"\\u2928\",\"nesim;\":\"\\u2242\\u0338\",\"NestedGreaterGreater;\":\"\\u226b\",\"NestedLessLess;\":\"\\u226a\",\"NewLine;\":\"\\n\",\"nexist;\":\"\\u2204\",\"nexists;\":\"\\u2204\",\"Nfr;\":\"\\ud835\\udd11\",\"nfr;\":\"\\ud835\\udd2b\",\"ngE;\":\"\\u2267\\u0338\",\"nge;\":\"\\u2271\",\"ngeq;\":\"\\u2271\",\"ngeqq;\":\"\\u2267\\u0338\",\"ngeqslant;\":\"\\u2a7e\\u0338\",\"nges;\":\"\\u2a7e\\u0338\",\"nGg;\":\"\\u22d9\\u0338\",\"ngsim;\":\"\\u2275\",\"nGt;\":\"\\u226b\\u20d2\",\"ngt;\":\"\\u226f\",\"ngtr;\":\"\\u226f\",\"nGtv;\":\"\\u226b\\u0338\",\"nharr;\":\"\\u21ae\",\"nhArr;\":\"\\u21ce\",\"nhpar;\":\"\\u2af2\",\"ni;\":\"\\u220b\",\"nis;\":\"\\u22fc\",\"nisd;\":\"\\u22fa\",\"niv;\":\"\\u220b\",\"NJcy;\":\"\\u040a\",\"njcy;\":\"\\u045a\",\"nlarr;\":\"\\u219a\",\"nlArr;\":\"\\u21cd\",\"nldr;\":\"\\u2025\",\"nlE;\":\"\\u2266\\u0338\",\"nle;\":\"\\u2270\",\"nleftarrow;\":\"\\u219a\",\"nLeftarrow;\":\"\\u21cd\",\"nleftrightarrow;\":\"\\u21ae\",\"nLeftrightarrow;\":\"\\u21ce\",\"nleq;\":\"\\u2270\",\"nleqq;\":\"\\u2266\\u0338\",\"nleqslant;\":\"\\u2a7d\\u0338\",\"nles;\":\"\\u2a7d\\u0338\",\"nless;\":\"\\u226e\",\"nLl;\":\"\\u22d8\\u0338\",\"nlsim;\":\"\\u2274\",\"nLt;\":\"\\u226a\\u20d2\",\"nlt;\":\"\\u226e\",\"nltri;\":\"\\u22ea\",\"nltrie;\":\"\\u22ec\",\"nLtv;\":\"\\u226a\\u0338\",\"nmid;\":\"\\u2224\",\"NoBreak;\":\"\\u2060\",\"NonBreakingSpace;\":\"\\u00a0\",\"nopf;\":\"\\ud835\\udd5f\",\"Nopf;\":\"\\u2115\",\"Not;\":\"\\u2aec\",\"not;\":\"\\u00ac\",not:\"\\u00ac\",\"NotCongruent;\":\"\\u2262\",\"NotCupCap;\":\"\\u226d\",\"NotDoubleVerticalBar;\":\"\\u2226\",\"NotElement;\":\"\\u2209\",\"NotEqual;\":\"\\u2260\",\"NotEqualTilde;\":\"\\u2242\\u0338\",\"NotExists;\":\"\\u2204\",\"NotGreater;\":\"\\u226f\",\"NotGreaterEqual;\":\"\\u2271\",\"NotGreaterFullEqual;\":\"\\u2267\\u0338\",\"NotGreaterGreater;\":\"\\u226b\\u0338\",\"NotGreaterLess;\":\"\\u2279\",\"NotGreaterSlantEqual;\":\"\\u2a7e\\u0338\",\"NotGreaterTilde;\":\"\\u2275\",\"NotHumpDownHump;\":\"\\u224e\\u0338\",\"NotHumpEqual;\":\"\\u224f\\u0338\",\"notin;\":\"\\u2209\",\"notindot;\":\"\\u22f5\\u0338\",\"notinE;\":\"\\u22f9\\u0338\",\"notinva;\":\"\\u2209\",\"notinvb;\":\"\\u22f7\",\"notinvc;\":\"\\u22f6\",\"NotLeftTriangleBar;\":\"\\u29cf\\u0338\",\"NotLeftTriangle;\":\"\\u22ea\",\"NotLeftTriangleEqual;\":\"\\u22ec\",\"NotLess;\":\"\\u226e\",\"NotLessEqual;\":\"\\u2270\",\"NotLessGreater;\":\"\\u2278\",\"NotLessLess;\":\"\\u226a\\u0338\",\"NotLessSlantEqual;\":\"\\u2a7d\\u0338\",\"NotLessTilde;\":\"\\u2274\",\"NotNestedGreaterGreater;\":\"\\u2aa2\\u0338\",\"NotNestedLessLess;\":\"\\u2aa1\\u0338\",\"notni;\":\"\\u220c\",\"notniva;\":\"\\u220c\",\"notnivb;\":\"\\u22fe\",\"notnivc;\":\"\\u22fd\",\"NotPrecedes;\":\"\\u2280\",\"NotPrecedesEqual;\":\"\\u2aaf\\u0338\",\"NotPrecedesSlantEqual;\":\"\\u22e0\",\"NotReverseElement;\":\"\\u220c\",\"NotRightTriangleBar;\":\"\\u29d0\\u0338\",\"NotRightTriangle;\":\"\\u22eb\",\"NotRightTriangleEqual;\":\"\\u22ed\",\"NotSquareSubset;\":\"\\u228f\\u0338\",\"NotSquareSubsetEqual;\":\"\\u22e2\",\"NotSquareSuperset;\":\"\\u2290\\u0338\",\"NotSquareSupersetEqual;\":\"\\u22e3\",\"NotSubset;\":\"\\u2282\\u20d2\",\"NotSubsetEqual;\":\"\\u2288\",\"NotSucceeds;\":\"\\u2281\",\"NotSucceedsEqual;\":\"\\u2ab0\\u0338\",\"NotSucceedsSlantEqual;\":\"\\u22e1\",\"NotSucceedsTilde;\":\"\\u227f\\u0338\",\"NotSuperset;\":\"\\u2283\\u20d2\",\"NotSupersetEqual;\":\"\\u2289\",\"NotTilde;\":\"\\u2241\",\"NotTildeEqual;\":\"\\u2244\",\"NotTildeFullEqual;\":\"\\u2247\",\"NotTildeTilde;\":\"\\u2249\",\"NotVerticalBar;\":\"\\u2224\",\"nparallel;\":\"\\u2226\",\"npar;\":\"\\u2226\",\"nparsl;\":\"\\u2afd\\u20e5\",\"npart;\":\"\\u2202\\u0338\",\"npolint;\":\"\\u2a14\",\"npr;\":\"\\u2280\",\"nprcue;\":\"\\u22e0\",\"nprec;\":\"\\u2280\",\"npreceq;\":\"\\u2aaf\\u0338\",\"npre;\":\"\\u2aaf\\u0338\",\"nrarrc;\":\"\\u2933\\u0338\",\"nrarr;\":\"\\u219b\",\"nrArr;\":\"\\u21cf\",\"nrarrw;\":\"\\u219d\\u0338\",\"nrightarrow;\":\"\\u219b\",\"nRightarrow;\":\"\\u21cf\",\"nrtri;\":\"\\u22eb\",\"nrtrie;\":\"\\u22ed\",\"nsc;\":\"\\u2281\",\"nsccue;\":\"\\u22e1\",\"nsce;\":\"\\u2ab0\\u0338\",\"Nscr;\":\"\\ud835\\udca9\",\"nscr;\":\"\\ud835\\udcc3\",\"nshortmid;\":\"\\u2224\",\"nshortparallel;\":\"\\u2226\",\"nsim;\":\"\\u2241\",\"nsime;\":\"\\u2244\",\"nsimeq;\":\"\\u2244\",\"nsmid;\":\"\\u2224\",\"nspar;\":\"\\u2226\",\"nsqsube;\":\"\\u22e2\",\"nsqsupe;\":\"\\u22e3\",\"nsub;\":\"\\u2284\",\"nsubE;\":\"\\u2ac5\\u0338\",\"nsube;\":\"\\u2288\",\"nsubset;\":\"\\u2282\\u20d2\",\"nsubseteq;\":\"\\u2288\",\"nsubseteqq;\":\"\\u2ac5\\u0338\",\"nsucc;\":\"\\u2281\",\"nsucceq;\":\"\\u2ab0\\u0338\",\"nsup;\":\"\\u2285\",\"nsupE;\":\"\\u2ac6\\u0338\",\"nsupe;\":\"\\u2289\",\"nsupset;\":\"\\u2283\\u20d2\",\"nsupseteq;\":\"\\u2289\",\"nsupseteqq;\":\"\\u2ac6\\u0338\",\"ntgl;\":\"\\u2279\",\"Ntilde;\":\"\\u00d1\",Ntilde:\"\\u00d1\",\"ntilde;\":\"\\u00f1\",ntilde:\"\\u00f1\",\"ntlg;\":\"\\u2278\",\"ntriangleleft;\":\"\\u22ea\",\"ntrianglelefteq;\":\"\\u22ec\",\"ntriangleright;\":\"\\u22eb\",\"ntrianglerighteq;\":\"\\u22ed\",\"Nu;\":\"\\u039d\",\"nu;\":\"\\u03bd\",\"num;\":\"#\",\"numero;\":\"\\u2116\",\"numsp;\":\"\\u2007\",\"nvap;\":\"\\u224d\\u20d2\",\"nvdash;\":\"\\u22ac\",\"nvDash;\":\"\\u22ad\",\"nVdash;\":\"\\u22ae\",\"nVDash;\":\"\\u22af\",\"nvge;\":\"\\u2265\\u20d2\",\"nvgt;\":\">\\u20d2\",\"nvHarr;\":\"\\u2904\",\"nvinfin;\":\"\\u29de\",\"nvlArr;\":\"\\u2902\",\"nvle;\":\"\\u2264\\u20d2\",\"nvlt;\":\"<\\u20d2\",\"nvltrie;\":\"\\u22b4\\u20d2\",\"nvrArr;\":\"\\u2903\",\"nvrtrie;\":\"\\u22b5\\u20d2\",\"nvsim;\":\"\\u223c\\u20d2\",\"nwarhk;\":\"\\u2923\",\"nwarr;\":\"\\u2196\",\"nwArr;\":\"\\u21d6\",\"nwarrow;\":\"\\u2196\",\"nwnear;\":\"\\u2927\",\"Oacute;\":\"\\u00d3\",Oacute:\"\\u00d3\",\"oacute;\":\"\\u00f3\",oacute:\"\\u00f3\",\"oast;\":\"\\u229b\",\"Ocirc;\":\"\\u00d4\",Ocirc:\"\\u00d4\",\"ocirc;\":\"\\u00f4\",ocirc:\"\\u00f4\",\"ocir;\":\"\\u229a\",\"Ocy;\":\"\\u041e\",\"ocy;\":\"\\u043e\",\"odash;\":\"\\u229d\",\"Odblac;\":\"\\u0150\",\"odblac;\":\"\\u0151\",\"odiv;\":\"\\u2a38\",\"odot;\":\"\\u2299\",\"odsold;\":\"\\u29bc\",\"OElig;\":\"\\u0152\",\"oelig;\":\"\\u0153\",\"ofcir;\":\"\\u29bf\",\"Ofr;\":\"\\ud835\\udd12\",\"ofr;\":\"\\ud835\\udd2c\",\"ogon;\":\"\\u02db\",\"Ograve;\":\"\\u00d2\",Ograve:\"\\u00d2\",\"ograve;\":\"\\u00f2\",ograve:\"\\u00f2\",\"ogt;\":\"\\u29c1\",\"ohbar;\":\"\\u29b5\",\"ohm;\":\"\\u03a9\",\"oint;\":\"\\u222e\",\"olarr;\":\"\\u21ba\",\"olcir;\":\"\\u29be\",\"olcross;\":\"\\u29bb\",\"oline;\":\"\\u203e\",\"olt;\":\"\\u29c0\",\"Omacr;\":\"\\u014c\",\"omacr;\":\"\\u014d\",\"Omega;\":\"\\u03a9\",\"omega;\":\"\\u03c9\",\"Omicron;\":\"\\u039f\",\"omicron;\":\"\\u03bf\",\"omid;\":\"\\u29b6\",\"ominus;\":\"\\u2296\",\"Oopf;\":\"\\ud835\\udd46\",\"oopf;\":\"\\ud835\\udd60\",\"opar;\":\"\\u29b7\",\"OpenCurlyDoubleQuote;\":\"\\u201c\",\"OpenCurlyQuote;\":\"\\u2018\",\"operp;\":\"\\u29b9\",\"oplus;\":\"\\u2295\",\"orarr;\":\"\\u21bb\",\"Or;\":\"\\u2a54\",\"or;\":\"\\u2228\",\"ord;\":\"\\u2a5d\",\"order;\":\"\\u2134\",\"orderof;\":\"\\u2134\",\"ordf;\":\"\\u00aa\",ordf:\"\\u00aa\",\"ordm;\":\"\\u00ba\",ordm:\"\\u00ba\",\"origof;\":\"\\u22b6\",\"oror;\":\"\\u2a56\",\"orslope;\":\"\\u2a57\",\"orv;\":\"\\u2a5b\",\"oS;\":\"\\u24c8\",\"Oscr;\":\"\\ud835\\udcaa\",\"oscr;\":\"\\u2134\",\"Oslash;\":\"\\u00d8\",Oslash:\"\\u00d8\",\"oslash;\":\"\\u00f8\",oslash:\"\\u00f8\",\"osol;\":\"\\u2298\",\"Otilde;\":\"\\u00d5\",Otilde:\"\\u00d5\",\"otilde;\":\"\\u00f5\",otilde:\"\\u00f5\",\"otimesas;\":\"\\u2a36\",\"Otimes;\":\"\\u2a37\",\"otimes;\":\"\\u2297\",\"Ouml;\":\"\\u00d6\",Ouml:\"\\u00d6\",\"ouml;\":\"\\u00f6\",ouml:\"\\u00f6\",\"ovbar;\":\"\\u233d\",\"OverBar;\":\"\\u203e\",\"OverBrace;\":\"\\u23de\",\"OverBracket;\":\"\\u23b4\",\"OverParenthesis;\":\"\\u23dc\",\"para;\":\"\\u00b6\",para:\"\\u00b6\",\"parallel;\":\"\\u2225\",\"par;\":\"\\u2225\",\"parsim;\":\"\\u2af3\",\"parsl;\":\"\\u2afd\",\"part;\":\"\\u2202\",\"PartialD;\":\"\\u2202\",\"Pcy;\":\"\\u041f\",\"pcy;\":\"\\u043f\",\"percnt;\":\"%\",\"period;\":\".\",\"permil;\":\"\\u2030\",\"perp;\":\"\\u22a5\",\"pertenk;\":\"\\u2031\",\"Pfr;\":\"\\ud835\\udd13\",\"pfr;\":\"\\ud835\\udd2d\",\"Phi;\":\"\\u03a6\",\"phi;\":\"\\u03c6\",\"phiv;\":\"\\u03d5\",\"phmmat;\":\"\\u2133\",\"phone;\":\"\\u260e\",\"Pi;\":\"\\u03a0\",\"pi;\":\"\\u03c0\",\"pitchfork;\":\"\\u22d4\",\"piv;\":\"\\u03d6\",\"planck;\":\"\\u210f\",\"planckh;\":\"\\u210e\",\"plankv;\":\"\\u210f\",\"plusacir;\":\"\\u2a23\",\"plusb;\":\"\\u229e\",\"pluscir;\":\"\\u2a22\",\"plus;\":\"+\",\"plusdo;\":\"\\u2214\",\"plusdu;\":\"\\u2a25\",\"pluse;\":\"\\u2a72\",\"PlusMinus;\":\"\\u00b1\",\"plusmn;\":\"\\u00b1\",plusmn:\"\\u00b1\",\"plussim;\":\"\\u2a26\",\"plustwo;\":\"\\u2a27\",\"pm;\":\"\\u00b1\",\"Poincareplane;\":\"\\u210c\",\"pointint;\":\"\\u2a15\",\"popf;\":\"\\ud835\\udd61\",\"Popf;\":\"\\u2119\",\"pound;\":\"\\u00a3\",pound:\"\\u00a3\",\"prap;\":\"\\u2ab7\",\"Pr;\":\"\\u2abb\",\"pr;\":\"\\u227a\",\"prcue;\":\"\\u227c\",\"precapprox;\":\"\\u2ab7\",\"prec;\":\"\\u227a\",\"preccurlyeq;\":\"\\u227c\",\"Precedes;\":\"\\u227a\",\"PrecedesEqual;\":\"\\u2aaf\",\"PrecedesSlantEqual;\":\"\\u227c\",\"PrecedesTilde;\":\"\\u227e\",\"preceq;\":\"\\u2aaf\",\"precnapprox;\":\"\\u2ab9\",\"precneqq;\":\"\\u2ab5\",\"precnsim;\":\"\\u22e8\",\"pre;\":\"\\u2aaf\",\"prE;\":\"\\u2ab3\",\"precsim;\":\"\\u227e\",\"prime;\":\"\\u2032\",\"Prime;\":\"\\u2033\",\"primes;\":\"\\u2119\",\"prnap;\":\"\\u2ab9\",\"prnE;\":\"\\u2ab5\",\"prnsim;\":\"\\u22e8\",\"prod;\":\"\\u220f\",\"Product;\":\"\\u220f\",\"profalar;\":\"\\u232e\",\"profline;\":\"\\u2312\",\"profsurf;\":\"\\u2313\",\"prop;\":\"\\u221d\",\"Proportional;\":\"\\u221d\",\"Proportion;\":\"\\u2237\",\"propto;\":\"\\u221d\",\"prsim;\":\"\\u227e\",\"prurel;\":\"\\u22b0\",\"Pscr;\":\"\\ud835\\udcab\",\"pscr;\":\"\\ud835\\udcc5\",\"Psi;\":\"\\u03a8\",\"psi;\":\"\\u03c8\",\"puncsp;\":\"\\u2008\",\"Qfr;\":\"\\ud835\\udd14\",\"qfr;\":\"\\ud835\\udd2e\",\"qint;\":\"\\u2a0c\",\"qopf;\":\"\\ud835\\udd62\",\"Qopf;\":\"\\u211a\",\"qprime;\":\"\\u2057\",\"Qscr;\":\"\\ud835\\udcac\",\"qscr;\":\"\\ud835\\udcc6\",\"quaternions;\":\"\\u210d\",\"quatint;\":\"\\u2a16\",\"quest;\":\"?\",\"questeq;\":\"\\u225f\",\"quot;\":'\"',quot:'\"',\"QUOT;\":'\"',QUOT:'\"',\"rAarr;\":\"\\u21db\",\"race;\":\"\\u223d\\u0331\",\"Racute;\":\"\\u0154\",\"racute;\":\"\\u0155\",\"radic;\":\"\\u221a\",\"raemptyv;\":\"\\u29b3\",\"rang;\":\"\\u27e9\",\"Rang;\":\"\\u27eb\",\"rangd;\":\"\\u2992\",\"range;\":\"\\u29a5\",\"rangle;\":\"\\u27e9\",\"raquo;\":\"\\u00bb\",raquo:\"\\u00bb\",\"rarrap;\":\"\\u2975\",\"rarrb;\":\"\\u21e5\",\"rarrbfs;\":\"\\u2920\",\"rarrc;\":\"\\u2933\",\"rarr;\":\"\\u2192\",\"Rarr;\":\"\\u21a0\",\"rArr;\":\"\\u21d2\",\"rarrfs;\":\"\\u291e\",\"rarrhk;\":\"\\u21aa\",\"rarrlp;\":\"\\u21ac\",\"rarrpl;\":\"\\u2945\",\"rarrsim;\":\"\\u2974\",\"Rarrtl;\":\"\\u2916\",\"rarrtl;\":\"\\u21a3\",\"rarrw;\":\"\\u219d\",\"ratail;\":\"\\u291a\",\"rAtail;\":\"\\u291c\",\"ratio;\":\"\\u2236\",\"rationals;\":\"\\u211a\",\"rbarr;\":\"\\u290d\",\"rBarr;\":\"\\u290f\",\"RBarr;\":\"\\u2910\",\"rbbrk;\":\"\\u2773\",\"rbrace;\":\"}\",\"rbrack;\":\"]\",\"rbrke;\":\"\\u298c\",\"rbrksld;\":\"\\u298e\",\"rbrkslu;\":\"\\u2990\",\"Rcaron;\":\"\\u0158\",\"rcaron;\":\"\\u0159\",\"Rcedil;\":\"\\u0156\",\"rcedil;\":\"\\u0157\",\"rceil;\":\"\\u2309\",\"rcub;\":\"}\",\"Rcy;\":\"\\u0420\",\"rcy;\":\"\\u0440\",\"rdca;\":\"\\u2937\",\"rdldhar;\":\"\\u2969\",\"rdquo;\":\"\\u201d\",\"rdquor;\":\"\\u201d\",\"rdsh;\":\"\\u21b3\",\"real;\":\"\\u211c\",\"realine;\":\"\\u211b\",\"realpart;\":\"\\u211c\",\"reals;\":\"\\u211d\",\"Re;\":\"\\u211c\",\"rect;\":\"\\u25ad\",\"reg;\":\"\\u00ae\",reg:\"\\u00ae\",\"REG;\":\"\\u00ae\",REG:\"\\u00ae\",\"ReverseElement;\":\"\\u220b\",\"ReverseEquilibrium;\":\"\\u21cb\",\"ReverseUpEquilibrium;\":\"\\u296f\",\"rfisht;\":\"\\u297d\",\"rfloor;\":\"\\u230b\",\"rfr;\":\"\\ud835\\udd2f\",\"Rfr;\":\"\\u211c\",\"rHar;\":\"\\u2964\",\"rhard;\":\"\\u21c1\",\"rharu;\":\"\\u21c0\",\"rharul;\":\"\\u296c\",\"Rho;\":\"\\u03a1\",\"rho;\":\"\\u03c1\",\"rhov;\":\"\\u03f1\",\"RightAngleBracket;\":\"\\u27e9\",\"RightArrowBar;\":\"\\u21e5\",\"rightarrow;\":\"\\u2192\",\"RightArrow;\":\"\\u2192\",\"Rightarrow;\":\"\\u21d2\",\"RightArrowLeftArrow;\":\"\\u21c4\",\"rightarrowtail;\":\"\\u21a3\",\"RightCeiling;\":\"\\u2309\",\"RightDoubleBracket;\":\"\\u27e7\",\"RightDownTeeVector;\":\"\\u295d\",\"RightDownVectorBar;\":\"\\u2955\",\"RightDownVector;\":\"\\u21c2\",\"RightFloor;\":\"\\u230b\",\"rightharpoondown;\":\"\\u21c1\",\"rightharpoonup;\":\"\\u21c0\",\"rightleftarrows;\":\"\\u21c4\",\"rightleftharpoons;\":\"\\u21cc\",\"rightrightarrows;\":\"\\u21c9\",\"rightsquigarrow;\":\"\\u219d\",\"RightTeeArrow;\":\"\\u21a6\",\"RightTee;\":\"\\u22a2\",\"RightTeeVector;\":\"\\u295b\",\"rightthreetimes;\":\"\\u22cc\",\"RightTriangleBar;\":\"\\u29d0\",\"RightTriangle;\":\"\\u22b3\",\"RightTriangleEqual;\":\"\\u22b5\",\"RightUpDownVector;\":\"\\u294f\",\"RightUpTeeVector;\":\"\\u295c\",\"RightUpVectorBar;\":\"\\u2954\",\"RightUpVector;\":\"\\u21be\",\"RightVectorBar;\":\"\\u2953\",\"RightVector;\":\"\\u21c0\",\"ring;\":\"\\u02da\",\"risingdotseq;\":\"\\u2253\",\"rlarr;\":\"\\u21c4\",\"rlhar;\":\"\\u21cc\",\"rlm;\":\"\\u200f\",\"rmoustache;\":\"\\u23b1\",\"rmoust;\":\"\\u23b1\",\"rnmid;\":\"\\u2aee\",\"roang;\":\"\\u27ed\",\"roarr;\":\"\\u21fe\",\"robrk;\":\"\\u27e7\",\"ropar;\":\"\\u2986\",\"ropf;\":\"\\ud835\\udd63\",\"Ropf;\":\"\\u211d\",\"roplus;\":\"\\u2a2e\",\"rotimes;\":\"\\u2a35\",\"RoundImplies;\":\"\\u2970\",\"rpar;\":\")\",\"rpargt;\":\"\\u2994\",\"rppolint;\":\"\\u2a12\",\"rrarr;\":\"\\u21c9\",\"Rrightarrow;\":\"\\u21db\",\"rsaquo;\":\"\\u203a\",\"rscr;\":\"\\ud835\\udcc7\",\"Rscr;\":\"\\u211b\",\"rsh;\":\"\\u21b1\",\"Rsh;\":\"\\u21b1\",\"rsqb;\":\"]\",\"rsquo;\":\"\\u2019\",\"rsquor;\":\"\\u2019\",\"rthree;\":\"\\u22cc\",\"rtimes;\":\"\\u22ca\",\"rtri;\":\"\\u25b9\",\"rtrie;\":\"\\u22b5\",\"rtrif;\":\"\\u25b8\",\"rtriltri;\":\"\\u29ce\",\"RuleDelayed;\":\"\\u29f4\",\"ruluhar;\":\"\\u2968\",\"rx;\":\"\\u211e\",\"Sacute;\":\"\\u015a\",\"sacute;\":\"\\u015b\",\"sbquo;\":\"\\u201a\",\"scap;\":\"\\u2ab8\",\"Scaron;\":\"\\u0160\",\"scaron;\":\"\\u0161\",\"Sc;\":\"\\u2abc\",\"sc;\":\"\\u227b\",\"sccue;\":\"\\u227d\",\"sce;\":\"\\u2ab0\",\"scE;\":\"\\u2ab4\",\"Scedil;\":\"\\u015e\",\"scedil;\":\"\\u015f\",\"Scirc;\":\"\\u015c\",\"scirc;\":\"\\u015d\",\"scnap;\":\"\\u2aba\",\"scnE;\":\"\\u2ab6\",\"scnsim;\":\"\\u22e9\",\"scpolint;\":\"\\u2a13\",\"scsim;\":\"\\u227f\",\"Scy;\":\"\\u0421\",\"scy;\":\"\\u0441\",\"sdotb;\":\"\\u22a1\",\"sdot;\":\"\\u22c5\",\"sdote;\":\"\\u2a66\",\"searhk;\":\"\\u2925\",\"searr;\":\"\\u2198\",\"seArr;\":\"\\u21d8\",\"searrow;\":\"\\u2198\",\"sect;\":\"\\u00a7\",sect:\"\\u00a7\",\"semi;\":\";\",\"seswar;\":\"\\u2929\",\"setminus;\":\"\\u2216\",\"setmn;\":\"\\u2216\",\"sext;\":\"\\u2736\",\"Sfr;\":\"\\ud835\\udd16\",\"sfr;\":\"\\ud835\\udd30\",\"sfrown;\":\"\\u2322\",\"sharp;\":\"\\u266f\",\"SHCHcy;\":\"\\u0429\",\"shchcy;\":\"\\u0449\",\"SHcy;\":\"\\u0428\",\"shcy;\":\"\\u0448\",\"ShortDownArrow;\":\"\\u2193\",\"ShortLeftArrow;\":\"\\u2190\",\"shortmid;\":\"\\u2223\",\"shortparallel;\":\"\\u2225\",\"ShortRightArrow;\":\"\\u2192\",\"ShortUpArrow;\":\"\\u2191\",\"shy;\":\"\\u00ad\",shy:\"\\u00ad\",\"Sigma;\":\"\\u03a3\",\"sigma;\":\"\\u03c3\",\"sigmaf;\":\"\\u03c2\",\"sigmav;\":\"\\u03c2\",\"sim;\":\"\\u223c\",\"simdot;\":\"\\u2a6a\",\"sime;\":\"\\u2243\",\"simeq;\":\"\\u2243\",\"simg;\":\"\\u2a9e\",\"simgE;\":\"\\u2aa0\",\"siml;\":\"\\u2a9d\",\"simlE;\":\"\\u2a9f\",\"simne;\":\"\\u2246\",\"simplus;\":\"\\u2a24\",\"simrarr;\":\"\\u2972\",\"slarr;\":\"\\u2190\",\"SmallCircle;\":\"\\u2218\",\"smallsetminus;\":\"\\u2216\",\"smashp;\":\"\\u2a33\",\"smeparsl;\":\"\\u29e4\",\"smid;\":\"\\u2223\",\"smile;\":\"\\u2323\",\"smt;\":\"\\u2aaa\",\"smte;\":\"\\u2aac\",\"smtes;\":\"\\u2aac\\ufe00\",\"SOFTcy;\":\"\\u042c\",\"softcy;\":\"\\u044c\",\"solbar;\":\"\\u233f\",\"solb;\":\"\\u29c4\",\"sol;\":\"/\",\"Sopf;\":\"\\ud835\\udd4a\",\"sopf;\":\"\\ud835\\udd64\",\"spades;\":\"\\u2660\",\"spadesuit;\":\"\\u2660\",\"spar;\":\"\\u2225\",\"sqcap;\":\"\\u2293\",\"sqcaps;\":\"\\u2293\\ufe00\",\"sqcup;\":\"\\u2294\",\"sqcups;\":\"\\u2294\\ufe00\",\"Sqrt;\":\"\\u221a\",\"sqsub;\":\"\\u228f\",\"sqsube;\":\"\\u2291\",\"sqsubset;\":\"\\u228f\",\"sqsubseteq;\":\"\\u2291\",\"sqsup;\":\"\\u2290\",\"sqsupe;\":\"\\u2292\",\"sqsupset;\":\"\\u2290\",\"sqsupseteq;\":\"\\u2292\",\"square;\":\"\\u25a1\",\"Square;\":\"\\u25a1\",\"SquareIntersection;\":\"\\u2293\",\"SquareSubset;\":\"\\u228f\",\"SquareSubsetEqual;\":\"\\u2291\",\"SquareSuperset;\":\"\\u2290\",\"SquareSupersetEqual;\":\"\\u2292\",\"SquareUnion;\":\"\\u2294\",\"squarf;\":\"\\u25aa\",\"squ;\":\"\\u25a1\",\"squf;\":\"\\u25aa\",\"srarr;\":\"\\u2192\",\"Sscr;\":\"\\ud835\\udcae\",\"sscr;\":\"\\ud835\\udcc8\",\"ssetmn;\":\"\\u2216\",\"ssmile;\":\"\\u2323\",\"sstarf;\":\"\\u22c6\",\"Star;\":\"\\u22c6\",\"star;\":\"\\u2606\",\"starf;\":\"\\u2605\",\"straightepsilon;\":\"\\u03f5\",\"straightphi;\":\"\\u03d5\",\"strns;\":\"\\u00af\",\"sub;\":\"\\u2282\",\"Sub;\":\"\\u22d0\",\"subdot;\":\"\\u2abd\",\"subE;\":\"\\u2ac5\",\"sube;\":\"\\u2286\",\"subedot;\":\"\\u2ac3\",\"submult;\":\"\\u2ac1\",\"subnE;\":\"\\u2acb\",\"subne;\":\"\\u228a\",\"subplus;\":\"\\u2abf\",\"subrarr;\":\"\\u2979\",\"subset;\":\"\\u2282\",\"Subset;\":\"\\u22d0\",\"subseteq;\":\"\\u2286\",\"subseteqq;\":\"\\u2ac5\",\"SubsetEqual;\":\"\\u2286\",\"subsetneq;\":\"\\u228a\",\"subsetneqq;\":\"\\u2acb\",\"subsim;\":\"\\u2ac7\",\"subsub;\":\"\\u2ad5\",\"subsup;\":\"\\u2ad3\",\"succapprox;\":\"\\u2ab8\",\"succ;\":\"\\u227b\",\"succcurlyeq;\":\"\\u227d\",\"Succeeds;\":\"\\u227b\",\"SucceedsEqual;\":\"\\u2ab0\",\"SucceedsSlantEqual;\":\"\\u227d\",\"SucceedsTilde;\":\"\\u227f\",\"succeq;\":\"\\u2ab0\",\"succnapprox;\":\"\\u2aba\",\"succneqq;\":\"\\u2ab6\",\"succnsim;\":\"\\u22e9\",\"succsim;\":\"\\u227f\",\"SuchThat;\":\"\\u220b\",\"sum;\":\"\\u2211\",\"Sum;\":\"\\u2211\",\"sung;\":\"\\u266a\",\"sup1;\":\"\\u00b9\",sup1:\"\\u00b9\",\"sup2;\":\"\\u00b2\",sup2:\"\\u00b2\",\"sup3;\":\"\\u00b3\",sup3:\"\\u00b3\",\"sup;\":\"\\u2283\",\"Sup;\":\"\\u22d1\",\"supdot;\":\"\\u2abe\",\"supdsub;\":\"\\u2ad8\",\"supE;\":\"\\u2ac6\",\"supe;\":\"\\u2287\",\"supedot;\":\"\\u2ac4\",\"Superset;\":\"\\u2283\",\"SupersetEqual;\":\"\\u2287\",\"suphsol;\":\"\\u27c9\",\"suphsub;\":\"\\u2ad7\",\"suplarr;\":\"\\u297b\",\"supmult;\":\"\\u2ac2\",\"supnE;\":\"\\u2acc\",\"supne;\":\"\\u228b\",\"supplus;\":\"\\u2ac0\",\"supset;\":\"\\u2283\",\"Supset;\":\"\\u22d1\",\"supseteq;\":\"\\u2287\",\"supseteqq;\":\"\\u2ac6\",\"supsetneq;\":\"\\u228b\",\"supsetneqq;\":\"\\u2acc\",\"supsim;\":\"\\u2ac8\",\"supsub;\":\"\\u2ad4\",\"supsup;\":\"\\u2ad6\",\"swarhk;\":\"\\u2926\",\"swarr;\":\"\\u2199\",\"swArr;\":\"\\u21d9\",\"swarrow;\":\"\\u2199\",\"swnwar;\":\"\\u292a\",\"szlig;\":\"\\u00df\",szlig:\"\\u00df\",\"Tab;\":\"\t\",\"target;\":\"\\u2316\",\"Tau;\":\"\\u03a4\",\"tau;\":\"\\u03c4\",\"tbrk;\":\"\\u23b4\",\"Tcaron;\":\"\\u0164\",\"tcaron;\":\"\\u0165\",\"Tcedil;\":\"\\u0162\",\"tcedil;\":\"\\u0163\",\"Tcy;\":\"\\u0422\",\"tcy;\":\"\\u0442\",\"tdot;\":\"\\u20db\",\"telrec;\":\"\\u2315\",\"Tfr;\":\"\\ud835\\udd17\",\"tfr;\":\"\\ud835\\udd31\",\"there4;\":\"\\u2234\",\"therefore;\":\"\\u2234\",\"Therefore;\":\"\\u2234\",\"Theta;\":\"\\u0398\",\"theta;\":\"\\u03b8\",\"thetasym;\":\"\\u03d1\",\"thetav;\":\"\\u03d1\",\"thickapprox;\":\"\\u2248\",\"thicksim;\":\"\\u223c\",\"ThickSpace;\":\"\\u205f\\u200a\",\"ThinSpace;\":\"\\u2009\",\"thinsp;\":\"\\u2009\",\"thkap;\":\"\\u2248\",\"thksim;\":\"\\u223c\",\"THORN;\":\"\\u00de\",THORN:\"\\u00de\",\"thorn;\":\"\\u00fe\",thorn:\"\\u00fe\",\"tilde;\":\"\\u02dc\",\"Tilde;\":\"\\u223c\",\"TildeEqual;\":\"\\u2243\",\"TildeFullEqual;\":\"\\u2245\",\"TildeTilde;\":\"\\u2248\",\"timesbar;\":\"\\u2a31\",\"timesb;\":\"\\u22a0\",\"times;\":\"\\u00d7\",times:\"\\u00d7\",\"timesd;\":\"\\u2a30\",\"tint;\":\"\\u222d\",\"toea;\":\"\\u2928\",\"topbot;\":\"\\u2336\",\"topcir;\":\"\\u2af1\",\"top;\":\"\\u22a4\",\"Topf;\":\"\\ud835\\udd4b\",\"topf;\":\"\\ud835\\udd65\",\"topfork;\":\"\\u2ada\",\"tosa;\":\"\\u2929\",\"tprime;\":\"\\u2034\",\"trade;\":\"\\u2122\",\"TRADE;\":\"\\u2122\",\"triangle;\":\"\\u25b5\",\"triangledown;\":\"\\u25bf\",\"triangleleft;\":\"\\u25c3\",\"trianglelefteq;\":\"\\u22b4\",\"triangleq;\":\"\\u225c\",\"triangleright;\":\"\\u25b9\",\"trianglerighteq;\":\"\\u22b5\",\"tridot;\":\"\\u25ec\",\"trie;\":\"\\u225c\",\"triminus;\":\"\\u2a3a\",\"TripleDot;\":\"\\u20db\",\"triplus;\":\"\\u2a39\",\"trisb;\":\"\\u29cd\",\"tritime;\":\"\\u2a3b\",\"trpezium;\":\"\\u23e2\",\"Tscr;\":\"\\ud835\\udcaf\",\"tscr;\":\"\\ud835\\udcc9\",\"TScy;\":\"\\u0426\",\"tscy;\":\"\\u0446\",\"TSHcy;\":\"\\u040b\",\"tshcy;\":\"\\u045b\",\"Tstrok;\":\"\\u0166\",\"tstrok;\":\"\\u0167\",\"twixt;\":\"\\u226c\",\"twoheadleftarrow;\":\"\\u219e\",\"twoheadrightarrow;\":\"\\u21a0\",\"Uacute;\":\"\\u00da\",Uacute:\"\\u00da\",\"uacute;\":\"\\u00fa\",uacute:\"\\u00fa\",\"uarr;\":\"\\u2191\",\"Uarr;\":\"\\u219f\",\"uArr;\":\"\\u21d1\",\"Uarrocir;\":\"\\u2949\",\"Ubrcy;\":\"\\u040e\",\"ubrcy;\":\"\\u045e\",\"Ubreve;\":\"\\u016c\",\"ubreve;\":\"\\u016d\",\"Ucirc;\":\"\\u00db\",Ucirc:\"\\u00db\",\"ucirc;\":\"\\u00fb\",ucirc:\"\\u00fb\",\"Ucy;\":\"\\u0423\",\"ucy;\":\"\\u0443\",\"udarr;\":\"\\u21c5\",\"Udblac;\":\"\\u0170\",\"udblac;\":\"\\u0171\",\"udhar;\":\"\\u296e\",\"ufisht;\":\"\\u297e\",\"Ufr;\":\"\\ud835\\udd18\",\"ufr;\":\"\\ud835\\udd32\",\"Ugrave;\":\"\\u00d9\",Ugrave:\"\\u00d9\",\"ugrave;\":\"\\u00f9\",ugrave:\"\\u00f9\",\"uHar;\":\"\\u2963\",\"uharl;\":\"\\u21bf\",\"uharr;\":\"\\u21be\",\"uhblk;\":\"\\u2580\",\"ulcorn;\":\"\\u231c\",\"ulcorner;\":\"\\u231c\",\"ulcrop;\":\"\\u230f\",\"ultri;\":\"\\u25f8\",\"Umacr;\":\"\\u016a\",\"umacr;\":\"\\u016b\",\"uml;\":\"\\u00a8\",uml:\"\\u00a8\",\"UnderBar;\":\"_\",\"UnderBrace;\":\"\\u23df\",\"UnderBracket;\":\"\\u23b5\",\"UnderParenthesis;\":\"\\u23dd\",\"Union;\":\"\\u22c3\",\"UnionPlus;\":\"\\u228e\",\"Uogon;\":\"\\u0172\",\"uogon;\":\"\\u0173\",\"Uopf;\":\"\\ud835\\udd4c\",\"uopf;\":\"\\ud835\\udd66\",\"UpArrowBar;\":\"\\u2912\",\"uparrow;\":\"\\u2191\",\"UpArrow;\":\"\\u2191\",\"Uparrow;\":\"\\u21d1\",\"UpArrowDownArrow;\":\"\\u21c5\",\"updownarrow;\":\"\\u2195\",\"UpDownArrow;\":\"\\u2195\",\"Updownarrow;\":\"\\u21d5\",\"UpEquilibrium;\":\"\\u296e\",\"upharpoonleft;\":\"\\u21bf\",\"upharpoonright;\":\"\\u21be\",\"uplus;\":\"\\u228e\",\"UpperLeftArrow;\":\"\\u2196\",\"UpperRightArrow;\":\"\\u2197\",\"upsi;\":\"\\u03c5\",\"Upsi;\":\"\\u03d2\",\"upsih;\":\"\\u03d2\",\"Upsilon;\":\"\\u03a5\",\"upsilon;\":\"\\u03c5\",\"UpTeeArrow;\":\"\\u21a5\",\"UpTee;\":\"\\u22a5\",\"upuparrows;\":\"\\u21c8\",\"urcorn;\":\"\\u231d\",\"urcorner;\":\"\\u231d\",\"urcrop;\":\"\\u230e\",\"Uring;\":\"\\u016e\",\"uring;\":\"\\u016f\",\"urtri;\":\"\\u25f9\",\"Uscr;\":\"\\ud835\\udcb0\",\"uscr;\":\"\\ud835\\udcca\",\"utdot;\":\"\\u22f0\",\"Utilde;\":\"\\u0168\",\"utilde;\":\"\\u0169\",\"utri;\":\"\\u25b5\",\"utrif;\":\"\\u25b4\",\"uuarr;\":\"\\u21c8\",\"Uuml;\":\"\\u00dc\",Uuml:\"\\u00dc\",\"uuml;\":\"\\u00fc\",uuml:\"\\u00fc\",\"uwangle;\":\"\\u29a7\",\"vangrt;\":\"\\u299c\",\"varepsilon;\":\"\\u03f5\",\"varkappa;\":\"\\u03f0\",\"varnothing;\":\"\\u2205\",\"varphi;\":\"\\u03d5\",\"varpi;\":\"\\u03d6\",\"varpropto;\":\"\\u221d\",\"varr;\":\"\\u2195\",\"vArr;\":\"\\u21d5\",\"varrho;\":\"\\u03f1\",\"varsigma;\":\"\\u03c2\",\"varsubsetneq;\":\"\\u228a\\ufe00\",\"varsubsetneqq;\":\"\\u2acb\\ufe00\",\"varsupsetneq;\":\"\\u228b\\ufe00\",\"varsupsetneqq;\":\"\\u2acc\\ufe00\",\"vartheta;\":\"\\u03d1\",\"vartriangleleft;\":\"\\u22b2\",\"vartriangleright;\":\"\\u22b3\",\"vBar;\":\"\\u2ae8\",\"Vbar;\":\"\\u2aeb\",\"vBarv;\":\"\\u2ae9\",\"Vcy;\":\"\\u0412\",\"vcy;\":\"\\u0432\",\"vdash;\":\"\\u22a2\",\"vDash;\":\"\\u22a8\",\"Vdash;\":\"\\u22a9\",\"VDash;\":\"\\u22ab\",\"Vdashl;\":\"\\u2ae6\",\"veebar;\":\"\\u22bb\",\"vee;\":\"\\u2228\",\"Vee;\":\"\\u22c1\",\"veeeq;\":\"\\u225a\",\"vellip;\":\"\\u22ee\",\"verbar;\":\"|\",\"Verbar;\":\"\\u2016\",\"vert;\":\"|\",\"Vert;\":\"\\u2016\",\"VerticalBar;\":\"\\u2223\",\"VerticalLine;\":\"|\",\"VerticalSeparator;\":\"\\u2758\",\"VerticalTilde;\":\"\\u2240\",\"VeryThinSpace;\":\"\\u200a\",\"Vfr;\":\"\\ud835\\udd19\",\"vfr;\":\"\\ud835\\udd33\",\"vltri;\":\"\\u22b2\",\"vnsub;\":\"\\u2282\\u20d2\",\"vnsup;\":\"\\u2283\\u20d2\",\"Vopf;\":\"\\ud835\\udd4d\",\"vopf;\":\"\\ud835\\udd67\",\"vprop;\":\"\\u221d\",\"vrtri;\":\"\\u22b3\",\"Vscr;\":\"\\ud835\\udcb1\",\"vscr;\":\"\\ud835\\udccb\",\"vsubnE;\":\"\\u2acb\\ufe00\",\"vsubne;\":\"\\u228a\\ufe00\",\"vsupnE;\":\"\\u2acc\\ufe00\",\"vsupne;\":\"\\u228b\\ufe00\",\"Vvdash;\":\"\\u22aa\",\"vzigzag;\":\"\\u299a\",\"Wcirc;\":\"\\u0174\",\"wcirc;\":\"\\u0175\",\"wedbar;\":\"\\u2a5f\",\"wedge;\":\"\\u2227\",\"Wedge;\":\"\\u22c0\",\"wedgeq;\":\"\\u2259\",\"weierp;\":\"\\u2118\",\"Wfr;\":\"\\ud835\\udd1a\",\"wfr;\":\"\\ud835\\udd34\",\"Wopf;\":\"\\ud835\\udd4e\",\"wopf;\":\"\\ud835\\udd68\",\"wp;\":\"\\u2118\",\"wr;\":\"\\u2240\",\"wreath;\":\"\\u2240\",\"Wscr;\":\"\\ud835\\udcb2\",\"wscr;\":\"\\ud835\\udccc\",\"xcap;\":\"\\u22c2\",\"xcirc;\":\"\\u25ef\",\"xcup;\":\"\\u22c3\",\"xdtri;\":\"\\u25bd\",\"Xfr;\":\"\\ud835\\udd1b\",\"xfr;\":\"\\ud835\\udd35\",\"xharr;\":\"\\u27f7\",\"xhArr;\":\"\\u27fa\",\"Xi;\":\"\\u039e\",\"xi;\":\"\\u03be\",\"xlarr;\":\"\\u27f5\",\"xlArr;\":\"\\u27f8\",\"xmap;\":\"\\u27fc\",\"xnis;\":\"\\u22fb\",\"xodot;\":\"\\u2a00\",\"Xopf;\":\"\\ud835\\udd4f\",\"xopf;\":\"\\ud835\\udd69\",\"xoplus;\":\"\\u2a01\",\"xotime;\":\"\\u2a02\",\"xrarr;\":\"\\u27f6\",\"xrArr;\":\"\\u27f9\",\"Xscr;\":\"\\ud835\\udcb3\",\"xscr;\":\"\\ud835\\udccd\",\"xsqcup;\":\"\\u2a06\",\"xuplus;\":\"\\u2a04\",\"xutri;\":\"\\u25b3\",\"xvee;\":\"\\u22c1\",\"xwedge;\":\"\\u22c0\",\"Yacute;\":\"\\u00dd\",Yacute:\"\\u00dd\",\"yacute;\":\"\\u00fd\",yacute:\"\\u00fd\",\"YAcy;\":\"\\u042f\",\"yacy;\":\"\\u044f\",\"Ycirc;\":\"\\u0176\",\"ycirc;\":\"\\u0177\",\"Ycy;\":\"\\u042b\",\"ycy;\":\"\\u044b\",\"yen;\":\"\\u00a5\",yen:\"\\u00a5\",\"Yfr;\":\"\\ud835\\udd1c\",\"yfr;\":\"\\ud835\\udd36\",\"YIcy;\":\"\\u0407\",\"yicy;\":\"\\u0457\",\"Yopf;\":\"\\ud835\\udd50\",\"yopf;\":\"\\ud835\\udd6a\",\"Yscr;\":\"\\ud835\\udcb4\",\"yscr;\":\"\\ud835\\udcce\",\"YUcy;\":\"\\u042e\",\"yucy;\":\"\\u044e\",\"yuml;\":\"\\u00ff\",yuml:\"\\u00ff\",\"Yuml;\":\"\\u0178\",\"Zacute;\":\"\\u0179\",\"zacute;\":\"\\u017a\",\"Zcaron;\":\"\\u017d\",\"zcaron;\":\"\\u017e\",\"Zcy;\":\"\\u0417\",\"zcy;\":\"\\u0437\",\"Zdot;\":\"\\u017b\",\"zdot;\":\"\\u017c\",\"zeetrf;\":\"\\u2128\",\"ZeroWidthSpace;\":\"\\u200b\",\"Zeta;\":\"\\u0396\",\"zeta;\":\"\\u03b6\",\"zfr;\":\"\\ud835\\udd37\",\"Zfr;\":\"\\u2128\",\"ZHcy;\":\"\\u0416\",\"zhcy;\":\"\\u0436\",\"zigrarr;\":\"\\u21dd\",\"zopf;\":\"\\ud835\\udd6b\",\"Zopf;\":\"\\u2124\",\"Zscr;\":\"\\ud835\\udcb5\",\"zscr;\":\"\\ud835\\udccf\",\"zwj;\":\"\\u200d\",\"zwnj;\":\"\\u200c\"}},{}],13:[function(e,t,n){function u(e,t){return r.isUndefined(t)?\"\"+t:r.isNumber(t)&&(isNaN(t)||!isFinite(t))?t.toString():r.isFunction(t)||r.isRegExp(t)?t.toString():t}function a(e,t){return r.isString(e)?e.length<t?e:e.slice(0,t):e}function f(e){return a(JSON.stringify(e.actual,u),128)+\" \"+e.operator+\" \"+a(JSON.stringify(e.expected,u),128)}function l(e,t,n,r,i){throw new o.AssertionError({message:n,actual:e,expected:t,operator:r,stackStartFunction:i})}function c(e,t){e||l(e,!0,t,\"==\",o.ok)}function h(e,t){if(e===t)return!0;if(r.isBuffer(e)&&r.isBuffer(t)){if(e.length!=t.length)return!1;for(var n=0;n<e.length;n++)if(e[n]!==t[n])return!1;return!0}return r.isDate(e)&&r.isDate(t)?e.getTime()===t.getTime():r.isRegExp(e)&&r.isRegExp(t)?e.source===t.source&&e.global===t.global&&e.multiline===t.multiline&&e.lastIndex===t.lastIndex&&e.ignoreCase===t.ignoreCase:!r.isObject(e)&&!r.isObject(t)?e==t:d(e,t)}function p(e){return Object.prototype.toString.call(e)==\"[object Arguments]\"}function d(e,t){if(r.isNullOrUndefined(e)||r.isNullOrUndefined(t))return!1;if(e.prototype!==t.prototype)return!1;if(p(e))return p(t)?(e=i.call(e),t=i.call(t),h(e,t)):!1;try{var n=g(e),s=g(t),o,u}catch(a){return!1}if(n.length!=s.length)return!1;n.sort(),s.sort();for(u=n.length-1;u>=0;u--)if(n[u]!=s[u])return!1;for(u=n.length-1;u>=0;u--){o=n[u];if(!h(e[o],t[o]))return!1}return!0}function v(e,t){return!e||!t?!1:Object.prototype.toString.call(t)==\"[object RegExp]\"?t.test(e):e instanceof t?!0:t.call({},e)===!0?!0:!1}function m(e,t,n,i){var s;r.isString(n)&&(i=n,n=null);try{t()}catch(o){s=o}i=(n&&n.name?\" (\"+n.name+\").\":\".\")+(i?\" \"+i:\".\"),e&&!s&&l(s,n,\"Missing expected exception\"+i),!e&&v(s,n)&&l(s,n,\"Got unwanted exception\"+i);if(e&&s&&n&&!v(s,n)||!e&&s)throw s}var r=e(\"util/\"),i=Array.prototype.slice,s=Object.prototype.hasOwnProperty,o=t.exports=c;o.AssertionError=function(t){this.name=\"AssertionError\",this.actual=t.actual,this.expected=t.expected,this.operator=t.operator,t.message?(this.message=t.message,this.generatedMessage=!1):(this.message=f(this),this.generatedMessage=!0);var n=t.stackStartFunction||l;if(Error.captureStackTrace)Error.captureStackTrace(this,n);else{var r=new Error;if(r.stack){var i=r.stack,s=n.name,o=i.indexOf(\"\\n\"+s);if(o>=0){var u=i.indexOf(\"\\n\",o+1);i=i.substring(u+1)}this.stack=i}}},r.inherits(o.AssertionError,Error),o.fail=l,o.ok=c,o.equal=function(t,n,r){t!=n&&l(t,n,r,\"==\",o.equal)},o.notEqual=function(t,n,r){t==n&&l(t,n,r,\"!=\",o.notEqual)},o.deepEqual=function(t,n,r){h(t,n)||l(t,n,r,\"deepEqual\",o.deepEqual)},o.notDeepEqual=function(t,n,r){h(t,n)&&l(t,n,r,\"notDeepEqual\",o.notDeepEqual)},o.strictEqual=function(t,n,r){t!==n&&l(t,n,r,\"===\",o.strictEqual)},o.notStrictEqual=function(t,n,r){t===n&&l(t,n,r,\"!==\",o.notStrictEqual)},o.throws=function(e,t,n){m.apply(this,[!0].concat(i.call(arguments)))},o.doesNotThrow=function(e,t){m.apply(this,[!1].concat(i.call(arguments)))},o.ifError=function(e){if(e)throw e};var g=Object.keys||function(e){var t=[];for(var n in e)s.call(e,n)&&t.push(n);return t}},{\"util/\":15}],14:[function(e,t,n){t.exports=function(t){return t&&typeof t==\"object\"&&typeof t.copy==\"function\"&&typeof t.fill==\"function\"&&typeof t.readUInt8==\"function\"}},{}],15:[function(e,t,n){(function(t,r){function u(e,t){var r={seen:[],stylize:f};return arguments.length>=3&&(r.depth=arguments[2]),arguments.length>=4&&(r.colors=arguments[3]),y(t)?r.showHidden=t:t&&n._extend(r,t),T(r.showHidden)&&(r.showHidden=!1),T(r.depth)&&(r.depth=2),T(r.colors)&&(r.colors=!1),T(r.customInspect)&&(r.customInspect=!0),r.colors&&(r.stylize=a),c(r,e,r.depth)}function a(e,t){var n=u.styles[t];return n?\"\u001b[\"+u.colors[n][0]+\"m\"+e+\"\u001b[\"+u.colors[n][1]+\"m\":e}function f(e,t){return e}function l(e){var t={};return e.forEach(function(e,n){t[e]=!0}),t}function c(e,t,r){if(e.customInspect&&t&&A(t.inspect)&&t.inspect!==n.inspect&&(!t.constructor||t.constructor.prototype!==t)){var i=t.inspect(r,e);return S(i)||(i=c(e,i,r)),i}var s=h(e,t);if(s)return s;var o=Object.keys(t),u=l(o);e.showHidden&&(o=Object.getOwnPropertyNames(t));if(L(t)&&(o.indexOf(\"message\")>=0||o.indexOf(\"description\")>=0))return p(t);if(o.length===0){if(A(t)){var a=t.name?\": \"+t.name:\"\";return e.stylize(\"[Function\"+a+\"]\",\"special\")}if(N(t))return e.stylize(RegExp.prototype.toString.call(t),\"regexp\");if(k(t))return e.stylize(Date.prototype.toString.call(t),\"date\");if(L(t))return p(t)}var f=\"\",y=!1,b=[\"{\",\"}\"];g(t)&&(y=!0,b=[\"[\",\"]\"]);if(A(t)){var w=t.name?\": \"+t.name:\"\";f=\" [Function\"+w+\"]\"}N(t)&&(f=\" \"+RegExp.prototype.toString.call(t)),k(t)&&(f=\" \"+Date.prototype.toUTCString.call(t)),L(t)&&(f=\" \"+p(t));if(o.length!==0||!!y&&t.length!=0){if(r<0)return N(t)?e.stylize(RegExp.prototype.toString.call(t),\"regexp\"):e.stylize(\"[Object]\",\"special\");e.seen.push(t);var E;return y?E=d(e,t,r,u,o):E=o.map(function(n){return v(e,t,r,u,n,y)}),e.seen.pop(),m(E,f,b)}return b[0]+f+b[1]}function h(e,t){if(T(t))return e.stylize(\"undefined\",\"undefined\");if(S(t)){var n=\"'\"+JSON.stringify(t).replace(/^\"|\"$/g,\"\").replace(/'/g,\"\\\\'\").replace(/\\\\\"/g,'\"')+\"'\";return e.stylize(n,\"string\")}if(E(t))return e.stylize(\"\"+t,\"number\");if(y(t))return e.stylize(\"\"+t,\"boolean\");if(b(t))return e.stylize(\"null\",\"null\")}function p(e){return\"[\"+Error.prototype.toString.call(e)+\"]\"}function d(e,t,n,r,i){var s=[];for(var o=0,u=t.length;o<u;++o)H(t,String(o))?s.push(v(e,t,n,r,String(o),!0)):s.push(\"\");return i.forEach(function(i){i.match(/^\\d+$/)||s.push(v(e,t,n,r,i,!0))}),s}function v(e,t,n,r,i,s){var o,u,a;a=Object.getOwnPropertyDescriptor(t,i)||{value:t[i]},a.get?a.set?u=e.stylize(\"[Getter/Setter]\",\"special\"):u=e.stylize(\"[Getter]\",\"special\"):a.set&&(u=e.stylize(\"[Setter]\",\"special\")),H(r,i)||(o=\"[\"+i+\"]\"),u||(e.seen.indexOf(a.value)<0?(b(n)?u=c(e,a.value,null):u=c(e,a.value,n-1),u.indexOf(\"\\n\")>-1&&(s?u=u.split(\"\\n\").map(function(e){return\"  \"+e}).join(\"\\n\").substr(2):u=\"\\n\"+u.split(\"\\n\").map(function(e){return\"   \"+e}).join(\"\\n\"))):u=e.stylize(\"[Circular]\",\"special\"));if(T(o)){if(s&&i.match(/^\\d+$/))return u;o=JSON.stringify(\"\"+i),o.match(/^\"([a-zA-Z_][a-zA-Z_0-9]*)\"$/)?(o=o.substr(1,o.length-2),o=e.stylize(o,\"name\")):(o=o.replace(/'/g,\"\\\\'\").replace(/\\\\\"/g,'\"').replace(/(^\"|\"$)/g,\"'\"),o=e.stylize(o,\"string\"))}return o+\": \"+u}function m(e,t,n){var r=0,i=e.reduce(function(e,t){return r++,t.indexOf(\"\\n\")>=0&&r++,e+t.replace(/\\u001b\\[\\d\\d?m/g,\"\").length+1},0);return i>60?n[0]+(t===\"\"?\"\":t+\"\\n \")+\" \"+e.join(\",\\n  \")+\" \"+n[1]:n[0]+t+\" \"+e.join(\", \")+\" \"+n[1]}function g(e){return Array.isArray(e)}function y(e){return typeof e==\"boolean\"}function b(e){return e===null}function w(e){return e==null}function E(e){return typeof e==\"number\"}function S(e){return typeof e==\"string\"}function x(e){return typeof e==\"symbol\"}function T(e){return e===void 0}function N(e){return C(e)&&M(e)===\"[object RegExp]\"}function C(e){return typeof e==\"object\"&&e!==null}function k(e){return C(e)&&M(e)===\"[object Date]\"}function L(e){return C(e)&&(M(e)===\"[object Error]\"||e instanceof Error)}function A(e){return typeof e==\"function\"}function O(e){return e===null||typeof e==\"boolean\"||typeof e==\"number\"||typeof e==\"string\"||typeof e==\"symbol\"||typeof e==\"undefined\"}function M(e){return Object.prototype.toString.call(e)}function _(e){return e<10?\"0\"+e.toString(10):e.toString(10)}function P(){var e=new Date,t=[_(e.getHours()),_(e.getMinutes()),_(e.getSeconds())].join(\":\");return[e.getDate(),D[e.getMonth()],t].join(\" \")}function H(e,t){return Object.prototype.hasOwnProperty.call(e,t)}var i=/%[sdj%]/g;n.format=function(e){if(!S(e)){var t=[];for(var n=0;n<arguments.length;n++)t.push(u(arguments[n]));return t.join(\" \")}var n=1,r=arguments,s=r.length,o=String(e).replace(i,function(e){if(e===\"%%\")return\"%\";if(n>=s)return e;switch(e){case\"%s\":return String(r[n++]);case\"%d\":return Number(r[n++]);case\"%j\":try{return JSON.stringify(r[n++])}catch(t){return\"[Circular]\"};default:return e}});for(var a=r[n];n<s;a=r[++n])b(a)||!C(a)?o+=\" \"+a:o+=\" \"+u(a);return o},n.deprecate=function(e,i){function o(){if(!s){if(t.throwDeprecation)throw new Error(i);t.traceDeprecation?console.trace(i):console.error(i),s=!0}return e.apply(this,arguments)}if(T(r.process))return function(){return n.deprecate(e,i).apply(this,arguments)};if(t.noDeprecation===!0)return e;var s=!1;return o};var s={},o;n.debuglog=function(e){T(o)&&(o=t.env.NODE_DEBUG||\"\"),e=e.toUpperCase();if(!s[e])if((new RegExp(\"\\\\b\"+e+\"\\\\b\",\"i\")).test(o)){var r=t.pid;s[e]=function(){var t=n.format.apply(n,arguments);console.error(\"%s %d: %s\",e,r,t)}}else s[e]=function(){};return s[e]},n.inspect=u,u.colors={bold:[1,22],italic:[3,23],underline:[4,24],inverse:[7,27],white:[37,39],grey:[90,39],black:[30,39],blue:[34,39],cyan:[36,39],green:[32,39],magenta:[35,39],red:[31,39],yellow:[33,39]},u.styles={special:\"cyan\",number:\"yellow\",\"boolean\":\"yellow\",\"undefined\":\"grey\",\"null\":\"bold\",string:\"green\",date:\"magenta\",regexp:\"red\"},n.isArray=g,n.isBoolean=y,n.isNull=b,n.isNullOrUndefined=w,n.isNumber=E,n.isString=S,n.isSymbol=x,n.isUndefined=T,n.isRegExp=N,n.isObject=C,n.isDate=k,n.isError=L,n.isFunction=A,n.isPrimitive=O,n.isBuffer=e(\"./support/isBuffer\");var D=[\"Jan\",\"Feb\",\"Mar\",\"Apr\",\"May\",\"Jun\",\"Jul\",\"Aug\",\"Sep\",\"Oct\",\"Nov\",\"Dec\"];n.log=function(){console.log(\"%s - %s\",P(),n.format.apply(n,arguments))},n.inherits=e(\"inherits\"),n._extend=function(e,t){if(!t||!C(t))return e;var n=Object.keys(t),r=n.length;while(r--)e[n[r]]=t[n[r]];return e}}).call(this,e(\"/usr/local/lib/node_modules/browserify/node_modules/insert-module-globals/node_modules/process/browser.js\"),typeof self!=\"undefined\"?self:typeof window!=\"undefined\"?window:{})},{\"./support/isBuffer\":14,\"/usr/local/lib/node_modules/browserify/node_modules/insert-module-globals/node_modules/process/browser.js\":18,inherits:17}],16:[function(e,t,n){function r(){this._events=this._events||{},this._maxListeners=this._maxListeners||undefined}function i(e){return typeof e==\"function\"}function s(e){return typeof e==\"number\"}function o(e){return typeof e==\"object\"&&e!==null}function u(e){return e===void 0}t.exports=r,r.EventEmitter=r,r.prototype._events=undefined,r.prototype._maxListeners=undefined,r.defaultMaxListeners=10,r.prototype.setMaxListeners=function(e){if(!s(e)||e<0||isNaN(e))throw TypeError(\"n must be a positive number\");return this._maxListeners=e,this},r.prototype.emit=function(e){var t,n,r,s,a,f;this._events||(this._events={});if(e===\"error\")if(!this._events.error||o(this._events.error)&&!this._events.error.length)throw t=arguments[1],t instanceof Error?t:TypeError('Uncaught, unspecified \"error\" event.');n=this._events[e];if(u(n))return!1;if(i(n))switch(arguments.length){case 1:n.call(this);break;case 2:n.call(this,arguments[1]);break;case 3:n.call(this,arguments[1],arguments[2]);break;default:r=arguments.length,s=new Array(r-1);for(a=1;a<r;a++)s[a-1]=arguments[a];n.apply(this,s)}else if(o(n)){r=arguments.length,s=new Array(r-1);for(a=1;a<r;a++)s[a-1]=arguments[a];f=n.slice(),r=f.length;for(a=0;a<r;a++)f[a].apply(this,s)}return!0},r.prototype.addListener=function(e,t){var n;if(!i(t))throw TypeError(\"listener must be a function\");this._events||(this._events={}),this._events.newListener&&this.emit(\"newListener\",e,i(t.listener)?t.listener:t),this._events[e]?o(this._events[e])?this._events[e].push(t):this._events[e]=[this._events[e],t]:this._events[e]=t;if(o(this._events[e])&&!this._events[e].warned){var n;u(this._maxListeners)?n=r.defaultMaxListeners:n=this._maxListeners,n&&n>0&&this._events[e].length>n&&(this._events[e].warned=!0,console.error(\"(node) warning: possible EventEmitter memory leak detected. %d listeners added. Use emitter.setMaxListeners() to increase limit.\",this._events[e].length),console.trace())}return this},r.prototype.on=r.prototype.addListener,r.prototype.once=function(e,t){function r(){this.removeListener(e,r),n||(n=!0,t.apply(this,arguments))}if(!i(t))throw TypeError(\"listener must be a function\");var n=!1;return r.listener=t,this.on(e,r),this},r.prototype.removeListener=function(e,t){var n,r,s,u;if(!i(t))throw TypeError(\"listener must be a function\");if(!this._events||!this._events[e])return this;n=this._events[e],s=n.length,r=-1;if(n===t||i(n.listener)&&n.listener===t)delete this._events[e],this._events.removeListener&&this.emit(\"removeListener\",e,t);else if(o(n)){for(u=s;u-->0;)if(n[u]===t||n[u].listener&&n[u].listener===t){r=u;break}if(r<0)return this;n.length===1?(n.length=0,delete this._events[e]):n.splice(r,1),this._events.removeListener&&this.emit(\"removeListener\",e,t)}return this},r.prototype.removeAllListeners=function(e){var t,n;if(!this._events)return this;if(!this._events.removeListener)return arguments.length===0?this._events={}:this._events[e]&&delete this._events[e],this;if(arguments.length===0){for(t in this._events){if(t===\"removeListener\")continue;this.removeAllListeners(t)}return this.removeAllListeners(\"removeListener\"),this._events={},this}n=this._events[e];if(i(n))this.removeListener(e,n);else while(n.length)this.removeListener(e,n[n.length-1]);return delete this._events[e],this},r.prototype.listeners=function(e){var t;return!this._events||!this._events[e]?t=[]:i(this._events[e])?t=[this._events[e]]:t=this._events[e].slice(),t},r.listenerCount=function(e,t){var n;return!e._events||!e._events[t]?n=0:i(e._events[t])?n=1:n=e._events[t].length,n}},{}],17:[function(e,t,n){typeof Object.create==\"function\"?t.exports=function(t,n){t.super_=n,t.prototype=Object.create(n.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}})}:t.exports=function(t,n){t.super_=n;var r=function(){};r.prototype=n.prototype,t.prototype=new r,t.prototype.constructor=t}},{}],18:[function(e,t,n){function i(){}var r=t.exports={};r.nextTick=function(){var e=typeof window!=\"undefined\"&&window.setImmediate,t=typeof window!=\"undefined\"&&window.postMessage&&window.addEventListener;if(e)return function(e){return window.setImmediate(e)};if(t){var n=[];return window.addEventListener(\"message\",function(e){var t=e.source;if((t===window||t===null)&&e.data===\"process-tick\"){e.stopPropagation();if(n.length>0){var r=n.shift();r()}}},!0),function(t){n.push(t),window.postMessage(\"process-tick\",\"*\")}}return function(t){setTimeout(t,0)}}(),r.title=\"browser\",r.browser=!0,r.env={},r.argv=[],r.on=i,r.once=i,r.off=i,r.emit=i,r.binding=function(e){throw new Error(\"process.binding is not supported\")},r.cwd=function(){return\"/\"},r.chdir=function(e){throw new Error(\"process.chdir is not supported\")}},{}],19:[function(e,t,n){t.exports=e(14)},{}],20:[function(e,t,n){t.exports=e(15)},{\"./support/isBuffer\":19,\"/usr/local/lib/node_modules/browserify/node_modules/insert-module-globals/node_modules/process/browser.js\":18,inherits:17}]},{},[9])(9)}),define(\"ace/mode/html_worker\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/worker/mirror\",\"ace/mode/html/saxparser\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"../worker/mirror\").Mirror,o=e(\"./html/saxparser\").SAXParser,u={\"expected-doctype-but-got-start-tag\":\"info\",\"expected-doctype-but-got-chars\":\"info\",\"non-html-root\":\"info\"},a=t.Worker=function(e){s.call(this,e),this.setTimeout(400),this.context=null};r.inherits(a,s),function(){this.setOptions=function(e){this.context=e.context},this.onUpdate=function(){var e=this.doc.getValue();if(!e)return;var t=new o,n=[],r=function(){};t.contentHandler={startDocument:r,endDocument:r,startElement:r,endElement:r,characters:r},t.errorHandler={error:function(e,t,r){n.push({row:t.line,column:t.column,text:e,type:u[r]||\"error\"})}},this.context?t.parseFragment(e,this.context):t.parse(e),this.sender.emit(\"error\",n)}}.call(a.prototype)}),define(\"ace/lib/es5-shim\",[\"require\",\"exports\",\"module\"],function(e,t,n){function r(){}function w(e){try{return Object.defineProperty(e,\"sentinel\",{}),\"sentinel\"in e}catch(t){}}function H(e){return e=+e,e!==e?e=0:e!==0&&e!==1/0&&e!==-1/0&&(e=(e>0||-1)*Math.floor(Math.abs(e))),e}function B(e){var t=typeof e;return e===null||t===\"undefined\"||t===\"boolean\"||t===\"number\"||t===\"string\"}function j(e){var t,n,r;if(B(e))return e;n=e.valueOf;if(typeof n==\"function\"){t=n.call(e);if(B(t))return t}r=e.toString;if(typeof r==\"function\"){t=r.call(e);if(B(t))return t}throw new TypeError}Function.prototype.bind||(Function.prototype.bind=function(t){var n=this;if(typeof n!=\"function\")throw new TypeError(\"Function.prototype.bind called on incompatible \"+n);var i=u.call(arguments,1),s=function(){if(this instanceof s){var e=n.apply(this,i.concat(u.call(arguments)));return Object(e)===e?e:this}return n.apply(t,i.concat(u.call(arguments)))};return n.prototype&&(r.prototype=n.prototype,s.prototype=new r,r.prototype=null),s});var i=Function.prototype.call,s=Array.prototype,o=Object.prototype,u=s.slice,a=i.bind(o.toString),f=i.bind(o.hasOwnProperty),l,c,h,p,d;if(d=f(o,\"__defineGetter__\"))l=i.bind(o.__defineGetter__),c=i.bind(o.__defineSetter__),h=i.bind(o.__lookupGetter__),p=i.bind(o.__lookupSetter__);if([1,2].splice(0).length!=2)if(!function(){function e(e){var t=new Array(e+2);return t[0]=t[1]=0,t}var t=[],n;t.splice.apply(t,e(20)),t.splice.apply(t,e(26)),n=t.length,t.splice(5,0,\"XXX\"),n+1==t.length;if(n+1==t.length)return!0}())Array.prototype.splice=function(e,t){var n=this.length;e>0?e>n&&(e=n):e==void 0?e=0:e<0&&(e=Math.max(n+e,0)),e+t<n||(t=n-e);var r=this.slice(e,e+t),i=u.call(arguments,2),s=i.length;if(e===n)s&&this.push.apply(this,i);else{var o=Math.min(t,n-e),a=e+o,f=a+s-o,l=n-a,c=n-o;if(f<a)for(var h=0;h<l;++h)this[f+h]=this[a+h];else if(f>a)for(h=l;h--;)this[f+h]=this[a+h];if(s&&e===c)this.length=c,this.push.apply(this,i);else{this.length=c+s;for(h=0;h<s;++h)this[e+h]=i[h]}}return r};else{var v=Array.prototype.splice;Array.prototype.splice=function(e,t){return arguments.length?v.apply(this,[e===void 0?0:e,t===void 0?this.length-e:t].concat(u.call(arguments,2))):[]}}Array.isArray||(Array.isArray=function(t){return a(t)==\"[object Array]\"});var m=Object(\"a\"),g=m[0]!=\"a\"||!(0 in m);Array.prototype.forEach||(Array.prototype.forEach=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=arguments[1],s=-1,o=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError;while(++s<o)s in r&&t.call(i,r[s],s,n)}),Array.prototype.map||(Array.prototype.map=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=Array(i),o=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var u=0;u<i;u++)u in r&&(s[u]=t.call(o,r[u],u,n));return s}),Array.prototype.filter||(Array.prototype.filter=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=[],o,u=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var f=0;f<i;f++)f in r&&(o=r[f],t.call(u,o,f,n)&&s.push(o));return s}),Array.prototype.every||(Array.prototype.every=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&!t.call(s,r[o],o,n))return!1;return!0}),Array.prototype.some||(Array.prototype.some=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&t.call(s,r[o],o,n))return!0;return!1}),Array.prototype.reduce||(Array.prototype.reduce=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduce of empty array with no initial value\");var s=0,o;if(arguments.length>=2)o=arguments[1];else do{if(s in r){o=r[s++];break}if(++s>=i)throw new TypeError(\"reduce of empty array with no initial value\")}while(!0);for(;s<i;s++)s in r&&(o=t.call(void 0,o,r[s],s,n));return o}),Array.prototype.reduceRight||(Array.prototype.reduceRight=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduceRight of empty array with no initial value\");var s,o=i-1;if(arguments.length>=2)s=arguments[1];else do{if(o in r){s=r[o--];break}if(--o<0)throw new TypeError(\"reduceRight of empty array with no initial value\")}while(!0);do o in this&&(s=t.call(void 0,s,r[o],o,n));while(o--);return s});if(!Array.prototype.indexOf||[0,1].indexOf(1,2)!=-1)Array.prototype.indexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=0;arguments.length>1&&(i=H(arguments[1])),i=i>=0?i:Math.max(0,r+i);for(;i<r;i++)if(i in n&&n[i]===t)return i;return-1};if(!Array.prototype.lastIndexOf||[0,1].lastIndexOf(0,-3)!=-1)Array.prototype.lastIndexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=r-1;arguments.length>1&&(i=Math.min(i,H(arguments[1]))),i=i>=0?i:r-Math.abs(i);for(;i>=0;i--)if(i in n&&t===n[i])return i;return-1};Object.getPrototypeOf||(Object.getPrototypeOf=function(t){return t.__proto__||(t.constructor?t.constructor.prototype:o)});if(!Object.getOwnPropertyDescriptor){var y=\"Object.getOwnPropertyDescriptor called on a non-object: \";Object.getOwnPropertyDescriptor=function(t,n){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(y+t);if(!f(t,n))return;var r,i,s;r={enumerable:!0,configurable:!0};if(d){var u=t.__proto__;t.__proto__=o;var i=h(t,n),s=p(t,n);t.__proto__=u;if(i||s)return i&&(r.get=i),s&&(r.set=s),r}return r.value=t[n],r}}Object.getOwnPropertyNames||(Object.getOwnPropertyNames=function(t){return Object.keys(t)});if(!Object.create){var b;Object.prototype.__proto__===null?b=function(){return{__proto__:null}}:b=function(){var e={};for(var t in e)e[t]=null;return e.constructor=e.hasOwnProperty=e.propertyIsEnumerable=e.isPrototypeOf=e.toLocaleString=e.toString=e.valueOf=e.__proto__=null,e},Object.create=function(t,n){var r;if(t===null)r=b();else{if(typeof t!=\"object\")throw new TypeError(\"typeof prototype[\"+typeof t+\"] != 'object'\");var i=function(){};i.prototype=t,r=new i,r.__proto__=t}return n!==void 0&&Object.defineProperties(r,n),r}}if(Object.defineProperty){var E=w({}),S=typeof document==\"undefined\"||w(document.createElement(\"div\"));if(!E||!S)var x=Object.defineProperty}if(!Object.defineProperty||x){var T=\"Property description must be an object: \",N=\"Object.defineProperty called on non-object: \",C=\"getters & setters can not be defined on this javascript engine\";Object.defineProperty=function(t,n,r){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(N+t);if(typeof r!=\"object\"&&typeof r!=\"function\"||r===null)throw new TypeError(T+r);if(x)try{return x.call(Object,t,n,r)}catch(i){}if(f(r,\"value\"))if(d&&(h(t,n)||p(t,n))){var s=t.__proto__;t.__proto__=o,delete t[n],t[n]=r.value,t.__proto__=s}else t[n]=r.value;else{if(!d)throw new TypeError(C);f(r,\"get\")&&l(t,n,r.get),f(r,\"set\")&&c(t,n,r.set)}return t}}Object.defineProperties||(Object.defineProperties=function(t,n){for(var r in n)f(n,r)&&Object.defineProperty(t,r,n[r]);return t}),Object.seal||(Object.seal=function(t){return t}),Object.freeze||(Object.freeze=function(t){return t});try{Object.freeze(function(){})}catch(k){Object.freeze=function(t){return function(n){return typeof n==\"function\"?n:t(n)}}(Object.freeze)}Object.preventExtensions||(Object.preventExtensions=function(t){return t}),Object.isSealed||(Object.isSealed=function(t){return!1}),Object.isFrozen||(Object.isFrozen=function(t){return!1}),Object.isExtensible||(Object.isExtensible=function(t){if(Object(t)===t)throw new TypeError;var n=\"\";while(f(t,n))n+=\"?\";t[n]=!0;var r=f(t,n);return delete t[n],r});if(!Object.keys){var L=!0,A=[\"toString\",\"toLocaleString\",\"valueOf\",\"hasOwnProperty\",\"isPrototypeOf\",\"propertyIsEnumerable\",\"constructor\"],O=A.length;for(var M in{toString:null})L=!1;Object.keys=function I(e){if(typeof e!=\"object\"&&typeof e!=\"function\"||e===null)throw new TypeError(\"Object.keys called on a non-object\");var I=[];for(var t in e)f(e,t)&&I.push(t);if(L)for(var n=0,r=O;n<r;n++){var i=A[n];f(e,i)&&I.push(i)}return I}}Date.now||(Date.now=function(){return(new Date).getTime()});var _=\"\t\\n\u000b\\f\\r \\u00a0\\u1680\\u180e\\u2000\\u2001\\u2002\\u2003\\u2004\\u2005\\u2006\\u2007\\u2008\\u2009\\u200a\\u202f\\u205f\\u3000\\u2028\\u2029\\ufeff\";if(!String.prototype.trim||_.trim()){_=\"[\"+_+\"]\";var D=new RegExp(\"^\"+_+_+\"*\"),P=new RegExp(_+_+\"*$\");String.prototype.trim=function(){return String(this).replace(D,\"\").replace(P,\"\")}}var F=function(e){if(e==null)throw new TypeError(\"can't convert \"+e+\" to object\");return Object(e)}})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/worker-javascript.js",
    "content": "\"no use strict\";(function(e){function t(e,t){var n=e,r=\"\";while(n){var i=t[n];if(typeof i==\"string\")return i+r;if(i)return i.location.replace(/\\/*$/,\"/\")+(r||i.main||i.name);if(i===!1)return\"\";var s=n.lastIndexOf(\"/\");if(s===-1)break;r=n.substr(s)+r,n=n.slice(0,s)}return e}if(typeof e.window!=\"undefined\"&&e.document)return;if(e.require&&e.define)return;e.console||(e.console=function(){var e=Array.prototype.slice.call(arguments,0);postMessage({type:\"log\",data:e})},e.console.error=e.console.warn=e.console.log=e.console.trace=e.console),e.window=e,e.ace=e,e.onerror=function(e,t,n,r,i){postMessage({type:\"error\",data:{message:e,data:i.data,file:t,line:n,col:r,stack:i.stack}})},e.normalizeModule=function(t,n){if(n.indexOf(\"!\")!==-1){var r=n.split(\"!\");return e.normalizeModule(t,r[0])+\"!\"+e.normalizeModule(t,r[1])}if(n.charAt(0)==\".\"){var i=t.split(\"/\").slice(0,-1).join(\"/\");n=(i?i+\"/\":\"\")+n;while(n.indexOf(\".\")!==-1&&s!=n){var s=n;n=n.replace(/^\\.\\//,\"\").replace(/\\/\\.\\//,\"/\").replace(/[^\\/]+\\/\\.\\.\\//,\"\")}}return n},e.require=function(r,i){i||(i=r,r=null);if(!i.charAt)throw new Error(\"worker.js require() accepts only (parentId, id) as arguments\");i=e.normalizeModule(r,i);var s=e.require.modules[i];if(s)return s.initialized||(s.initialized=!0,s.exports=s.factory().exports),s.exports;if(!e.require.tlns)return console.log(\"unable to load \"+i);var o=t(i,e.require.tlns);return o.slice(-3)!=\".js\"&&(o+=\".js\"),e.require.id=i,e.require.modules[i]={},importScripts(o),e.require(r,i)},e.require.modules={},e.require.tlns={},e.define=function(t,n,r){arguments.length==2?(r=n,typeof t!=\"string\"&&(n=t,t=e.require.id)):arguments.length==1&&(r=t,n=[],t=e.require.id);if(typeof r!=\"function\"){e.require.modules[t]={exports:r,initialized:!0};return}n.length||(n=[\"require\",\"exports\",\"module\"]);var i=function(n){return e.require(t,n)};e.require.modules[t]={exports:{},factory:function(){var e=this,t=r.apply(this,n.map(function(t){switch(t){case\"require\":return i;case\"exports\":return e.exports;case\"module\":return e;default:return i(t)}}));return t&&(e.exports=t),e}}},e.define.amd={},require.tlns={},e.initBaseUrls=function(t){for(var n in t)require.tlns[n]=t[n]},e.initSender=function(){var n=e.require(\"ace/lib/event_emitter\").EventEmitter,r=e.require(\"ace/lib/oop\"),i=function(){};return function(){r.implement(this,n),this.callback=function(e,t){postMessage({type:\"call\",id:t,data:e})},this.emit=function(e,t){postMessage({type:\"event\",name:e,data:t})}}.call(i.prototype),new i};var n=e.main=null,r=e.sender=null;e.onmessage=function(t){var i=t.data;if(i.event&&r)r._signal(i.event,i.data);else if(i.command)if(n[i.command])n[i.command].apply(n,i.args);else{if(!e[i.command])throw new Error(\"Unknown command:\"+i.command);e[i.command].apply(e,i.args)}else if(i.init){e.initBaseUrls(i.tlns),require(\"ace/lib/es5-shim\"),r=e.sender=e.initSender();var s=require(i.module)[i.classname];n=e.main=new s(r)}}})(this),define(\"ace/lib/oop\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.inherits=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})},t.mixin=function(e,t){for(var n in t)e[n]=t[n];return e},t.implement=function(e,n){t.mixin(e,n)}}),define(\"ace/range\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(e,t){return e.row-t.row||e.column-t.column},i=function(e,t,n,r){this.start={row:e,column:t},this.end={row:n,column:r}};(function(){this.isEqual=function(e){return this.start.row===e.start.row&&this.end.row===e.end.row&&this.start.column===e.start.column&&this.end.column===e.end.column},this.toString=function(){return\"Range: [\"+this.start.row+\"/\"+this.start.column+\"] -> [\"+this.end.row+\"/\"+this.end.column+\"]\"},this.contains=function(e,t){return this.compare(e,t)==0},this.compareRange=function(e){var t,n=e.end,r=e.start;return t=this.compare(n.row,n.column),t==1?(t=this.compare(r.row,r.column),t==1?2:t==0?1:0):t==-1?-2:(t=this.compare(r.row,r.column),t==-1?-1:t==1?42:0)},this.comparePoint=function(e){return this.compare(e.row,e.column)},this.containsRange=function(e){return this.comparePoint(e.start)==0&&this.comparePoint(e.end)==0},this.intersects=function(e){var t=this.compareRange(e);return t==-1||t==0||t==1},this.isEnd=function(e,t){return this.end.row==e&&this.end.column==t},this.isStart=function(e,t){return this.start.row==e&&this.start.column==t},this.setStart=function(e,t){typeof e==\"object\"?(this.start.column=e.column,this.start.row=e.row):(this.start.row=e,this.start.column=t)},this.setEnd=function(e,t){typeof e==\"object\"?(this.end.column=e.column,this.end.row=e.row):(this.end.row=e,this.end.column=t)},this.inside=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)||this.isStart(e,t)?!1:!0:!1},this.insideStart=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)?!1:!0:!1},this.insideEnd=function(e,t){return this.compare(e,t)==0?this.isStart(e,t)?!1:!0:!1},this.compare=function(e,t){return!this.isMultiLine()&&e===this.start.row?t<this.start.column?-1:t>this.end.column?1:0:e<this.start.row?-1:e>this.end.row?1:this.start.row===e?t>=this.start.column?0:-1:this.end.row===e?t<=this.end.column?0:1:0},this.compareStart=function(e,t){return this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.compareEnd=function(e,t){return this.end.row==e&&this.end.column==t?1:this.compare(e,t)},this.compareInside=function(e,t){return this.end.row==e&&this.end.column==t?1:this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.clipRows=function(e,t){if(this.end.row>t)var n={row:t+1,column:0};else if(this.end.row<e)var n={row:e,column:0};if(this.start.row>t)var r={row:t+1,column:0};else if(this.start.row<e)var r={row:e,column:0};return i.fromPoints(r||this.start,n||this.end)},this.extend=function(e,t){var n=this.compare(e,t);if(n==0)return this;if(n==-1)var r={row:e,column:t};else var s={row:e,column:t};return i.fromPoints(r||this.start,s||this.end)},this.isEmpty=function(){return this.start.row===this.end.row&&this.start.column===this.end.column},this.isMultiLine=function(){return this.start.row!==this.end.row},this.clone=function(){return i.fromPoints(this.start,this.end)},this.collapseRows=function(){return this.end.column==0?new i(this.start.row,0,Math.max(this.start.row,this.end.row-1),0):new i(this.start.row,0,this.end.row,0)},this.toScreenRange=function(e){var t=e.documentToScreenPosition(this.start),n=e.documentToScreenPosition(this.end);return new i(t.row,t.column,n.row,n.column)},this.moveBy=function(e,t){this.start.row+=e,this.start.column+=t,this.end.row+=e,this.end.column+=t}}).call(i.prototype),i.fromPoints=function(e,t){return new i(e.row,e.column,t.row,t.column)},i.comparePoints=r,i.comparePoints=function(e,t){return e.row-t.row||e.column-t.column},t.Range=i}),define(\"ace/apply_delta\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function r(e,t){throw console.log(\"Invalid Delta:\",e),\"Invalid Delta: \"+t}function i(e,t){return t.row>=0&&t.row<e.length&&t.column>=0&&t.column<=e[t.row].length}function s(e,t){t.action!=\"insert\"&&t.action!=\"remove\"&&r(t,\"delta.action must be 'insert' or 'remove'\"),t.lines instanceof Array||r(t,\"delta.lines must be an Array\"),(!t.start||!t.end)&&r(t,\"delta.start/end must be an present\");var n=t.start;i(e,t.start)||r(t,\"delta.start must be contained in document\");var s=t.end;t.action==\"remove\"&&!i(e,s)&&r(t,\"delta.end must contained in document for 'remove' actions\");var o=s.row-n.row,u=s.column-(o==0?n.column:0);(o!=t.lines.length-1||t.lines[o].length!=u)&&r(t,\"delta.range must match delta lines\")}t.applyDelta=function(e,t,n){var r=t.start.row,i=t.start.column,s=e[r]||\"\";switch(t.action){case\"insert\":var o=t.lines;if(o.length===1)e[r]=s.substring(0,i)+t.lines[0]+s.substring(i);else{var u=[r,1].concat(t.lines);e.splice.apply(e,u),e[r]=s.substring(0,i)+e[r],e[r+t.lines.length-1]+=s.substring(i)}break;case\"remove\":var a=t.end.column,f=t.end.row;r===f?e[r]=s.substring(0,i)+s.substring(a):e.splice(r,f-r+1,s.substring(0,i)+e[f].substring(a))}}}),define(\"ace/lib/event_emitter\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={},i=function(){this.propagationStopped=!0},s=function(){this.defaultPrevented=!0};r._emit=r._dispatchEvent=function(e,t){this._eventRegistry||(this._eventRegistry={}),this._defaultHandlers||(this._defaultHandlers={});var n=this._eventRegistry[e]||[],r=this._defaultHandlers[e];if(!n.length&&!r)return;if(typeof t!=\"object\"||!t)t={};t.type||(t.type=e),t.stopPropagation||(t.stopPropagation=i),t.preventDefault||(t.preventDefault=s),n=n.slice();for(var o=0;o<n.length;o++){n[o](t,this);if(t.propagationStopped)break}if(r&&!t.defaultPrevented)return r(t,this)},r._signal=function(e,t){var n=(this._eventRegistry||{})[e];if(!n)return;n=n.slice();for(var r=0;r<n.length;r++)n[r](t,this)},r.once=function(e,t){var n=this;t&&this.addEventListener(e,function r(){n.removeEventListener(e,r),t.apply(null,arguments)})},r.setDefaultHandler=function(e,t){var n=this._defaultHandlers;n||(n=this._defaultHandlers={_disabled_:{}});if(n[e]){var r=n[e],i=n._disabled_[e];i||(n._disabled_[e]=i=[]),i.push(r);var s=i.indexOf(t);s!=-1&&i.splice(s,1)}n[e]=t},r.removeDefaultHandler=function(e,t){var n=this._defaultHandlers;if(!n)return;var r=n._disabled_[e];if(n[e]==t){var i=n[e];r&&this.setDefaultHandler(e,r.pop())}else if(r){var s=r.indexOf(t);s!=-1&&r.splice(s,1)}},r.on=r.addEventListener=function(e,t,n){this._eventRegistry=this._eventRegistry||{};var r=this._eventRegistry[e];return r||(r=this._eventRegistry[e]=[]),r.indexOf(t)==-1&&r[n?\"unshift\":\"push\"](t),t},r.off=r.removeListener=r.removeEventListener=function(e,t){this._eventRegistry=this._eventRegistry||{};var n=this._eventRegistry[e];if(!n)return;var r=n.indexOf(t);r!==-1&&n.splice(r,1)},r.removeAllListeners=function(e){this._eventRegistry&&(this._eventRegistry[e]=[])},t.EventEmitter=r}),define(\"ace/anchor\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/event_emitter\").EventEmitter,s=t.Anchor=function(e,t,n){this.$onChange=this.onChange.bind(this),this.attach(e),typeof n==\"undefined\"?this.setPosition(t.row,t.column):this.setPosition(t,n)};(function(){function e(e,t,n){var r=n?e.column<=t.column:e.column<t.column;return e.row<t.row||e.row==t.row&&r}function t(t,n,r){var i=t.action==\"insert\",s=(i?1:-1)*(t.end.row-t.start.row),o=(i?1:-1)*(t.end.column-t.start.column),u=t.start,a=i?u:t.end;return e(n,u,r)?{row:n.row,column:n.column}:e(a,n,!r)?{row:n.row+s,column:n.column+(n.row==a.row?o:0)}:{row:u.row,column:u.column}}r.implement(this,i),this.getPosition=function(){return this.$clipPositionToDocument(this.row,this.column)},this.getDocument=function(){return this.document},this.$insertRight=!1,this.onChange=function(e){if(e.start.row==e.end.row&&e.start.row!=this.row)return;if(e.start.row>this.row)return;var n=t(e,{row:this.row,column:this.column},this.$insertRight);this.setPosition(n.row,n.column,!0)},this.setPosition=function(e,t,n){var r;n?r={row:e,column:t}:r=this.$clipPositionToDocument(e,t);if(this.row==r.row&&this.column==r.column)return;var i={row:this.row,column:this.column};this.row=r.row,this.column=r.column,this._signal(\"change\",{old:i,value:r})},this.detach=function(){this.document.removeEventListener(\"change\",this.$onChange)},this.attach=function(e){this.document=e||this.document,this.document.on(\"change\",this.$onChange)},this.$clipPositionToDocument=function(e,t){var n={};return e>=this.document.getLength()?(n.row=Math.max(0,this.document.getLength()-1),n.column=this.document.getLine(n.row).length):e<0?(n.row=0,n.column=0):(n.row=e,n.column=Math.min(this.document.getLine(n.row).length,Math.max(0,t))),t<0&&(n.column=0),n}}).call(s.prototype)}),define(\"ace/document\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/apply_delta\",\"ace/lib/event_emitter\",\"ace/range\",\"ace/anchor\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./apply_delta\").applyDelta,s=e(\"./lib/event_emitter\").EventEmitter,o=e(\"./range\").Range,u=e(\"./anchor\").Anchor,a=function(e){this.$lines=[\"\"],e.length===0?this.$lines=[\"\"]:Array.isArray(e)?this.insertMergedLines({row:0,column:0},e):this.insert({row:0,column:0},e)};(function(){r.implement(this,s),this.setValue=function(e){var t=this.getLength()-1;this.remove(new o(0,0,t,this.getLine(t).length)),this.insert({row:0,column:0},e)},this.getValue=function(){return this.getAllLines().join(this.getNewLineCharacter())},this.createAnchor=function(e,t){return new u(this,e,t)},\"aaa\".split(/a/).length===0?this.$split=function(e){return e.replace(/\\r\\n|\\r/g,\"\\n\").split(\"\\n\")}:this.$split=function(e){return e.split(/\\r\\n|\\r|\\n/)},this.$detectNewLine=function(e){var t=e.match(/^.*?(\\r\\n|\\r|\\n)/m);this.$autoNewLine=t?t[1]:\"\\n\",this._signal(\"changeNewLineMode\")},this.getNewLineCharacter=function(){switch(this.$newLineMode){case\"windows\":return\"\\r\\n\";case\"unix\":return\"\\n\";default:return this.$autoNewLine||\"\\n\"}},this.$autoNewLine=\"\",this.$newLineMode=\"auto\",this.setNewLineMode=function(e){if(this.$newLineMode===e)return;this.$newLineMode=e,this._signal(\"changeNewLineMode\")},this.getNewLineMode=function(){return this.$newLineMode},this.isNewLine=function(e){return e==\"\\r\\n\"||e==\"\\r\"||e==\"\\n\"},this.getLine=function(e){return this.$lines[e]||\"\"},this.getLines=function(e,t){return this.$lines.slice(e,t+1)},this.getAllLines=function(){return this.getLines(0,this.getLength())},this.getLength=function(){return this.$lines.length},this.getTextRange=function(e){return this.getLinesForRange(e).join(this.getNewLineCharacter())},this.getLinesForRange=function(e){var t;if(e.start.row===e.end.row)t=[this.getLine(e.start.row).substring(e.start.column,e.end.column)];else{t=this.getLines(e.start.row,e.end.row),t[0]=(t[0]||\"\").substring(e.start.column);var n=t.length-1;e.end.row-e.start.row==n&&(t[n]=t[n].substring(0,e.end.column))}return t},this.insertLines=function(e,t){return console.warn(\"Use of document.insertLines is deprecated. Use the insertFullLines method instead.\"),this.insertFullLines(e,t)},this.removeLines=function(e,t){return console.warn(\"Use of document.removeLines is deprecated. Use the removeFullLines method instead.\"),this.removeFullLines(e,t)},this.insertNewLine=function(e){return console.warn(\"Use of document.insertNewLine is deprecated. Use insertMergedLines(position, ['', '']) instead.\"),this.insertMergedLines(e,[\"\",\"\"])},this.insert=function(e,t){return this.getLength()<=1&&this.$detectNewLine(t),this.insertMergedLines(e,this.$split(t))},this.insertInLine=function(e,t){var n=this.clippedPos(e.row,e.column),r=this.pos(e.row,e.column+t.length);return this.applyDelta({start:n,end:r,action:\"insert\",lines:[t]},!0),this.clonePos(r)},this.clippedPos=function(e,t){var n=this.getLength();e===undefined?e=n:e<0?e=0:e>=n&&(e=n-1,t=undefined);var r=this.getLine(e);return t==undefined&&(t=r.length),t=Math.min(Math.max(t,0),r.length),{row:e,column:t}},this.clonePos=function(e){return{row:e.row,column:e.column}},this.pos=function(e,t){return{row:e,column:t}},this.$clipPosition=function(e){var t=this.getLength();return e.row>=t?(e.row=Math.max(0,t-1),e.column=this.getLine(t-1).length):(e.row=Math.max(0,e.row),e.column=Math.min(Math.max(e.column,0),this.getLine(e.row).length)),e},this.insertFullLines=function(e,t){e=Math.min(Math.max(e,0),this.getLength());var n=0;e<this.getLength()?(t=t.concat([\"\"]),n=0):(t=[\"\"].concat(t),e--,n=this.$lines[e].length),this.insertMergedLines({row:e,column:n},t)},this.insertMergedLines=function(e,t){var n=this.clippedPos(e.row,e.column),r={row:n.row+t.length-1,column:(t.length==1?n.column:0)+t[t.length-1].length};return this.applyDelta({start:n,end:r,action:\"insert\",lines:t}),this.clonePos(r)},this.remove=function(e){var t=this.clippedPos(e.start.row,e.start.column),n=this.clippedPos(e.end.row,e.end.column);return this.applyDelta({start:t,end:n,action:\"remove\",lines:this.getLinesForRange({start:t,end:n})}),this.clonePos(t)},this.removeInLine=function(e,t,n){var r=this.clippedPos(e,t),i=this.clippedPos(e,n);return this.applyDelta({start:r,end:i,action:\"remove\",lines:this.getLinesForRange({start:r,end:i})},!0),this.clonePos(r)},this.removeFullLines=function(e,t){e=Math.min(Math.max(0,e),this.getLength()-1),t=Math.min(Math.max(0,t),this.getLength()-1);var n=t==this.getLength()-1&&e>0,r=t<this.getLength()-1,i=n?e-1:e,s=n?this.getLine(i).length:0,u=r?t+1:t,a=r?0:this.getLine(u).length,f=new o(i,s,u,a),l=this.$lines.slice(e,t+1);return this.applyDelta({start:f.start,end:f.end,action:\"remove\",lines:this.getLinesForRange(f)}),l},this.removeNewLine=function(e){e<this.getLength()-1&&e>=0&&this.applyDelta({start:this.pos(e,this.getLine(e).length),end:this.pos(e+1,0),action:\"remove\",lines:[\"\",\"\"]})},this.replace=function(e,t){e instanceof o||(e=o.fromPoints(e.start,e.end));if(t.length===0&&e.isEmpty())return e.start;if(t==this.getTextRange(e))return e.end;this.remove(e);var n;return t?n=this.insert(e.start,t):n=e.start,n},this.applyDeltas=function(e){for(var t=0;t<e.length;t++)this.applyDelta(e[t])},this.revertDeltas=function(e){for(var t=e.length-1;t>=0;t--)this.revertDelta(e[t])},this.applyDelta=function(e,t){var n=e.action==\"insert\";if(n?e.lines.length<=1&&!e.lines[0]:!o.comparePoints(e.start,e.end))return;n&&e.lines.length>2e4&&this.$splitAndapplyLargeDelta(e,2e4),i(this.$lines,e,t),this._signal(\"change\",e)},this.$splitAndapplyLargeDelta=function(e,t){var n=e.lines,r=n.length,i=e.start.row,s=e.start.column,o=0,u=0;do{o=u,u+=t-1;var a=n.slice(o,u);if(u>r){e.lines=a,e.start.row=i+o,e.start.column=s;break}a.push(\"\"),this.applyDelta({start:this.pos(i+o,s),end:this.pos(i+u,s=0),action:e.action,lines:a},!0)}while(!0)},this.revertDelta=function(e){this.applyDelta({start:this.clonePos(e.start),end:this.clonePos(e.end),action:e.action==\"insert\"?\"remove\":\"insert\",lines:e.lines.slice()})},this.indexToPosition=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length;for(var i=t||0,s=n.length;i<s;i++){e-=n[i].length+r;if(e<0)return{row:i,column:e+n[i].length+r}}return{row:s-1,column:n[s-1].length}},this.positionToIndex=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length,i=0,s=Math.min(e.row,n.length);for(var o=t||0;o<s;++o)i+=n[o].length+r;return i+e.column}}).call(a.prototype),t.Document=a}),define(\"ace/lib/lang\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.last=function(e){return e[e.length-1]},t.stringReverse=function(e){return e.split(\"\").reverse().join(\"\")},t.stringRepeat=function(e,t){var n=\"\";while(t>0){t&1&&(n+=e);if(t>>=1)e+=e}return n};var r=/^\\s\\s*/,i=/\\s\\s*$/;t.stringTrimLeft=function(e){return e.replace(r,\"\")},t.stringTrimRight=function(e){return e.replace(i,\"\")},t.copyObject=function(e){var t={};for(var n in e)t[n]=e[n];return t},t.copyArray=function(e){var t=[];for(var n=0,r=e.length;n<r;n++)e[n]&&typeof e[n]==\"object\"?t[n]=this.copyObject(e[n]):t[n]=e[n];return t},t.deepCopy=function s(e){if(typeof e!=\"object\"||!e)return e;var t;if(Array.isArray(e)){t=[];for(var n=0;n<e.length;n++)t[n]=s(e[n]);return t}if(Object.prototype.toString.call(e)!==\"[object Object]\")return e;t={};for(var n in e)t[n]=s(e[n]);return t},t.arrayToMap=function(e){var t={};for(var n=0;n<e.length;n++)t[e[n]]=1;return t},t.createMap=function(e){var t=Object.create(null);for(var n in e)t[n]=e[n];return t},t.arrayRemove=function(e,t){for(var n=0;n<=e.length;n++)t===e[n]&&e.splice(n,1)},t.escapeRegExp=function(e){return e.replace(/([.*+?^${}()|[\\]\\/\\\\])/g,\"\\\\$1\")},t.escapeHTML=function(e){return e.replace(/&/g,\"&#38;\").replace(/\"/g,\"&#34;\").replace(/'/g,\"&#39;\").replace(/</g,\"&#60;\")},t.getMatchOffsets=function(e,t){var n=[];return e.replace(t,function(e){n.push({offset:arguments[arguments.length-2],length:e.length})}),n},t.deferredCall=function(e){var t=null,n=function(){t=null,e()},r=function(e){return r.cancel(),t=setTimeout(n,e||0),r};return r.schedule=r,r.call=function(){return this.cancel(),e(),r},r.cancel=function(){return clearTimeout(t),t=null,r},r.isPending=function(){return t},r},t.delayedCall=function(e,t){var n=null,r=function(){n=null,e()},i=function(e){n==null&&(n=setTimeout(r,e||t))};return i.delay=function(e){n&&clearTimeout(n),n=setTimeout(r,e||t)},i.schedule=i,i.call=function(){this.cancel(),e()},i.cancel=function(){n&&clearTimeout(n),n=null},i.isPending=function(){return n},i}}),define(\"ace/worker/mirror\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/document\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=e(\"../document\").Document,s=e(\"../lib/lang\"),o=t.Mirror=function(e){this.sender=e;var t=this.doc=new i(\"\"),n=this.deferredUpdate=s.delayedCall(this.onUpdate.bind(this)),r=this;e.on(\"change\",function(e){var i=e.data;if(i[0].start)t.applyDeltas(i);else for(var s=0;s<i.length;s+=2){if(Array.isArray(i[s+1]))var o={action:\"insert\",start:i[s],lines:i[s+1]};else var o={action:\"remove\",start:i[s],end:i[s+1]};t.applyDelta(o,!0)}if(r.$timeout)return n.schedule(r.$timeout);r.onUpdate()})};(function(){this.$timeout=500,this.setTimeout=function(e){this.$timeout=e},this.setValue=function(e){this.doc.setValue(e),this.deferredUpdate.schedule(this.$timeout)},this.getValue=function(e){this.sender.callback(this.doc.getValue(),e)},this.onUpdate=function(){},this.isPending=function(){return this.deferredUpdate.isPending()}}).call(o.prototype)}),define(\"ace/mode/javascript/jshint\",[\"require\",\"exports\",\"module\"],function(e,t,n){n.exports=function r(t,n,i){function o(u,a){if(!n[u]){if(!t[u]){var f=typeof e==\"function\"&&e;if(!a&&f)return f(u,!0);if(s)return s(u,!0);var l=new Error(\"Cannot find module '\"+u+\"'\");throw l.code=\"MODULE_NOT_FOUND\",l}var c=n[u]={exports:{}};t[u][0].call(c.exports,function(e){var n=t[u][1][e];return o(n?n:e)},c,c.exports,r,t,n,i)}return n[u].exports}var s=typeof e==\"function\"&&e;for(var u=0;u<i.length;u++)o(i[u]);return o(i[0])}({\"/node_modules/browserify/node_modules/events/events.js\":[function(e,t,n){function r(){this._events=this._events||{},this._maxListeners=this._maxListeners||undefined}function i(e){return typeof e==\"function\"}function s(e){return typeof e==\"number\"}function o(e){return typeof e==\"object\"&&e!==null}function u(e){return e===void 0}t.exports=r,r.EventEmitter=r,r.prototype._events=undefined,r.prototype._maxListeners=undefined,r.defaultMaxListeners=10,r.prototype.setMaxListeners=function(e){if(!s(e)||e<0||isNaN(e))throw TypeError(\"n must be a positive number\");return this._maxListeners=e,this},r.prototype.emit=function(e){var t,n,r,s,a,f;this._events||(this._events={});if(e===\"error\")if(!this._events.error||o(this._events.error)&&!this._events.error.length)throw t=arguments[1],t instanceof Error?t:TypeError('Uncaught, unspecified \"error\" event.');n=this._events[e];if(u(n))return!1;if(i(n))switch(arguments.length){case 1:n.call(this);break;case 2:n.call(this,arguments[1]);break;case 3:n.call(this,arguments[1],arguments[2]);break;default:r=arguments.length,s=new Array(r-1);for(a=1;a<r;a++)s[a-1]=arguments[a];n.apply(this,s)}else if(o(n)){r=arguments.length,s=new Array(r-1);for(a=1;a<r;a++)s[a-1]=arguments[a];f=n.slice(),r=f.length;for(a=0;a<r;a++)f[a].apply(this,s)}return!0},r.prototype.addListener=function(e,t){var n;if(!i(t))throw TypeError(\"listener must be a function\");this._events||(this._events={}),this._events.newListener&&this.emit(\"newListener\",e,i(t.listener)?t.listener:t),this._events[e]?o(this._events[e])?this._events[e].push(t):this._events[e]=[this._events[e],t]:this._events[e]=t;if(o(this._events[e])&&!this._events[e].warned){var n;u(this._maxListeners)?n=r.defaultMaxListeners:n=this._maxListeners,n&&n>0&&this._events[e].length>n&&(this._events[e].warned=!0,console.error(\"(node) warning: possible EventEmitter memory leak detected. %d listeners added. Use emitter.setMaxListeners() to increase limit.\",this._events[e].length),typeof console.trace==\"function\"&&console.trace())}return this},r.prototype.on=r.prototype.addListener,r.prototype.once=function(e,t){function r(){this.removeListener(e,r),n||(n=!0,t.apply(this,arguments))}if(!i(t))throw TypeError(\"listener must be a function\");var n=!1;return r.listener=t,this.on(e,r),this},r.prototype.removeListener=function(e,t){var n,r,s,u;if(!i(t))throw TypeError(\"listener must be a function\");if(!this._events||!this._events[e])return this;n=this._events[e],s=n.length,r=-1;if(n===t||i(n.listener)&&n.listener===t)delete this._events[e],this._events.removeListener&&this.emit(\"removeListener\",e,t);else if(o(n)){for(u=s;u-->0;)if(n[u]===t||n[u].listener&&n[u].listener===t){r=u;break}if(r<0)return this;n.length===1?(n.length=0,delete this._events[e]):n.splice(r,1),this._events.removeListener&&this.emit(\"removeListener\",e,t)}return this},r.prototype.removeAllListeners=function(e){var t,n;if(!this._events)return this;if(!this._events.removeListener)return arguments.length===0?this._events={}:this._events[e]&&delete this._events[e],this;if(arguments.length===0){for(t in this._events){if(t===\"removeListener\")continue;this.removeAllListeners(t)}return this.removeAllListeners(\"removeListener\"),this._events={},this}n=this._events[e];if(i(n))this.removeListener(e,n);else while(n.length)this.removeListener(e,n[n.length-1]);return delete this._events[e],this},r.prototype.listeners=function(e){var t;return!this._events||!this._events[e]?t=[]:i(this._events[e])?t=[this._events[e]]:t=this._events[e].slice(),t},r.listenerCount=function(e,t){var n;return!e._events||!e._events[t]?n=0:i(e._events[t])?n=1:n=e._events[t].length,n}},{}],\"/node_modules/jshint/data/ascii-identifier-data.js\":[function(e,t,n){var r=[];for(var i=0;i<128;i++)r[i]=i===36||i>=65&&i<=90||i===95||i>=97&&i<=122;var s=[];for(var i=0;i<128;i++)s[i]=r[i]||i>=48&&i<=57;t.exports={asciiIdentifierStartTable:r,asciiIdentifierPartTable:s}},{}],\"/node_modules/jshint/lodash.js\":[function(e,t,n){(function(e){(function(){function $(e,t,n){var r=e.length,i=n?r:-1;while(n?i--:++i<r)if(t(e[i],i,e))return i;return-1}function J(e,t,n){if(t!==t)return G(e,n);var r=n-1,i=e.length;while(++r<i)if(e[r]===t)return r;return-1}function K(e){return typeof e==\"function\"||!1}function Q(e){return typeof e==\"string\"?e:e==null?\"\":e+\"\"}function G(e,t,n){var r=e.length,i=t+(n?0:-1);while(n?i--:++i<r){var s=e[i];if(s!==s)return i}return-1}function Y(e){return!!e&&typeof e==\"object\"}function Ct(){}function Lt(e,t){var n=-1,r=e.length;t||(t=Array(r));while(++n<r)t[n]=e[n];return t}function At(e,t){var n=-1,r=e.length;while(++n<r)if(t(e[n],n,e)===!1)break;return e}function Ot(e,t){var n=-1,r=e.length,i=-1,s=[];while(++n<r){var o=e[n];t(o,n,e)&&(s[++i]=o)}return s}function Mt(e,t){var n=-1,r=e.length,i=Array(r);while(++n<r)i[n]=t(e[n],n,e);return i}function _t(e){var t=-1,n=e.length,r=wt;while(++t<n){var i=e[t];i>r&&(r=i)}return r}function Dt(e,t){var n=-1,r=e.length;while(++n<r)if(t(e[n],n,e))return!0;return!1}function Pt(e,t,n){var i=rr(t);lt.apply(i,bn(t));var s=-1,o=i.length;while(++s<o){var u=i[s],a=e[u],f=n(a,t[u],u,e,t);if((f===f?f!==a:a===a)||a===r&&!(u in e))e[u]=f}return e}function Bt(e,t,n){n||(n={});var r=-1,i=t.length;while(++r<i){var s=t[r];n[s]=e[s]}return n}function jt(e,t,n){var i=typeof e;return i==\"function\"?t===r?e:on(e,t,n):e==null?lr:i==\"object\"?Jt(e):t===r?cr(e):Kt(e,t)}function Ft(e,t,n,i,s,u,a){var f;n&&(f=s?n(e,i,s):n(e));if(f!==r)return f;if(!Jn(e))return e;var l=Xn(e);if(l){f=wn(e);if(!t)return Lt(e,f)}else{var h=rt.call(e),p=h==c;if(!(h==d||h==o||p&&!s))return F[h]?Sn(e,h,t):s?e:{};f=En(p?{}:e);if(!t)return Ht(f,e)}u||(u=[]),a||(a=[]);var v=u.length;while(v--)if(u[v]==e)return a[v];return u.push(e),a.push(f),(l?At:zt)(e,function(r,i){f[i]=Ft(r,t,n,i,e,u,a)}),f}function qt(e,t){var n=[];return It(e,function(e,r,i){t(e,r,i)&&n.push(e)}),n}function Ut(e,t){return Rt(e,t,ir)}function zt(e,t){return Rt(e,t,rr)}function Wt(e,t,n){if(e==null)return;n!==r&&n in On(e)&&(t=[n]);var i=-1,s=t.length;while(e!=null&&++i<s)var o=e=e[t[i]];return o}function Xt(e,t,n,r,i,s){if(e===t)return e!==0||1/e==1/t;var o=typeof e,u=typeof t;return o!=\"function\"&&o!=\"object\"&&u!=\"function\"&&u!=\"object\"||e==null||t==null?e!==e&&t!==t:Vt(e,t,Xt,n,r,i,s)}function Vt(e,t,n,r,i,s,a){var f=Xn(e),l=Xn(t),c=u,h=u;f||(c=rt.call(e),c==o?c=d:c!=d&&(f=Zn(e))),l||(h=rt.call(t),h==o?h=d:h!=d&&(l=Zn(t)));var p=c==d,v=h==d,m=c==h;if(m&&!f&&!p)return dn(e,t,c);if(!i){var g=p&&nt.call(e,\"__wrapped__\"),y=v&&nt.call(t,\"__wrapped__\");if(g||y)return n(g?e.value():e,y?t.value():t,r,i,s,a)}if(!m)return!1;s||(s=[]),a||(a=[]);var b=s.length;while(b--)if(s[b]==e)return a[b]==t;s.push(e),a.push(t);var w=(f?pn:vn)(e,t,n,r,i,s,a);return s.pop(),a.pop(),w}function $t(e,t,n,i,s){var o=-1,u=t.length,a=!s;while(++o<u)if(a&&i[o]?n[o]!==e[t[o]]:!(t[o]in e))return!1;o=-1;while(++o<u){var f=t[o],l=e[f],c=n[o];if(a&&i[o])var h=l!==r||f in e;else h=s?s(l,c,f):r,h===r&&(h=Xt(c,l,s,!0));if(!h)return!1}return!0}function Jt(e){var t=rr(e),n=t.length;if(!n)return fr(!0);if(n==1){var i=t[0],s=e[i];if(kn(s))return function(e){return e==null?!1:e[i]===s&&(s!==r||i in On(e))}}var o=Array(n),u=Array(n);while(n--)s=e[t[n]],o[n]=s,u[n]=kn(s);return function(e){return e!=null&&$t(On(e),t,o,u)}}function Kt(e,t){var n=Xn(e),i=Nn(e)&&kn(t),s=e+\"\";return e=Mn(e),function(o){if(o==null)return!1;var u=s;o=On(o);if((n||!i)&&!(u in o)){o=e.length==1?o:Wt(o,en(e,0,-1));if(o==null)return!1;u=Pn(e),o=On(o)}return o[u]===t?t!==r||u in o:Xt(t,o[u],null,!0)}}function Qt(e,t,n,i,s){if(!Jn(e))return e;var o=Cn(t.length)&&(Xn(t)||Zn(t));if(!o){var u=rr(t);lt.apply(u,bn(t))}return At(u||t,function(a,f){u&&(f=a,a=t[f]);if(Y(a))i||(i=[]),s||(s=[]),Gt(e,t,f,Qt,n,i,s);else{var l=e[f],c=n?n(l,a,f,e,t):r,h=c===r;h&&(c=a),(o||c!==r)&&(h||(c===c?c!==l:l===l))&&(e[f]=c)}}),e}function Gt(e,t,n,i,s,o,u){var a=o.length,f=t[n];while(a--)if(o[a]==f){e[n]=u[a];return}var l=e[n],c=s?s(l,f,n,e,t):r,h=c===r;h&&(c=f,Cn(f.length)&&(Xn(f)||Zn(f))?c=Xn(l)?l:yn(l)?Lt(l):[]:Gn(f)||Wn(f)?c=Wn(l)?er(l):Gn(l)?l:{}:h=!1),o.push(f),u.push(c);if(h)e[n]=i(c,f,s,o,u);else if(c===c?c!==l:l===l)e[n]=c}function Yt(e){return function(t){return t==null?r:t[e]}}function Zt(e){var t=e+\"\";return e=Mn(e),function(n){return Wt(n,e,t)}}function en(e,t,n){var i=-1,s=e.length;t=t==null?0:+t||0,t<0&&(t=-t>s?0:s+t),n=n===r||n>s?s:+n||0,n<0&&(n+=s),s=t>n?0:n-t>>>0,t>>>=0;var o=Array(s);while(++i<s)o[i]=e[i+t];return o}function tn(e,t){var n;return It(e,function(e,r,i){return n=t(e,r,i),!n}),!!n}function nn(e,t){var n=-1,r=t.length,i=Array(r);while(++n<r)i[n]=e[t[n]];return i}function rn(e,t,n){var r=0,i=e?e.length:r;if(typeof t==\"number\"&&t===t&&i<=xt){while(r<i){var s=r+i>>>1,o=e[s];(n?o<=t:o<t)?r=s+1:i=s}return i}return sn(e,t,lr,n)}function sn(e,t,n,i){t=n(t);var s=0,o=e?e.length:0,u=t!==t,a=t===r;while(s<o){var f=ut((s+o)/2),l=n(e[f]),c=l===l;if(u)var h=c||i;else a?h=c&&(i||l!==r):h=i?l<=t:l<t;h?s=f+1:o=f}return bt(o,St)}function on(e,t,n){if(typeof e!=\"function\")return lr;if(t===r)return e;switch(n){case 1:return function(n){return e.call(t,n)};case 3:return function(n,r,i){return e.call(t,n,r,i)};case 4:return function(n,r,i,s){return e.call(t,n,r,i,s)};case 5:return function(n,r,i,s,o){return e.call(t,n,r,i,s,o)}}return function(){return e.apply(t,arguments)}}function un(e){return ot.call(e,0)}function an(e){return Un(function(t,n){var r=-1,i=t==null?0:n.length,s=i>2&&n[i-2],o=i>2&&n[2],u=i>1&&n[i-1];typeof s==\"function\"?(s=on(s,u,5),i-=2):(s=typeof u==\"function\"?u:null,i-=s?1:0),o&&Tn(n[0],n[1],o)&&(s=i<3?null:s,i=1);while(++r<i){var a=n[r];a&&e(t,a,s)}return t})}function fn(e,t){return function(n,r){var i=n?yn(n):0;if(!Cn(i))return e(n,r);var s=t?i:-1,o=On(n);while(t?s--:++s<i)if(r(o[s],s,o)===!1)break;return n}}function ln(e){return function(t,n,r){var i=On(t),s=r(t),o=s.length,u=e?o:-1;while(e?u--:++u<o){var a=s[u];if(n(i[a],a,i)===!1)break}return t}}function cn(e){return function(t,n,r){return!t||!t.length?-1:(n=mn(n,r,3),$(t,n,e))}}function hn(e,t){return function(n,i,s){return typeof i==\"function\"&&s===r&&Xn(n)?e(n,i):t(n,on(i,s,3))}}function pn(e,t,n,i,s,o,u){var a=-1,f=e.length,l=t.length,c=!0;if(f!=l&&!(s&&l>f))return!1;while(c&&++a<f){var h=e[a],p=t[a];c=r,i&&(c=s?i(p,h,a):i(h,p,a));if(c===r)if(s){var d=l;while(d--){p=t[d],c=h&&h===p||n(h,p,i,s,o,u);if(c)break}}else c=h&&h===p||n(h,p,i,s,o,u)}return!!c}function dn(e,t,n){switch(n){case a:case f:return+e==+t;case l:return e.name==t.name&&e.message==t.message;case p:return e!=+e?t!=+t:e==0?1/e==1/t:e==+t;case v:case g:return e==t+\"\"}return!1}function vn(e,t,n,i,s,o,u){var a=rr(e),f=a.length,l=rr(t),c=l.length;if(f!=c&&!s)return!1;var h=s,p=-1;while(++p<f){var d=a[p],v=s?d in t:nt.call(t,d);if(v){var m=e[d],g=t[d];v=r,i&&(v=s?i(g,m,d):i(m,g,d)),v===r&&(v=m&&m===g||n(m,g,i,s,o,u))}if(!v)return!1;h||(h=d==\"constructor\")}if(!h){var y=e.constructor,b=t.constructor;if(y!=b&&\"constructor\"in e&&\"constructor\"in t&&!(typeof y==\"function\"&&y instanceof y&&typeof b==\"function\"&&b instanceof b))return!1}return!0}function mn(e,t,n){var r=Ct.callback||ar;return r=r===ar?jt:r,n?r(e,t,n):r}function gn(e,t,n){var r=Ct.indexOf||Dn;return r=r===Dn?J:r,e?r(e,t,n):r}function wn(e){var t=e.length,n=new e.constructor(t);return t&&typeof e[0]==\"string\"&&nt.call(e,\"index\")&&(n.index=e.index,n.input=e.input),n}function En(e){var t=e.constructor;return typeof t==\"function\"&&t instanceof t||(t=Object),new t}function Sn(e,t,n){var r=e.constructor;switch(t){case b:return un(e);case a:case f:return new r(+e);case w:case E:case S:case x:case T:case N:case C:case k:case L:var i=e.buffer;return new r(n?un(i):i,e.byteOffset,e.length);case p:case g:return new r(e);case v:var s=new r(e.source,H.exec(e));s.lastIndex=e.lastIndex}return s}function xn(e,t){return e=+e,t=t==null?Nt:t,e>-1&&e%1==0&&e<t}function Tn(e,t,n){if(!Jn(n))return!1;var r=typeof t;if(r==\"number\")var i=yn(n),s=Cn(i)&&xn(t,i);else s=r==\"string\"&&t in n;if(s){var o=n[t];return e===e?e===o:o!==o}return!1}function Nn(e,t){var n=typeof e;if(n==\"string\"&&O.test(e)||n==\"number\")return!0;if(Xn(e))return!1;var r=!A.test(e);return r||t!=null&&e in On(t)}function Cn(e){return typeof e==\"number\"&&e>-1&&e%1==0&&e<=Nt}function kn(e){return e===e&&(e===0?1/e>0:!Jn(e))}function Ln(e){var t,n=Ct.support;if(!Y(e)||rt.call(e)!=d||!nt.call(e,\"constructor\")&&(t=e.constructor,typeof t==\"function\"&&!(t instanceof t)))return!1;var i;return Ut(e,function(e,t){i=t}),i===r||nt.call(e,i)}function An(e){var t=ir(e),n=t.length,r=n&&e.length,i=Ct.support,s=r&&Cn(r)&&(Xn(e)||i.nonEnumArgs&&Wn(e)),o=-1,u=[];while(++o<n){var a=t[o];(s&&xn(a,r)||nt.call(e,a))&&u.push(a)}return u}function On(e){return Jn(e)?e:Object(e)}function Mn(e){if(Xn(e))return e;var t=[];return Q(e).replace(M,function(e,n,r,i){t.push(r?i.replace(P,\"$1\"):n||e)}),t}function Dn(e,t,n){var r=e?e.length:0;if(!r)return-1;if(typeof n==\"number\")n=n<0?yt(r+n,0):n;else if(n){var i=rn(e,t),s=e[i];return(t===t?t===s:s!==s)?i:-1}return J(e,t,n||0)}function Pn(e){var t=e?e.length:0;return t?e[t-1]:r}function Hn(e,t,n){var r=e?e.length:0;return r?(n&&typeof n!=\"number\"&&Tn(e,t,n)&&(t=0,n=r),en(e,t,n)):[]}function Bn(e){var t=-1,n=(e&&e.length&&_t(Mt(e,yn)))>>>0,r=Array(n);while(++t<n)r[t]=Mt(e,Yt(t));return r}function In(e,t,n,r){var i=e?yn(e):0;return Cn(i)||(e=or(e),i=e.length),i?(typeof n!=\"number\"||r&&Tn(t,n,r)?n=0:n=n<0?yt(i+n,0):n||0,typeof e==\"string\"||!Xn(e)&&Yn(e)?n<i&&e.indexOf(t,n)>-1:gn(e,t,n)>-1):!1}function qn(e,t,n){var r=Xn(e)?Ot:qt;return t=mn(t,n,3),r(e,function(e,n,r){return!t(e,n,r)})}function Rn(e,t,n){var i=Xn(e)?Dt:tn;n&&Tn(e,t,n)&&(t=null);if(typeof t!=\"function\"||n!==r)t=mn(t,n,3);return i(e,t)}function Un(e,t){if(typeof e!=\"function\")throw new TypeError(s);return t=yt(t===r?e.length-1:+t||0,0),function(){var n=arguments,r=-1,i=yt(n.length-t,0),s=Array(i);while(++r<i)s[r]=n[t+r];switch(t){case 0:return e.call(this,s);case 1:return e.call(this,n[0],s);case 2:return e.call(this,n[0],n[1],s)}var o=Array(t+1);r=-1;while(++r<t)o[r]=n[r];return o[t]=s,e.apply(this,o)}}function zn(e,t,n,r){return t&&typeof t!=\"boolean\"&&Tn(e,t,n)?t=!1:typeof t==\"function\"&&(r=n,n=t,t=!1),n=typeof n==\"function\"&&on(n,r,1),Ft(e,t,n)}function Wn(e){var t=Y(e)?e.length:r;return Cn(t)&&rt.call(e)==o}function Vn(e){if(e==null)return!0;var t=yn(e);return Cn(t)&&(Xn(e)||Yn(e)||Wn(e)||Y(e)&&$n(e.splice))?!t:!rr(e).length}function Jn(e){var t=typeof e;return t==\"function\"||!!e&&t==\"object\"}function Kn(e){return e==null?!1:rt.call(e)==c?it.test(tt.call(e)):Y(e)&&B.test(e)}function Qn(e){return typeof e==\"number\"||Y(e)&&rt.call(e)==p}function Yn(e){return typeof e==\"string\"||Y(e)&&rt.call(e)==g}function Zn(e){return Y(e)&&Cn(e.length)&&!!j[rt.call(e)]}function er(e){return Bt(e,ir(e))}function nr(e,t){if(e==null)return!1;var n=nt.call(e,t);return!n&&!Nn(t)&&(t=Mn(t),e=t.length==1?e:Wt(e,en(t,0,-1)),t=Pn(t),n=e!=null&&nt.call(e,t)),n}function ir(e){if(e==null)return[];Jn(e)||(e=Object(e));var t=e.length;t=t&&Cn(t)&&(Xn(e)||kt.nonEnumArgs&&Wn(e))&&t||0;var n=e.constructor,r=-1,i=typeof n==\"function\"&&n.prototype===e,s=Array(t),o=t>0;while(++r<t)s[r]=r+\"\";for(var u in e)(!o||!xn(u,t))&&(u!=\"constructor\"||!i&&!!nt.call(e,u))&&s.push(u);return s}function or(e){return nn(e,rr(e))}function ur(e){return e=Q(e),e&&D.test(e)?e.replace(_,\"\\\\$&\"):e}function ar(e,t,n){return n&&Tn(e,t,n)&&(t=null),jt(e,t)}function fr(e){return function(){return e}}function lr(e){return e}function cr(e){return Nn(e)?Yt(e):Zt(e)}var r,i=\"3.7.0\",s=\"Expected a function\",o=\"[object Arguments]\",u=\"[object Array]\",a=\"[object Boolean]\",f=\"[object Date]\",l=\"[object Error]\",c=\"[object Function]\",h=\"[object Map]\",p=\"[object Number]\",d=\"[object Object]\",v=\"[object RegExp]\",m=\"[object Set]\",g=\"[object String]\",y=\"[object WeakMap]\",b=\"[object ArrayBuffer]\",w=\"[object Float32Array]\",E=\"[object Float64Array]\",S=\"[object Int8Array]\",x=\"[object Int16Array]\",T=\"[object Int32Array]\",N=\"[object Uint8Array]\",C=\"[object Uint8ClampedArray]\",k=\"[object Uint16Array]\",L=\"[object Uint32Array]\",A=/\\.|\\[(?:[^[\\]]+|([\"'])(?:(?!\\1)[^\\n\\\\]|\\\\.)*?)\\1\\]/,O=/^\\w*$/,M=/[^.[\\]]+|\\[(?:(-?\\d+(?:\\.\\d+)?)|([\"'])((?:(?!\\2)[^\\n\\\\]|\\\\.)*?)\\2)\\]/g,_=/[.*+?^${}()|[\\]\\/\\\\]/g,D=RegExp(_.source),P=/\\\\(\\\\)?/g,H=/\\w*$/,B=/^\\[object .+?Constructor\\]$/,j={};j[w]=j[E]=j[S]=j[x]=j[T]=j[N]=j[C]=j[k]=j[L]=!0,j[o]=j[u]=j[b]=j[a]=j[f]=j[l]=j[c]=j[h]=j[p]=j[d]=j[v]=j[m]=j[g]=j[y]=!1;var F={};F[o]=F[u]=F[b]=F[a]=F[f]=F[w]=F[E]=F[S]=F[x]=F[T]=F[p]=F[d]=F[v]=F[g]=F[N]=F[C]=F[k]=F[L]=!0,F[l]=F[c]=F[h]=F[m]=F[y]=!1;var I={\"function\":!0,object:!0},q=I[typeof n]&&n&&!n.nodeType&&n,R=I[typeof t]&&t&&!t.nodeType&&t,U=q&&R&&typeof e==\"object\"&&e&&e.Object&&e,z=I[typeof self]&&self&&self.Object&&self,W=I[typeof window]&&window&&window.Object&&window,X=R&&R.exports===q&&q,V=U||W!==(this&&this.window)&&W||z||this,Z=Array.prototype,et=Object.prototype,tt=Function.prototype.toString,nt=et.hasOwnProperty,rt=et.toString,it=RegExp(\"^\"+ur(rt).replace(/toString|(function).*?(?=\\\\\\()| for .+?(?=\\\\\\])/g,\"$1.*?\")+\"$\"),st=Kn(st=V.ArrayBuffer)&&st,ot=Kn(ot=st&&(new st(0)).slice)&&ot,ut=Math.floor,at=Kn(at=Object.getOwnPropertySymbols)&&at,ft=Kn(ft=Object.getPrototypeOf)&&ft,lt=Z.push,ct=Kn(Object.preventExtensions=Object.preventExtensions)&&ct,ht=et.propertyIsEnumerable,pt=Kn(pt=V.Uint8Array)&&pt,dt=function(){try{var e=Kn(e=V.Float64Array)&&e,t=new e(new st(10),0,1)&&e}catch(n){}return t}(),vt=function(){var e={1:0},t=ct&&Kn(t=Object.assign)&&t;try{t(ct(e),\"xo\")}catch(n){}return!e[1]&&t}(),mt=Kn(mt=Array.isArray)&&mt,gt=Kn(gt=Object.keys)&&gt,yt=Math.max,bt=Math.min,wt=Number.NEGATIVE_INFINITY,Et=Math.pow(2,32)-1,St=Et-1,xt=Et>>>1,Tt=dt?dt.BYTES_PER_ELEMENT:0,Nt=Math.pow(2,53)-1,kt=Ct.support={};(function(e){var t=function(){this.x=e},n={0:e,length:e},r=[];t.prototype={valueOf:e,y:e};for(var i in new t)r.push(i);kt.funcDecomp=/\\bthis\\b/.test(function(){return this}),kt.funcNames=typeof Function.name==\"string\";try{kt.nonEnumArgs=!ht.call(arguments,1)}catch(s){kt.nonEnumArgs=!0}})(1,0);var Ht=vt||function(e,t){return t==null?e:Bt(t,bn(t),Bt(t,rr(t),e))},It=fn(zt),Rt=ln();ot||(un=!st||!pt?fr(null):function(e){var t=e.byteLength,n=dt?ut(t/Tt):0,r=n*Tt,i=new st(t);if(n){var s=new dt(i,0,n);s.set(new dt(e,0,n))}return t!=r&&(s=new pt(i,r),s.set(new pt(e,r))),i});var yn=Yt(\"length\"),bn=at?function(e){return at(On(e))}:fr([]),_n=cn(!0),jn=Un(Bn),Fn=hn(At,It),Xn=mt||function(e){return Y(e)&&Cn(e.length)&&rt.call(e)==u},$n=K(/x/)||pt&&!K(pt)?function(e){return rt.call(e)==c}:K,Gn=ft?function(e){if(!e||rt.call(e)!=d)return!1;var t=e.valueOf,n=Kn(t)&&(n=ft(t))&&ft(n);return n?e==n||ft(e)==n:Ln(e)}:Ln,tr=an(function(e,t,n){return n?Pt(e,t,n):Ht(e,t)}),rr=gt?function(e){if(e)var t=e.constructor,n=e.length;return typeof t==\"function\"&&t.prototype===e||typeof e!=\"function\"&&Cn(n)?An(e):Jn(e)?gt(e):[]}:An,sr=an(Qt);Ct.assign=tr,Ct.callback=ar,Ct.constant=fr,Ct.forEach=Fn,Ct.keys=rr,Ct.keysIn=ir,Ct.merge=sr,Ct.property=cr,Ct.reject=qn,Ct.restParam=Un,Ct.slice=Hn,Ct.toPlainObject=er,Ct.unzip=Bn,Ct.values=or,Ct.zip=jn,Ct.each=Fn,Ct.extend=tr,Ct.iteratee=ar,Ct.clone=zn,Ct.escapeRegExp=ur,Ct.findLastIndex=_n,Ct.has=nr,Ct.identity=lr,Ct.includes=In,Ct.indexOf=Dn,Ct.isArguments=Wn,Ct.isArray=Xn,Ct.isEmpty=Vn,Ct.isFunction=$n,Ct.isNative=Kn,Ct.isNumber=Qn,Ct.isObject=Jn,Ct.isPlainObject=Gn,Ct.isString=Yn,Ct.isTypedArray=Zn,Ct.last=Pn,Ct.some=Rn,Ct.any=Rn,Ct.contains=In,Ct.include=In,Ct.VERSION=i,q&&R?X?(R.exports=Ct)._=Ct:q._=Ct:V._=Ct}).call(this)}).call(this,typeof global!=\"undefined\"?global:typeof self!=\"undefined\"?self:typeof window!=\"undefined\"?window:{})},{}],\"/node_modules/jshint/src/jshint.js\":[function(e,t,n){var r=e(\"../lodash\"),i=e(\"events\"),s=e(\"./vars.js\"),o=e(\"./messages.js\"),u=e(\"./lex.js\").Lexer,a=e(\"./reg.js\"),f=e(\"./state.js\").state,l=e(\"./style.js\"),c=e(\"./options.js\"),h=e(\"./scope-manager.js\"),p=function(){\"use strict\";function k(e,t){return e=e.trim(),/^[+-]W\\d{3}$/g.test(e)?!0:c.validNames.indexOf(e)===-1&&t.type!==\"jslint\"&&!r.has(c.removed,e)?(q(\"E001\",t,e),!1):!0}function L(e){return Object.prototype.toString.call(e)===\"[object String]\"}function A(e,t){return e?!e.identifier||e.value!==t?!1:!0:!1}function O(e){if(!e.reserved)return!1;var t=e.meta;if(t&&t.isFutureReservedWord&&f.inES5()){if(!t.es5)return!1;if(t.strictOnly&&!f.option.strict&&!f.isStrict())return!1;if(e.isProperty)return!1}return!0}function M(e,t){return e.replace(/\\{([^{}]*)\\}/g,function(e,n){var r=t[n];return typeof r==\"string\"||typeof r==\"number\"?r:e})}function D(e,t){Object.keys(t).forEach(function(n){if(r.has(p.blacklist,n))return;e[n]=t[n]})}function P(){if(f.option.enforceall){for(var e in c.bool.enforcing)f.option[e]===undefined&&!c.noenforceall[e]&&(f.option[e]=!0);for(var t in c.bool.relaxing)f.option[t]===undefined&&(f.option[t]=!1)}}function H(){P(),!f.option.esversion&&!f.option.moz&&(f.option.es3?f.option.esversion=3:f.option.esnext?f.option.esversion=6:f.option.esversion=5),f.inES5()&&D(S,s.ecmaIdentifiers[5]),f.inES6()&&D(S,s.ecmaIdentifiers[6]),f.option.module&&(f.option.strict===!0&&(f.option.strict=\"global\"),f.inES6()||F(\"W134\",f.tokens.next,\"module\",6)),f.option.couch&&D(S,s.couch),f.option.qunit&&D(S,s.qunit),f.option.rhino&&D(S,s.rhino),f.option.shelljs&&(D(S,s.shelljs),D(S,s.node)),f.option.typed&&D(S,s.typed),f.option.phantom&&(D(S,s.phantom),f.option.strict===!0&&(f.option.strict=\"global\")),f.option.prototypejs&&D(S,s.prototypejs),f.option.node&&(D(S,s.node),D(S,s.typed),f.option.strict===!0&&(f.option.strict=\"global\")),f.option.devel&&D(S,s.devel),f.option.dojo&&D(S,s.dojo),f.option.browser&&(D(S,s.browser),D(S,s.typed)),f.option.browserify&&(D(S,s.browser),D(S,s.typed),D(S,s.browserify),f.option.strict===!0&&(f.option.strict=\"global\")),f.option.nonstandard&&D(S,s.nonstandard),f.option.jasmine&&D(S,s.jasmine),f.option.jquery&&D(S,s.jquery),f.option.mootools&&D(S,s.mootools),f.option.worker&&D(S,s.worker),f.option.wsh&&D(S,s.wsh),f.option.globalstrict&&f.option.strict!==!1&&(f.option.strict=\"global\"),f.option.yui&&D(S,s.yui),f.option.mocha&&D(S,s.mocha)}function B(e,t,n){var r=Math.floor(t/f.lines.length*100),i=o.errors[e].desc;throw{name:\"JSHintError\",line:t,character:n,message:i+\" (\"+r+\"% scanned).\",raw:i,code:e}}function j(){var e=f.ignoredLines;if(r.isEmpty(e))return;p.errors=r.reject(p.errors,function(t){return e[t.line]})}function F(e,t,n,r,i,s){var u,a,l,c;if(/^W\\d{3}$/.test(e)){if(f.ignored[e])return;c=o.warnings[e]}else/E\\d{3}/.test(e)?c=o.errors[e]:/I\\d{3}/.test(e)&&(c=o.info[e]);return t=t||f.tokens.next||{},t.id===\"(end)\"&&(t=f.tokens.curr),a=t.line||0,u=t.from||0,l={id:\"(error)\",raw:c.desc,code:c.code,evidence:f.lines[a-1]||\"\",line:a,character:u,scope:p.scope,a:n,b:r,c:i,d:s},l.reason=M(c.desc,l),p.errors.push(l),j(),p.errors.length>=f.option.maxerr&&B(\"E043\",a,u),l}function I(e,t,n,r,i,s,o){return F(e,{line:t,from:n},r,i,s,o)}function q(e,t,n,r,i,s){F(e,t,n,r,i,s)}function R(e,t,n,r,i,s,o){return q(e,{line:t,from:n},r,i,s,o)}function U(e,t){var n;return n={id:\"(internal)\",elem:e,value:t},p.internals.push(n),n}function z(){var e=f.tokens.next,t=e.body.match(/(-\\s+)?[^\\s,:]+(?:\\s*:\\s*(-\\s+)?[^\\s,]+)?/g)||[],i={};if(e.type===\"globals\"){t.forEach(function(n,r){n=n.split(\":\");var s=(n[0]||\"\").trim(),o=(n[1]||\"\").trim();if(s===\"-\"||!s.length){if(r>0&&r===t.length-1)return;q(\"E002\",e);return}s.charAt(0)===\"-\"?(s=s.slice(1),o=!1,p.blacklist[s]=s,delete S[s]):i[s]=o===\"true\"}),D(S,i);for(var s in i)r.has(i,s)&&(n[s]=e)}e.type===\"exported\"&&t.forEach(function(n,r){if(!n.length){if(r>0&&r===t.length-1)return;q(\"E002\",e);return}f.funct[\"(scope)\"].addExported(n)}),e.type===\"members\"&&(E=E||{},t.forEach(function(e){var t=e.charAt(0),n=e.charAt(e.length-1);t===n&&(t==='\"'||t===\"'\")&&(e=e.substr(1,e.length-2).replace('\\\\\"','\"')),E[e]=!1}));var o=[\"maxstatements\",\"maxparams\",\"maxdepth\",\"maxcomplexity\",\"maxerr\",\"maxlen\",\"indent\"];if(e.type===\"jshint\"||e.type===\"jslint\")t.forEach(function(t){t=t.split(\":\");var n=(t[0]||\"\").trim(),i=(t[1]||\"\").trim();if(!k(n,e))return;if(o.indexOf(n)>=0){if(i!==\"false\"){i=+i;if(typeof i!=\"number\"||!isFinite(i)||i<=0||Math.floor(i)!==i){q(\"E032\",e,t[1].trim());return}f.option[n]=i}else f.option[n]=n===\"indent\"?4:!1;return}if(n===\"validthis\"){if(f.funct[\"(global)\"])return void q(\"E009\");if(i!==\"true\"&&i!==\"false\")return void q(\"E002\",e);f.option.validthis=i===\"true\";return}if(n===\"quotmark\"){switch(i){case\"true\":case\"false\":f.option.quotmark=i===\"true\";break;case\"double\":case\"single\":f.option.quotmark=i;break;default:q(\"E002\",e)}return}if(n===\"shadow\"){switch(i){case\"true\":f.option.shadow=!0;break;case\"outer\":f.option.shadow=\"outer\";break;case\"false\":case\"inner\":f.option.shadow=\"inner\";break;default:q(\"E002\",e)}return}if(n===\"unused\"){switch(i){case\"true\":f.option.unused=!0;break;case\"false\":f.option.unused=!1;break;case\"vars\":case\"strict\":f.option.unused=i;break;default:q(\"E002\",e)}return}if(n===\"latedef\"){switch(i){case\"true\":f.option.latedef=!0;break;case\"false\":f.option.latedef=!1;break;case\"nofunc\":f.option.latedef=\"nofunc\";break;default:q(\"E002\",e)}return}if(n===\"ignore\"){switch(i){case\"line\":f.ignoredLines[e.line]=!0,j();break;default:q(\"E002\",e)}return}if(n===\"strict\"){switch(i){case\"true\":f.option.strict=!0;break;case\"false\":f.option.strict=!1;break;case\"func\":case\"global\":case\"implied\":f.option.strict=i;break;default:q(\"E002\",e)}return}n===\"module\"&&(zt(f.funct)||q(\"E055\",f.tokens.next,\"module\"));var s={es3:3,es5:5,esnext:6};if(r.has(s,n)){switch(i){case\"true\":f.option.moz=!1,f.option.esversion=s[n];break;case\"false\":f.option.moz||(f.option.esversion=5);break;default:q(\"E002\",e)}return}if(n===\"esversion\"){switch(i){case\"5\":f.inES5(!0)&&F(\"I003\");case\"3\":case\"6\":f.option.moz=!1,f.option.esversion=+i;break;case\"2015\":f.option.moz=!1,f.option.esversion=6;break;default:q(\"E002\",e)}zt(f.funct)||q(\"E055\",f.tokens.next,\"esversion\");return}var u=/^([+-])(W\\d{3})$/g.exec(n);if(u){f.ignored[u[2]]=u[1]===\"-\";return}var a;if(i===\"true\"||i===\"false\"){e.type===\"jslint\"?(a=c.renamed[n]||n,f.option[a]=i===\"true\",c.inverted[a]!==undefined&&(f.option[a]=!f.option[a])):f.option[n]=i===\"true\",n===\"newcap\"&&(f.option[\"(explicitNewcap)\"]=!0);return}q(\"E002\",e)}),H()}function W(e){var t=e||0,n=y.length,r;if(t<n)return y[t];while(n<=t)r=y[n],r||(r=y[n]=b.token()),n+=1;return!r&&f.tokens.next.id===\"(end)\"?f.tokens.next:r}function X(){var e=0,t;do t=W(e++);while(t.id===\"(endline)\");return t}function V(e,t){switch(f.tokens.curr.id){case\"(number)\":f.tokens.next.id===\".\"&&F(\"W005\",f.tokens.curr);break;case\"-\":(f.tokens.next.id===\"-\"||f.tokens.next.id===\"--\")&&F(\"W006\");break;case\"+\":(f.tokens.next.id===\"+\"||f.tokens.next.id===\"++\")&&F(\"W007\")}e&&f.tokens.next.id!==e&&(t?f.tokens.next.id===\"(end)\"?q(\"E019\",t,t.id):q(\"E020\",f.tokens.next,e,t.id,t.line,f.tokens.next.value):(f.tokens.next.type!==\"(identifier)\"||f.tokens.next.value!==e)&&F(\"W116\",f.tokens.next,e,f.tokens.next.value)),f.tokens.prev=f.tokens.curr,f.tokens.curr=f.tokens.next;for(;;){f.tokens.next=y.shift()||b.token(),f.tokens.next||B(\"E041\",f.tokens.curr.line);if(f.tokens.next.id===\"(end)\"||f.tokens.next.id===\"(error)\")return;f.tokens.next.check&&f.tokens.next.check();if(f.tokens.next.isSpecial)f.tokens.next.type===\"falls through\"?f.tokens.curr.caseFallsThrough=!0:z();else if(f.tokens.next.id!==\"(endline)\")break}}function $(e){return e.infix||!e.identifier&&!e.template&&!!e.led}function J(){var e=f.tokens.curr,t=f.tokens.next;return t.id===\";\"||t.id===\"}\"||t.id===\":\"?!0:$(t)===$(e)||e.id===\"yield\"&&f.inMoz()?e.line!==G(t):!1}function K(e){return!e.left&&e.arity!==\"unary\"}function Q(e,t){var n,i=!1,s=!1,o=!1;f.nameStack.push(),!t&&f.tokens.next.value===\"let\"&&W(0).value===\"(\"&&(f.inMoz()||F(\"W118\",f.tokens.next,\"let expressions\"),o=!0,f.funct[\"(scope)\"].stack(),V(\"let\"),V(\"(\"),f.tokens.prev.fud(),V(\")\")),f.tokens.next.id===\"(end)\"&&q(\"E006\",f.tokens.curr);var u=f.option.asi&&f.tokens.prev.line!==G(f.tokens.curr)&&r.contains([\"]\",\")\"],f.tokens.prev.id)&&r.contains([\"[\",\"(\"],f.tokens.curr.id);u&&F(\"W014\",f.tokens.curr,f.tokens.curr.id),V(),t&&(f.funct[\"(verb)\"]=f.tokens.curr.value,f.tokens.curr.beginsStmt=!0);if(t===!0&&f.tokens.curr.fud)n=f.tokens.curr.fud();else{f.tokens.curr.nud?n=f.tokens.curr.nud():q(\"E030\",f.tokens.curr,f.tokens.curr.id);while((e<f.tokens.next.lbp||f.tokens.next.type===\"(template)\")&&!J())i=f.tokens.curr.value===\"Array\",s=f.tokens.curr.value===\"Object\",n&&(n.value||n.first&&n.first.value)&&(n.value!==\"new\"||n.first&&n.first.value&&n.first.value===\".\")&&(i=!1,n.value!==f.tokens.curr.value&&(s=!1)),V(),i&&f.tokens.curr.id===\"(\"&&f.tokens.next.id===\")\"&&F(\"W009\",f.tokens.curr),s&&f.tokens.curr.id===\"(\"&&f.tokens.next.id===\")\"&&F(\"W010\",f.tokens.curr),n&&f.tokens.curr.led?n=f.tokens.curr.led(n):q(\"E033\",f.tokens.curr,f.tokens.curr.id)}return o&&f.funct[\"(scope)\"].unstack(),f.nameStack.pop(),n}function G(e){return e.startLine||e.line}function Y(e,t){e=e||f.tokens.curr,t=t||f.tokens.next,!f.option.laxbreak&&e.line!==G(t)&&F(\"W014\",t,t.value)}function Z(e){e=e||f.tokens.curr,e.line!==G(f.tokens.next)&&F(\"E022\",e,e.value)}function et(e,t){e.line!==G(t)&&(f.option.laxcomma||(tt.first&&(F(\"I001\"),tt.first=!1),F(\"W014\",e,t.value)))}function tt(e){e=e||{},e.peek?et(f.tokens.prev,f.tokens.curr):(et(f.tokens.curr,f.tokens.next),V(\",\"));if(f.tokens.next.identifier&&(!e.property||!f.inES5()))switch(f.tokens.next.value){case\"break\":case\"case\":case\"catch\":case\"continue\":case\"default\":case\"do\":case\"else\":case\"finally\":case\"for\":case\"if\":case\"in\":case\"instanceof\":case\"return\":case\"switch\":case\"throw\":case\"try\":case\"var\":case\"let\":case\"while\":case\"with\":return q(\"E024\",f.tokens.next,f.tokens.next.value),!1}if(f.tokens.next.type===\"(punctuator)\")switch(f.tokens.next.value){case\"}\":case\"]\":case\",\":if(e.allowTrailing)return!0;case\")\":return q(\"E024\",f.tokens.next,f.tokens.next.value),!1}return!0}function nt(e,t){var n=f.syntax[e];if(!n||typeof n!=\"object\")f.syntax[e]=n={id:e,lbp:t,value:e};return n}function rt(e){var t=nt(e,0);return t.delim=!0,t}function it(e,t){var n=rt(e);return n.identifier=n.reserved=!0,n.fud=t,n}function st(e,t){var n=it(e,t);return n.block=!0,n}function ot(e){var t=e.id.charAt(0);if(t>=\"a\"&&t<=\"z\"||t>=\"A\"&&t<=\"Z\")e.identifier=e.reserved=!0;return e}function ut(e,t){var n=nt(e,150);return ot(n),n.nud=typeof t==\"function\"?t:function(){this.arity=\"unary\",this.right=Q(150);if(this.id===\"++\"||this.id===\"--\")f.option.plusplus?F(\"W016\",this,this.id):this.right&&(!this.right.identifier||O(this.right))&&this.right.id!==\".\"&&this.right.id!==\"[\"&&F(\"W017\",this),this.right&&this.right.isMetaProperty?q(\"E031\",this):this.right&&this.right.identifier&&f.funct[\"(scope)\"].block.modify(this.right.value,this);return this},n}function at(e,t){var n=rt(e);return n.type=e,n.nud=t,n}function ft(e,t){var n=at(e,t);return n.identifier=!0,n.reserved=!0,n}function lt(e,t){var n=at(e,t&&t.nud||function(){return this});return t=t||{},t.isFutureReservedWord=!0,n.value=e,n.identifier=!0,n.reserved=!0,n.meta=t,n}function ct(e,t){return ft(e,function(){return typeof t==\"function\"&&t(this),this})}function ht(e,t,n,r){var i=nt(e,n);return ot(i),i.infix=!0,i.led=function(i){return r||Y(f.tokens.prev,f.tokens.curr),(e===\"in\"||e===\"instanceof\")&&i.id===\"!\"&&F(\"W018\",i,\"!\"),typeof t==\"function\"?t(i,this):(this.left=i,this.right=Q(n),this)},i}function pt(e){var t=nt(e,42);return t.led=function(e){return Y(f.tokens.prev,f.tokens.curr),this.left=e,this.right=Xt({type:\"arrow\",loneArg:e}),this},t}function dt(e,t){var n=nt(e,100);return n.led=function(e){Y(f.tokens.prev,f.tokens.curr),this.left=e;var n=this.right=Q(100);return A(e,\"NaN\")||A(n,\"NaN\")?F(\"W019\",this):t&&t.apply(this,[e,n]),(!e||!n)&&B(\"E041\",f.tokens.curr.line),e.id===\"!\"&&F(\"W018\",e,\"!\"),n.id===\"!\"&&F(\"W018\",n,\"!\"),this},n}function vt(e){return e&&(e.type===\"(number)\"&&+e.value===0||e.type===\"(string)\"&&e.value===\"\"||e.type===\"null\"&&!f.option.eqnull||e.type===\"true\"||e.type===\"false\"||e.type===\"undefined\")}function gt(e,t,n){var i;return n.option.notypeof?!1:!e||!t?!1:(i=n.inES6()?mt.es6:mt.es3,t.type===\"(identifier)\"&&t.value===\"typeof\"&&e.type===\"(string)\"?!r.contains(i,e.value):!1)}function yt(e,t){var n=!1;return e.type===\"this\"&&t.funct[\"(context)\"]===null?n=!0:e.type===\"(identifier)\"&&(t.option.node&&e.value===\"global\"?n=!0:t.option.browser&&(e.value===\"window\"||e.value===\"document\")&&(n=!0)),n}function bt(e){function n(e){if(typeof e!=\"object\")return;return e.right===\"prototype\"?e:n(e.left)}function r(e){while(!e.identifier&&typeof e.left==\"object\")e=e.left;if(e.identifier&&t.indexOf(e.value)>=0)return e.value}var t=[\"Array\",\"ArrayBuffer\",\"Boolean\",\"Collator\",\"DataView\",\"Date\",\"DateTimeFormat\",\"Error\",\"EvalError\",\"Float32Array\",\"Float64Array\",\"Function\",\"Infinity\",\"Intl\",\"Int16Array\",\"Int32Array\",\"Int8Array\",\"Iterator\",\"Number\",\"NumberFormat\",\"Object\",\"RangeError\",\"ReferenceError\",\"RegExp\",\"StopIteration\",\"String\",\"SyntaxError\",\"TypeError\",\"Uint16Array\",\"Uint32Array\",\"Uint8Array\",\"Uint8ClampedArray\",\"URIError\"],i=n(e);if(i)return r(i)}function wt(e,t,n){var r=n&&n.allowDestructuring;t=t||e;if(f.option.freeze){var i=bt(e);i&&F(\"W121\",e,i)}return e.identifier&&!e.isMetaProperty&&f.funct[\"(scope)\"].block.reassign(e.value,e),e.id===\".\"?((!e.left||e.left.value===\"arguments\"&&!f.isStrict())&&F(\"E031\",t),f.nameStack.set(f.tokens.prev),!0):e.id===\"{\"||e.id===\"[\"?(r&&f.tokens.curr.left.destructAssign?f.tokens.curr.left.destructAssign.forEach(function(e){e.id&&f.funct[\"(scope)\"].block.modify(e.id,e.token)}):e.id===\"{\"||!e.left?F(\"E031\",t):e.left.value===\"arguments\"&&!f.isStrict()&&F(\"E031\",t),e.id===\"[\"&&f.nameStack.set(e.right),!0):e.isMetaProperty?(q(\"E031\",t),!0):e.identifier&&!O(e)?(f.funct[\"(scope)\"].labeltype(e.value)===\"exception\"&&F(\"W022\",e),f.nameStack.set(e),!0):(e===f.syntax[\"function\"]&&F(\"W023\",f.tokens.curr),!1)}function Et(e,t,n){var r=ht(e,typeof t==\"function\"?t:function(e,t){t.left=e;if(e&&wt(e,t,{allowDestructuring:!0}))return t.right=Q(10),t;q(\"E031\",t)},n);return r.exps=!0,r.assign=!0,r}function St(e,t,n){var r=nt(e,n);return ot(r),r.led=typeof t==\"function\"?t:function(e){return f.option.bitwise&&F(\"W016\",this,this.id),this.left=e,this.right=Q(n),this},r}function xt(e){return Et(e,function(e,t){f.option.bitwise&&F(\"W016\",t,t.id);if(e&&wt(e,t))return t.right=Q(10),t;q(\"E031\",t)},20)}function Tt(e){var t=nt(e,150);return t.led=function(e){return f.option.plusplus?F(\"W016\",this,this.id):(!e.identifier||O(e))&&e.id!==\".\"&&e.id!==\"[\"&&F(\"W017\",this),e.isMetaProperty?q(\"E031\",this):e&&e.identifier&&f.funct[\"(scope)\"].block.modify(e.value,e),this.left=e,this},t}function Nt(e,t,n){if(!f.tokens.next.identifier)return;n||V();var r=f.tokens.curr,i=f.tokens.curr.value;return O(r)?t&&f.inES5()?i:e&&i===\"undefined\"?i:(F(\"W024\",f.tokens.curr,f.tokens.curr.id),i):i}function Ct(e,t){var n=Nt(e,t,!1);if(n)return n;if(f.tokens.next.value===\"...\"){f.inES6(!0)||F(\"W119\",f.tokens.next,\"spread/rest operator\",\"6\"),V();if(pn(f.tokens.next,\"...\")){F(\"E024\",f.tokens.next,\"...\");while(pn(f.tokens.next,\"...\"))V()}if(!f.tokens.next.identifier){F(\"E024\",f.tokens.curr,\"...\");return}return Ct(e,t)}q(\"E030\",f.tokens.next,f.tokens.next.value),f.tokens.next.id!==\";\"&&V()}function kt(e){var t=0,n;if(f.tokens.next.id!==\";\"||e.inBracelessBlock)return;for(;;){do n=W(t),t+=1;while(n.id!==\"(end)\"&&n.id===\"(comment)\");if(n.reach)return;if(n.id!==\"(endline)\"){if(n.id===\"function\"){f.option.latedef===!0&&F(\"W026\",n);break}F(\"W027\",n,n.value,e.value);break}}}function Lt(){if(f.tokens.next.id!==\";\"){if(f.tokens.next.isUnclosed)return V();var e=G(f.tokens.next)===f.tokens.curr.line&&f.tokens.next.id!==\"(end)\",t=pn(f.tokens.next,\"}\");e&&!t?R(\"E058\",f.tokens.curr.line,f.tokens.curr.character):f.option.asi||(t&&!f.option.lastsemic||!e)&&I(\"W033\",f.tokens.curr.line,f.tokens.curr.character)}else V(\";\")}function At(){var e=g,t,n=f.tokens.next,r=!1;if(n.id===\";\"){V(\";\");return}var i=O(n);i&&n.meta&&n.meta.isFutureReservedWord&&W().id===\":\"&&(F(\"W024\",n,n.id),i=!1),n.identifier&&!i&&W().id===\":\"&&(V(),V(\":\"),r=!0,f.funct[\"(scope)\"].stack(),f.funct[\"(scope)\"].block.addBreakLabel(n.value,{token:f.tokens.curr}),!f.tokens.next.labelled&&f.tokens.next.value!==\"{\"&&F(\"W028\",f.tokens.next,n.value,f.tokens.next.value),f.tokens.next.label=n.value,n=f.tokens.next);if(n.id===\"{\"){var s=f.funct[\"(verb)\"]===\"case\"&&f.tokens.curr.value===\":\";_t(!0,!0,!1,!1,s);return}return t=Q(0,!0),t&&(!t.identifier||t.value!==\"function\")&&(t.type!==\"(punctuator)\"||!t.left||!t.left.identifier||t.left.value!==\"function\")&&!f.isStrict()&&f.option.strict===\"global\"&&F(\"E007\"),n.block||(!f.option.expr&&(!t||!t.exps)?F(\"W030\",f.tokens.curr):f.option.nonew&&t&&t.left&&t.id===\"(\"&&t.left.id===\"new\"&&F(\"W031\",n),Lt()),g=e,r&&f.funct[\"(scope)\"].unstack(),t}function Ot(){var e=[],t;while(!f.tokens.next.reach&&f.tokens.next.id!==\"(end)\")f.tokens.next.id===\";\"?(t=W(),(!t||t.id!==\"(\"&&t.id!==\"[\")&&F(\"W032\"),V(\";\")):e.push(At());return e}function Mt(){var e,t,n;while(f.tokens.next.id===\"(string)\"){t=W(0);if(t.id===\"(endline)\"){e=1;do n=W(e++);while(n.id===\"(endline)\");if(n.id===\";\")t=n;else{if(n.value===\"[\"||n.value===\".\")break;(!f.option.asi||n.value===\"(\")&&F(\"W033\",f.tokens.next)}}else{if(t.id===\".\"||t.id===\"[\")break;t.id!==\";\"&&F(\"W033\",t)}V();var r=f.tokens.curr.value;(f.directive[r]||r===\"use strict\"&&f.option.strict===\"implied\")&&F(\"W034\",f.tokens.curr,r),f.directive[r]=!0,t.id===\";\"&&V(\";\")}f.isStrict()&&(f.option[\"(explicitNewcap)\"]||(f.option.newcap=!0),f.option.undef=!0)}function _t(e,t,n,i,s){var o,u=m,a=g,l,c,h,p;m=e,c=f.tokens.next;var d=f.funct[\"(metrics)\"];d.nestedBlockDepth+=1,d.verifyMaxNestedBlockDepthPerFunction();if(f.tokens.next.id===\"{\"){V(\"{\"),f.funct[\"(scope)\"].stack(),h=f.tokens.curr.line;if(f.tokens.next.id!==\"}\"){g+=f.option.indent;while(!e&&f.tokens.next.from>g)g+=f.option.indent;if(n){l={};for(p in f.directive)r.has(f.directive,p)&&(l[p]=f.directive[p]);Mt(),f.option.strict&&f.funct[\"(context)\"][\"(global)\"]&&!l[\"use strict\"]&&!f.isStrict()&&F(\"E007\")}o=Ot(),d.statementCount+=o.length,g-=f.option.indent}V(\"}\",c),n&&(f.funct[\"(scope)\"].validateParams(),l&&(f.directive=l)),f.funct[\"(scope)\"].unstack(),g=a}else if(!e)if(n){f.funct[\"(scope)\"].stack(),l={},t&&!i&&!f.inMoz()&&q(\"W118\",f.tokens.curr,\"function closure expressions\");if(!t)for(p in f.directive)r.has(f.directive,p)&&(l[p]=f.directive[p]);Q(10),f.option.strict&&f.funct[\"(context)\"][\"(global)\"]&&!l[\"use strict\"]&&!f.isStrict()&&F(\"E007\"),f.funct[\"(scope)\"].unstack()}else q(\"E021\",f.tokens.next,\"{\",f.tokens.next.value);else f.funct[\"(noblockscopedvar)\"]=f.tokens.next.id!==\"for\",f.funct[\"(scope)\"].stack(),(!t||f.option.curly)&&F(\"W116\",f.tokens.next,\"{\",f.tokens.next.value),f.tokens.next.inBracelessBlock=!0,g+=f.option.indent,o=[At()],g-=f.option.indent,f.funct[\"(scope)\"].unstack(),delete f.funct[\"(noblockscopedvar)\"];switch(f.funct[\"(verb)\"]){case\"break\":case\"continue\":case\"return\":case\"throw\":if(s)break;default:f.funct[\"(verb)\"]=null}return m=u,e&&f.option.noempty&&(!o||o.length===0)&&F(\"W035\",f.tokens.prev),d.nestedBlockDepth-=1,o}function Dt(e){E&&typeof E[e]!=\"boolean\"&&F(\"W036\",f.tokens.curr,e),typeof w[e]==\"number\"?w[e]+=1:w[e]=1}function Bt(){var e={};e.exps=!0,f.funct[\"(comparray)\"].stack();var t=!1;return f.tokens.next.value!==\"for\"&&(t=!0,f.inMoz()||F(\"W116\",f.tokens.next,\"for\",f.tokens.next.value),f.funct[\"(comparray)\"].setState(\"use\"),e.right=Q(10)),V(\"for\"),f.tokens.next.value===\"each\"&&(V(\"each\"),f.inMoz()||F(\"W118\",f.tokens.curr,\"for each\")),V(\"(\"),f.funct[\"(comparray)\"].setState(\"define\"),e.left=Q(130),r.contains([\"in\",\"of\"],f.tokens.next.value)?V():q(\"E045\",f.tokens.curr),f.funct[\"(comparray)\"].setState(\"generate\"),Q(10),V(\")\"),f.tokens.next.value===\"if\"&&(V(\"if\"),V(\"(\"),f.funct[\"(comparray)\"].setState(\"filter\"),e.filter=Q(10),V(\")\")),t||(f.funct[\"(comparray)\"].setState(\"use\"),e.right=Q(10)),V(\"]\"),f.funct[\"(comparray)\"].unstack(),e}function jt(){return f.funct[\"(statement)\"]&&f.funct[\"(statement)\"].type===\"class\"||f.funct[\"(context)\"]&&f.funct[\"(context)\"][\"(verb)\"]===\"class\"}function Ft(e){return e.identifier||e.id===\"(string)\"||e.id===\"(number)\"}function It(e){var t,n=!0;return typeof e==\"object\"?t=e:(n=e,t=Nt(!1,!0,n)),t?typeof t==\"object\"&&(t.id===\"(string)\"||t.id===\"(identifier)\"?t=t.value:t.id===\"(number)\"&&(t=t.value.toString())):f.tokens.next.id===\"(string)\"?(t=f.tokens.next.value,n||V()):f.tokens.next.id===\"(number)\"&&(t=f.tokens.next.value.toString(),n||V()),t===\"hasOwnProperty\"&&F(\"W001\"),t}function qt(e){function h(e){f.funct[\"(scope)\"].addParam.apply(f.funct[\"(scope)\"],e)}var t,n=[],i,s=[],o,u=!1,a=!1,l=0,c=e&&e.loneArg;if(c&&c.identifier===!0)return f.funct[\"(scope)\"].addParam(c.value,c),{arity:1,params:[c.value]};t=f.tokens.next,(!e||!e.parsedOpening)&&V(\"(\");if(f.tokens.next.id===\")\"){V(\")\");return}for(;;){l++;var p=[];if(r.contains([\"{\",\"[\"],f.tokens.next.id)){s=Gt();for(o in s)o=s[o],o.id&&(n.push(o.id),p.push([o.id,o.token]))}else{pn(f.tokens.next,\"...\")&&(a=!0),i=Ct(!0);if(i)n.push(i),p.push([i,f.tokens.curr]);else while(!hn(f.tokens.next,[\",\",\")\"]))V()}u&&f.tokens.next.id!==\"=\"&&q(\"W138\",f.tokens.current),f.tokens.next.id===\"=\"&&(f.inES6()||F(\"W119\",f.tokens.next,\"default parameters\",\"6\"),V(\"=\"),u=!0,Q(10)),p.forEach(h);if(f.tokens.next.id!==\",\")return V(\")\",t),{arity:l,params:n};a&&F(\"W131\",f.tokens.next),tt()}}function Rt(e,t,n){var i={\"(name)\":e,\"(breakage)\":0,\"(loopage)\":0,\"(tokens)\":{},\"(properties)\":{},\"(catch)\":!1,\"(global)\":!1,\"(line)\":null,\"(character)\":null,\"(metrics)\":null,\"(statement)\":null,\"(context)\":null,\"(scope)\":null,\"(comparray)\":null,\"(generator)\":null,\"(arrow)\":null,\"(params)\":null};return t&&r.extend(i,{\"(line)\":t.line,\"(character)\":t.character,\"(metrics)\":Vt(t)}),r.extend(i,n),i[\"(context)\"]&&(i[\"(scope)\"]=i[\"(context)\"][\"(scope)\"],i[\"(comparray)\"]=i[\"(context)\"][\"(comparray)\"]),i}function Ut(e){return\"(scope)\"in e}function zt(e){return e[\"(global)\"]&&!e[\"(verb)\"]}function Wt(e){function i(){if(f.tokens.curr.template&&f.tokens.curr.tail&&f.tokens.curr.context===t)return!0;var e=f.tokens.next.template&&f.tokens.next.tail&&f.tokens.next.context===t;return e&&V(),e||f.tokens.next.isUnclosed}var t=this.context,n=this.noSubst,r=this.depth;if(!n)while(!i())!f.tokens.next.template||f.tokens.next.depth>r?Q(0):V();return{id:\"(template)\",type:\"(template)\",tag:e}}function Xt(e){var t,n,r,i,s,o,u,a,l=f.option,c=f.ignored;e&&(r=e.name,i=e.statement,s=e.classExprBinding,o=e.type===\"generator\",u=e.type===\"arrow\",a=e.ignoreLoopFunc),f.option=Object.create(f.option),f.ignored=Object.create(f.ignored),f.funct=Rt(r||f.nameStack.infer(),f.tokens.next,{\"(statement)\":i,\"(context)\":f.funct,\"(arrow)\":u,\"(generator)\":o}),t=f.funct,n=f.tokens.curr,n.funct=f.funct,v.push(f.funct),f.funct[\"(scope)\"].stack(\"functionouter\");var h=r||s;h&&f.funct[\"(scope)\"].block.add(h,s?\"class\":\"function\",f.tokens.curr,!1),f.funct[\"(scope)\"].stack(\"functionparams\");var p=qt(e);return p?(f.funct[\"(params)\"]=p.params,f.funct[\"(metrics)\"].arity=p.arity,f.funct[\"(metrics)\"].verifyMaxParametersPerFunction()):f.funct[\"(metrics)\"].arity=0,u&&(f.inES6(!0)||F(\"W119\",f.tokens.curr,\"arrow function syntax (=>)\",\"6\"),e.loneArg||V(\"=>\")),_t(!1,!0,!0,u),!f.option.noyield&&o&&f.funct[\"(generator)\"]!==\"yielded\"&&F(\"W124\",f.tokens.curr),f.funct[\"(metrics)\"].verifyMaxStatementsPerFunction(),f.funct[\"(metrics)\"].verifyMaxComplexityPerFunction(),f.funct[\"(unusedOption)\"]=f.option.unused,f.option=l,f.ignored=c,f.funct[\"(last)\"]=f.tokens.curr.line,f.funct[\"(lastcharacter)\"]=f.tokens.curr.character,f.funct[\"(scope)\"].unstack(),f.funct[\"(scope)\"].unstack(),f.funct=f.funct[\"(context)\"],!a&&!f.option.loopfunc&&f.funct[\"(loopage)\"]&&t[\"(isCapturing)\"]&&F(\"W083\",n),t}function Vt(e){return{statementCount:0,nestedBlockDepth:-1,ComplexityCount:1,arity:0,verifyMaxStatementsPerFunction:function(){f.option.maxstatements&&this.statementCount>f.option.maxstatements&&F(\"W071\",e,this.statementCount)},verifyMaxParametersPerFunction:function(){r.isNumber(f.option.maxparams)&&this.arity>f.option.maxparams&&F(\"W072\",e,this.arity)},verifyMaxNestedBlockDepthPerFunction:function(){f.option.maxdepth&&this.nestedBlockDepth>0&&this.nestedBlockDepth===f.option.maxdepth+1&&F(\"W073\",null,this.nestedBlockDepth)},verifyMaxComplexityPerFunction:function(){var t=f.option.maxcomplexity,n=this.ComplexityCount;t&&n>t&&F(\"W074\",e,n)}}}function $t(){f.funct[\"(metrics)\"].ComplexityCount+=1}function Jt(e){var t,n;e&&(t=e.id,n=e.paren,t===\",\"&&(e=e.exprs[e.exprs.length-1])&&(t=e.id,n=n||e.paren));switch(t){case\"=\":case\"+=\":case\"-=\":case\"*=\":case\"%=\":case\"&=\":case\"|=\":case\"^=\":case\"/=\":!n&&!f.option.boss&&F(\"W084\")}}function Kt(e){if(f.inES5())for(var t in e)e[t]&&e[t].setterToken&&!e[t].getterToken&&F(\"W078\",e[t].setterToken)}function Qt(e,t){if(pn(f.tokens.next,\".\")){var n=f.tokens.curr.id;V(\".\");var r=Ct();return f.tokens.curr.isMetaProperty=!0,e!==r?q(\"E057\",f.tokens.prev,n,r):t(),f.tokens.curr}}function Gt(e){var t=e&&e.assignment;return f.inES6()||F(\"W104\",f.tokens.curr,t?\"destructuring assignment\":\"destructuring binding\",\"6\"),Yt(e)}function Yt(e){var t,n=[],r=e&&e.openingParsed,i=e&&e.assignment,s=i?{assignment:i}:null,o=r?f.tokens.curr:f.tokens.next,u=function(){var e;if(hn(f.tokens.next,[\"[\",\"{\"])){t=Yt(s);for(var r in t)r=t[r],n.push({id:r.id,token:r.token})}else if(pn(f.tokens.next,\",\"))n.push({id:null,token:f.tokens.curr});else{if(!pn(f.tokens.next,\"(\")){var o=pn(f.tokens.next,\"...\");if(i){var a=o?W(0):f.tokens.next;a.identifier||F(\"E030\",a,a.value);var l=Q(155);l&&(wt(l),l.identifier&&(e=l.value))}else e=Ct();return e&&n.push({id:e,token:f.tokens.curr}),o}V(\"(\"),u(),V(\")\")}return!1},a=function(){var e;pn(f.tokens.next,\"[\")?(V(\"[\"),Q(10),V(\"]\"),V(\":\"),u()):f.tokens.next.id===\"(string)\"||f.tokens.next.id===\"(number)\"?(V(),V(\":\"),u()):(e=Ct(),pn(f.tokens.next,\":\")?(V(\":\"),u()):e&&(i&&wt(f.tokens.curr),n.push({id:e,token:f.tokens.curr})))};if(pn(o,\"[\")){r||V(\"[\"),pn(f.tokens.next,\"]\")&&F(\"W137\",f.tokens.curr);var l=!1;while(!pn(f.tokens.next,\"]\"))u()&&!l&&pn(f.tokens.next,\",\")&&(F(\"W130\",f.tokens.next),l=!0),pn(f.tokens.next,\"=\")&&(pn(f.tokens.prev,\"...\")?V(\"]\"):V(\"=\"),f.tokens.next.id===\"undefined\"&&F(\"W080\",f.tokens.prev,f.tokens.prev.value),Q(10)),pn(f.tokens.next,\"]\")||V(\",\");V(\"]\")}else if(pn(o,\"{\")){r||V(\"{\"),pn(f.tokens.next,\"}\")&&F(\"W137\",f.tokens.curr);while(!pn(f.tokens.next,\"}\")){a(),pn(f.tokens.next,\"=\")&&(V(\"=\"),f.tokens.next.id===\"undefined\"&&F(\"W080\",f.tokens.prev,f.tokens.prev.value),Q(10));if(!pn(f.tokens.next,\"}\")){V(\",\");if(pn(f.tokens.next,\"}\"))break}}V(\"}\")}return n}function Zt(e,t){var n=t.first;if(!n)return;r.zip(e,Array.isArray(n)?n:[n]).forEach(function(e){var t=e[0],n=e[1];t&&n?t.first=n:t&&t.first&&!n&&F(\"W080\",t.first,t.first.value)})}function en(e,t,n){var i=n&&n.prefix,s=n&&n.inexport,o=e===\"let\",u=e===\"const\",a,l,c,h;f.inES6()||F(\"W104\",f.tokens.curr,e,\"6\"),o&&f.tokens.next.value===\"(\"?(f.inMoz()||F(\"W118\",f.tokens.next,\"let block\"),V(\"(\"),f.funct[\"(scope)\"].stack(),h=!0):f.funct[\"(noblockscopedvar)\"]&&q(\"E048\",f.tokens.curr,u?\"Const\":\"Let\"),t.first=[];for(;;){var p=[];r.contains([\"{\",\"[\"],f.tokens.next.value)?(a=Gt(),l=!1):(a=[{id:Ct(),token:f.tokens.curr}],l=!0),!i&&u&&f.tokens.next.id!==\"=\"&&F(\"E012\",f.tokens.curr,f.tokens.curr.value);for(var d in a)a.hasOwnProperty(d)&&(d=a[d],f.funct[\"(scope)\"].block.isGlobal()&&S[d.id]===!1&&F(\"W079\",d.token,d.id),d.id&&!f.funct[\"(noblockscopedvar)\"]&&(f.funct[\"(scope)\"].addlabel(d.id,{type:e,token:d.token}),p.push(d.token),l&&s&&f.funct[\"(scope)\"].setExported(d.token.value,d.token)));f.tokens.next.id===\"=\"&&(V(\"=\"),!i&&f.tokens.next.id===\"undefined\"&&F(\"W080\",f.tokens.prev,f.tokens.prev.value),!i&&W(0).id===\"=\"&&f.tokens.next.identifier&&F(\"W120\",f.tokens.next,f.tokens.next.value),c=Q(i?120:10),l?a[0].first=c:Zt(p,c)),t.first=t.first.concat(p);if(f.tokens.next.id!==\",\")break;tt()}return h&&(V(\")\"),_t(!0,!0),t.block=!0,f.funct[\"(scope)\"].unstack()),t}function sn(e){return f.inES6()||F(\"W104\",f.tokens.curr,\"class\",\"6\"),e?(this.name=Ct(),f.funct[\"(scope)\"].addlabel(this.name,{type:\"class\",token:f.tokens.curr})):f.tokens.next.identifier&&f.tokens.next.value!==\"extends\"?(this.name=Ct(),this.namedExpr=!0):this.name=f.nameStack.infer(),on(this),this}function on(e){var t=f.inClassBody;f.tokens.next.value===\"extends\"&&(V(\"extends\"),e.heritage=Q(10)),f.inClassBody=!0,V(\"{\"),e.body=un(e),V(\"}\"),f.inClassBody=t}function un(e){var t,n,r,i,s=Object.create(null),o=Object.create(null),u;for(var a=0;f.tokens.next.id!==\"}\";++a){t=f.tokens.next,n=!1,r=!1,i=null;if(t.id===\";\"){F(\"W032\"),V(\";\");continue}t.id===\"*\"&&(r=!0,V(\"*\"),t=f.tokens.next);if(t.id===\"[\")t=cn(),u=!0;else{if(!Ft(t)){F(\"W052\",f.tokens.next,f.tokens.next.value||f.tokens.next.type),V();continue}V(),u=!1;if(t.identifier&&t.value===\"static\"){pn(f.tokens.next,\"*\")&&(r=!0,V(\"*\"));if(Ft(f.tokens.next)||f.tokens.next.id===\"[\")u=f.tokens.next.id===\"[\",n=!0,t=f.tokens.next,f.tokens.next.id===\"[\"?t=cn():V()}t.identifier&&(t.value===\"get\"||t.value===\"set\")&&(Ft(f.tokens.next)||f.tokens.next.id===\"[\")&&(u=f.tokens.next.id===\"[\",i=t,t=f.tokens.next,f.tokens.next.id===\"[\"?t=cn():V())}if(!pn(f.tokens.next,\"(\")){q(\"E054\",f.tokens.next,f.tokens.next.value);while(f.tokens.next.id!==\"}\"&&!pn(f.tokens.next,\"(\"))V();f.tokens.next.value!==\"(\"&&Xt({statement:e})}u||(i?ln(i.value,n?o:s,t.value,t,!0,n):(t.value===\"constructor\"?f.nameStack.set(e):f.nameStack.set(t),fn(n?o:s,t.value,t,!0,n)));if(i&&t.value===\"constructor\"){var l=i.value===\"get\"?\"class getter method\":\"class setter method\";q(\"E049\",t,l,\"constructor\")}else t.value===\"prototype\"&&q(\"E049\",t,\"class method\",\"prototype\");It(t),Xt({statement:e,type:r?\"generator\":null,classExprBinding:e.namedExpr?e.name:null})}Kt(s)}function fn(e,t,n,r,i){var s=[\"key\",\"class method\",\"static class method\"];s=s[(r||!1)+(i||!1)],n.identifier&&(t=n.value),e[t]&&t!==\"__proto__\"?F(\"W075\",f.tokens.next,s,t):e[t]=Object.create(null),e[t].basic=!0,e[t].basictkn=n}function ln(e,t,n,r,i,s){var o=e===\"get\"?\"getterToken\":\"setterToken\",u=\"\";i?(s&&(u+=\"static \"),u+=e+\"ter method\"):u=\"key\",f.tokens.curr.accessorType=e,f.nameStack.set(r),t[n]?(t[n].basic||t[n][o])&&n!==\"__proto__\"&&F(\"W075\",f.tokens.next,u,n):t[n]=Object.create(null),t[n][o]=r}function cn(){V(\"[\"),f.inES6()||F(\"W119\",f.tokens.curr,\"computed property names\",\"6\");var e=Q(10);return V(\"]\"),e}function hn(e,t){return e.type===\"(punctuator)\"?r.contains(t,e.value):!1}function pn(e,t){return e.type===\"(punctuator)\"&&e.value===t}function dn(){var e=an();e.notJson?(!f.inES6()&&e.isDestAssign&&F(\"W104\",f.tokens.curr,\"destructuring assignment\",\"6\"),Ot()):(f.option.laxbreak=!0,f.jsonMode=!0,mn())}function mn(){function e(){var e={},t=f.tokens.next;V(\"{\");if(f.tokens.next.id!==\"}\")for(;;){if(f.tokens.next.id===\"(end)\")q(\"E026\",f.tokens.next,t.line);else{if(f.tokens.next.id===\"}\"){F(\"W094\",f.tokens.curr);break}f.tokens.next.id===\",\"?q(\"E028\",f.tokens.next):f.tokens.next.id!==\"(string)\"&&F(\"W095\",f.tokens.next,f.tokens.next.value)}e[f.tokens.next.value]===!0?F(\"W075\",f.tokens.next,\"key\",f.tokens.next.value):f.tokens.next.value===\"__proto__\"&&!f.option.proto||f.tokens.next.value===\"__iterator__\"&&!f.option.iterator?F(\"W096\",f.tokens.next,f.tokens.next.value):e[f.tokens.next.value]=!0,V(),V(\":\"),mn();if(f.tokens.next.id!==\",\")break;V(\",\")}V(\"}\")}function t(){var e=f.tokens.next;V(\"[\");if(f.tokens.next.id!==\"]\")for(;;){if(f.tokens.next.id===\"(end)\")q(\"E027\",f.tokens.next,e.line);else{if(f.tokens.next.id===\"]\"){F(\"W094\",f.tokens.curr);break}f.tokens.next.id===\",\"&&q(\"E028\",f.tokens.next)}mn();if(f.tokens.next.id!==\",\")break;V(\",\")}V(\"]\")}switch(f.tokens.next.id){case\"{\":e();break;case\"[\":t();break;case\"true\":case\"false\":case\"null\":case\"(number)\":case\"(string)\":V();break;case\"-\":V(\"-\"),V(\"(number)\");break;default:q(\"E003\",f.tokens.next)}}var e,t={\"<\":!0,\"<=\":!0,\"==\":!0,\"===\":!0,\"!==\":!0,\"!=\":!0,\">\":!0,\">=\":!0,\"+\":!0,\"-\":!0,\"*\":!0,\"/\":!0,\"%\":!0},n,d=[\"closure\",\"exception\",\"global\",\"label\",\"outer\",\"unused\",\"var\"],v,m,g,y,b,w,E,S,x,T,N=[],C=new i.EventEmitter,mt={};mt.legacy=[\"xml\",\"unknown\"],mt.es3=[\"undefined\",\"boolean\",\"number\",\"string\",\"function\",\"object\"],mt.es3=mt.es3.concat(mt.legacy),mt.es6=mt.es3.concat(\"symbol\"),at(\"(number)\",function(){return this}),at(\"(string)\",function(){return this}),f.syntax[\"(identifier)\"]={type:\"(identifier)\",lbp:0,identifier:!0,nud:function(){var e=this.value;return f.tokens.next.id===\"=>\"?this:(f.funct[\"(comparray)\"].check(e)||f.funct[\"(scope)\"].block.use(e,f.tokens.curr),this)},led:function(){q(\"E033\",f.tokens.next,f.tokens.next.value)}};var Pt={lbp:0,identifier:!1,template:!0};f.syntax[\"(template)\"]=r.extend({type:\"(template)\",nud:Wt,led:Wt,noSubst:!1},Pt),f.syntax[\"(template middle)\"]=r.extend({type:\"(template middle)\",middle:!0,noSubst:!1},Pt),f.syntax[\"(template tail)\"]=r.extend({type:\"(template tail)\",tail:!0,noSubst:!1},Pt),f.syntax[\"(no subst template)\"]=r.extend({type:\"(template)\",nud:Wt,led:Wt,noSubst:!0,tail:!0},Pt),at(\"(regexp)\",function(){return this}),rt(\"(endline)\"),rt(\"(begin)\"),rt(\"(end)\").reach=!0,rt(\"(error)\").reach=!0,rt(\"}\").reach=!0,rt(\")\"),rt(\"]\"),rt('\"').reach=!0,rt(\"'\").reach=!0,rt(\";\"),rt(\":\").reach=!0,rt(\"#\"),ft(\"else\"),ft(\"case\").reach=!0,ft(\"catch\"),ft(\"default\").reach=!0,ft(\"finally\"),ct(\"arguments\",function(e){f.isStrict()&&f.funct[\"(global)\"]&&F(\"E008\",e)}),ct(\"eval\"),ct(\"false\"),ct(\"Infinity\"),ct(\"null\"),ct(\"this\",function(e){f.isStrict()&&!jt()&&!f.option.validthis&&(f.funct[\"(statement)\"]&&f.funct[\"(name)\"].charAt(0)>\"Z\"||f.funct[\"(global)\"])&&F(\"W040\",e)}),ct(\"true\"),ct(\"undefined\"),Et(\"=\",\"assign\",20),Et(\"+=\",\"assignadd\",20),Et(\"-=\",\"assignsub\",20),Et(\"*=\",\"assignmult\",20),Et(\"/=\",\"assigndiv\",20).nud=function(){q(\"E014\")},Et(\"%=\",\"assignmod\",20),xt(\"&=\"),xt(\"|=\"),xt(\"^=\"),xt(\"<<=\"),xt(\">>=\"),xt(\">>>=\"),ht(\",\",function(e,t){var n;t.exprs=[e],f.option.nocomma&&F(\"W127\");if(!tt({peek:!0}))return t;for(;;){if(!(n=Q(10)))break;t.exprs.push(n);if(f.tokens.next.value!==\",\"||!tt())break}return t},10,!0),ht(\"?\",function(e,t){return $t(),t.left=e,t.right=Q(10),V(\":\"),t[\"else\"]=Q(10),t},30);var Ht=40;ht(\"||\",function(e,t){return $t(),t.left=e,t.right=Q(Ht),t},Ht),ht(\"&&\",\"and\",50),St(\"|\",\"bitor\",70),St(\"^\",\"bitxor\",80),St(\"&\",\"bitand\",90),dt(\"==\",function(e,t){var n=f.option.eqnull&&((e&&e.value)===\"null\"||(t&&t.value)===\"null\");switch(!0){case!n&&f.option.eqeqeq:this.from=this.character,F(\"W116\",this,\"===\",\"==\");break;case vt(e):F(\"W041\",this,\"===\",e.value);break;case vt(t):F(\"W041\",this,\"===\",t.value);break;case gt(t,e,f):F(\"W122\",this,t.value);break;case gt(e,t,f):F(\"W122\",this,e.value)}return this}),dt(\"===\",function(e,t){return gt(t,e,f)?F(\"W122\",this,t.value):gt(e,t,f)&&F(\"W122\",this,e.value),this}),dt(\"!=\",function(e,t){var n=f.option.eqnull&&((e&&e.value)===\"null\"||(t&&t.value)===\"null\");return!n&&f.option.eqeqeq?(this.from=this.character,F(\"W116\",this,\"!==\",\"!=\")):vt(e)?F(\"W041\",this,\"!==\",e.value):vt(t)?F(\"W041\",this,\"!==\",t.value):gt(t,e,f)?F(\"W122\",this,t.value):gt(e,t,f)&&F(\"W122\",this,e.value),this}),dt(\"!==\",function(e,t){return gt(t,e,f)?F(\"W122\",this,t.value):gt(e,t,f)&&F(\"W122\",this,e.value),this}),dt(\"<\"),dt(\">\"),dt(\"<=\"),dt(\">=\"),St(\"<<\",\"shiftleft\",120),St(\">>\",\"shiftright\",120),St(\">>>\",\"shiftrightunsigned\",120),ht(\"in\",\"in\",120),ht(\"instanceof\",\"instanceof\",120),ht(\"+\",function(e,t){var n;return t.left=e,t.right=n=Q(130),e&&n&&e.id===\"(string)\"&&n.id===\"(string)\"?(e.value+=n.value,e.character=n.character,!f.option.scripturl&&a.javascriptURL.test(e.value)&&F(\"W050\",e),e):t},130),ut(\"+\",\"num\"),ut(\"+++\",function(){return F(\"W007\"),this.arity=\"unary\",this.right=Q(150),this}),ht(\"+++\",function(e){return F(\"W007\"),this.left=e,this.right=Q(130),this},130),ht(\"-\",\"sub\",130),ut(\"-\",\"neg\"),ut(\"---\",function(){return F(\"W006\"),this.arity=\"unary\",this.right=Q(150),this}),ht(\"---\",function(e){return F(\"W006\"),this.left=e,this.right=Q(130),this},130),ht(\"*\",\"mult\",140),ht(\"/\",\"div\",140),ht(\"%\",\"mod\",140),Tt(\"++\"),ut(\"++\",\"preinc\"),f.syntax[\"++\"].exps=!0,Tt(\"--\"),ut(\"--\",\"predec\"),f.syntax[\"--\"].exps=!0,ut(\"delete\",function(){var e=Q(10);return e?(e.id!==\".\"&&e.id!==\"[\"&&F(\"W051\"),this.first=e,e.identifier&&!f.isStrict()&&(e.forgiveUndef=!0),this):this}).exps=!0,ut(\"~\",function(){return f.option.bitwise&&F(\"W016\",this,\"~\"),this.arity=\"unary\",this.right=Q(150),this}),ut(\"...\",function(){return f.inES6(!0)||F(\"W119\",this,\"spread/rest operator\",\"6\"),!f.tokens.next.identifier&&f.tokens.next.type!==\"(string)\"&&!hn(f.tokens.next,[\"[\",\"(\"])&&q(\"E030\",f.tokens.next,f.tokens.next.value),Q(150),this}),ut(\"!\",function(){return this.arity=\"unary\",this.right=Q(150),this.right||B(\"E041\",this.line||0),t[this.right.id]===!0&&F(\"W018\",this,\"!\"),this}),ut(\"typeof\",function(){var e=Q(150);return this.first=this.right=e,e||B(\"E041\",this.line||0,this.character||0),e.identifier&&(e.forgiveUndef=!0),this}),ut(\"new\",function(){var e=Qt(\"target\",function(){f.inES6(!0)||F(\"W119\",f.tokens.prev,\"new.target\",\"6\");var e,t=f.funct;while(t){e=!t[\"(global)\"];if(!t[\"(arrow)\"])break;t=t[\"(context)\"]}e||F(\"W136\",f.tokens.prev,\"new.target\")});if(e)return e;var t=Q(155),n;if(t&&t.id!==\"function\")if(t.identifier){t[\"new\"]=!0;switch(t.value){case\"Number\":case\"String\":case\"Boolean\":case\"Math\":case\"JSON\":F(\"W053\",f.tokens.prev,t.value);break;case\"Symbol\":f.inES6()&&F(\"W053\",f.tokens.prev,t.value);break;case\"Function\":f.option.evil||F(\"W054\");break;case\"Date\":case\"RegExp\":case\"this\":break;default:t.id!==\"function\"&&(n=t.value.substr(0,1),f.option.newcap&&(n<\"A\"||n>\"Z\")&&!f.funct[\"(scope)\"].isPredefined(t.value)&&F(\"W055\",f.tokens.curr))}}else t.id!==\".\"&&t.id!==\"[\"&&t.id!==\"(\"&&F(\"W056\",f.tokens.curr);else f.option.supernew||F(\"W057\",this);return f.tokens.next.id!==\"(\"&&!f.option.supernew&&F(\"W058\",f.tokens.curr,f.tokens.curr.value),this.first=this.right=t,this}),f.syntax[\"new\"].exps=!0,ut(\"void\").exps=!0,ht(\".\",function(e,t){var n=Ct(!1,!0);return typeof n==\"string\"&&Dt(n),t.left=e,t.right=n,n&&n===\"hasOwnProperty\"&&f.tokens.next.value===\"=\"&&F(\"W001\"),!e||e.value!==\"arguments\"||n!==\"callee\"&&n!==\"caller\"?!f.option.evil&&e&&e.value===\"document\"&&(n===\"write\"||n===\"writeln\")&&F(\"W060\",e):f.option.noarg?F(\"W059\",e,n):f.isStrict()&&q(\"E008\"),!f.option.evil&&(n===\"eval\"||n===\"execScript\")&&yt(e,f)&&F(\"W061\"),t},160,!0),ht(\"(\",function(e,t){f.option.immed&&e&&!e.immed&&e.id===\"function\"&&F(\"W062\");var n=0,r=[];e&&e.type===\"(identifier)\"&&e.value.match(/^[A-Z]([A-Z0-9_$]*[a-z][A-Za-z0-9_$]*)?$/)&&\"Array Number String Boolean Date Object Error Symbol\".indexOf(e.value)===-1&&(e.value===\"Math\"?F(\"W063\",e):f.option.newcap&&F(\"W064\",e));if(f.tokens.next.id!==\")\")for(;;){r[r.length]=Q(10),n+=1;if(f.tokens.next.id!==\",\")break;tt()}return V(\")\"),typeof e==\"object\"&&(!f.inES5()&&e.value===\"parseInt\"&&n===1&&F(\"W065\",f.tokens.curr),f.option.evil||(e.value===\"eval\"||e.value===\"Function\"||e.value===\"execScript\"?(F(\"W061\",e),r[0]&&[0].id===\"(string)\"&&U(e,r[0].value)):!r[0]||r[0].id!==\"(string)\"||e.value!==\"setTimeout\"&&e.value!==\"setInterval\"?r[0]&&r[0].id===\"(string)\"&&e.value===\".\"&&e.left.value===\"window\"&&(e.right===\"setTimeout\"||e.right===\"setInterval\")&&(F(\"W066\",e),U(e,r[0].value)):(F(\"W066\",e),U(e,r[0].value))),!e.identifier&&e.id!==\".\"&&e.id!==\"[\"&&e.id!==\"=>\"&&e.id!==\"(\"&&e.id!==\"&&\"&&e.id!==\"||\"&&e.id!==\"?\"&&(!f.inES6()||!e[\"(name)\"])&&F(\"W067\",t)),t.left=e,t},155,!0).exps=!0,ut(\"(\",function(){var e=f.tokens.next,t,n=-1,r,i,s,o,u=1,a=f.tokens.curr,l=f.tokens.prev,c=!f.option.singleGroups;do e.value===\"(\"?u+=1:e.value===\")\"&&(u-=1),n+=1,t=e,e=W(n);while((u!==0||t.value!==\")\")&&e.value!==\";\"&&e.type!==\"(end)\");f.tokens.next.id===\"function\"&&(i=f.tokens.next.immed=!0);if(e.value===\"=>\")return Xt({type:\"arrow\",parsedOpening:!0});var h=[];if(f.tokens.next.id!==\")\")for(;;){h.push(Q(10));if(f.tokens.next.id!==\",\")break;f.option.nocomma&&F(\"W127\"),tt()}V(\")\",this),f.option.immed&&h[0]&&h[0].id===\"function\"&&f.tokens.next.id!==\"(\"&&f.tokens.next.id!==\".\"&&f.tokens.next.id!==\"[\"&&F(\"W068\",this);if(!h.length)return;return h.length>1?(r=Object.create(f.syntax[\",\"]),r.exprs=h,s=h[0],o=h[h.length-1],c||(c=l.assign||l.delim)):(r=s=o=h[0],c||(c=a.beginsStmt&&(r.id===\"{\"||i||Ut(r))||i&&(!J()||f.tokens.prev.id!==\"}\")||Ut(r)&&!J()||r.id===\"{\"&&l.id===\"=>\"||r.type===\"(number)\"&&pn(e,\".\")&&/^\\d+$/.test(r.value))),r&&(!c&&(s.left||s.right||r.exprs)&&(c=!K(l)&&s.lbp<=l.lbp||!J()&&o.lbp<f.tokens.next.lbp),c||F(\"W126\",a),r.paren=!0),r}),pt(\"=>\"),ht(\"[\",function(e,t){var n=Q(10),r;return n&&n.type===\"(string)\"&&(!f.option.evil&&(n.value===\"eval\"||n.value===\"execScript\")&&yt(e,f)&&F(\"W061\"),Dt(n.value),!f.option.sub&&a.identifier.test(n.value)&&(r=f.syntax[n.value],(!r||!O(r))&&F(\"W069\",f.tokens.prev,n.value))),V(\"]\",t),n&&n.value===\"hasOwnProperty\"&&f.tokens.next.value===\"=\"&&F(\"W001\"),t.left=e,t.right=n,t},160,!0),ut(\"[\",function(){var e=an();if(e.isCompArray)return!f.option.esnext&&!f.inMoz()&&F(\"W118\",f.tokens.curr,\"array comprehension\"),Bt();if(e.isDestAssign)return this.destructAssign=Gt({openingParsed:!0,assignment:!0}),this;var t=f.tokens.curr.line!==G(f.tokens.next);this.first=[],t&&(g+=f.option.indent,f.tokens.next.from===g+f.option.indent&&(g+=f.option.indent));while(f.tokens.next.id!==\"(end)\"){while(f.tokens.next.id===\",\"){if(!f.option.elision){if(!!f.inES5()){F(\"W128\");do V(\",\");while(f.tokens.next.id===\",\");continue}F(\"W070\")}V(\",\")}if(f.tokens.next.id===\"]\")break;this.first.push(Q(10));if(f.tokens.next.id!==\",\")break;tt({allowTrailing:!0});if(f.tokens.next.id===\"]\"&&!f.inES5()){F(\"W070\",f.tokens.curr);break}}return t&&(g-=f.option.indent),V(\"]\",this),this}),function(e){e.nud=function(){var e,t,n,r,i,s=!1,o,u=Object.create(null);e=f.tokens.curr.line!==G(f.tokens.next),e&&(g+=f.option.indent,f.tokens.next.from===g+f.option.indent&&(g+=f.option.indent));var a=an();if(a.isDestAssign)return this.destructAssign=Gt({openingParsed:!0,assignment:!0}),this;for(;;){if(f.tokens.next.id===\"}\")break;o=f.tokens.next.value;if(!f.tokens.next.identifier||X().id!==\",\"&&X().id!==\"}\")if(W().id===\":\"||o!==\"get\"&&o!==\"set\"){f.tokens.next.value===\"*\"&&f.tokens.next.type===\"(punctuator)\"?(f.inES6()||F(\"W104\",f.tokens.next,\"generator functions\",\"6\"),V(\"*\"),s=!0):s=!1;if(f.tokens.next.id===\"[\")n=cn(),f.nameStack.set(n);else{f.nameStack.set(f.tokens.next),n=It(),fn(u,n,f.tokens.next);if(typeof n!=\"string\")break}f.tokens.next.value===\"(\"?(f.inES6()||F(\"W104\",f.tokens.curr,\"concise methods\",\"6\"),Xt({type:s?\"generator\":null})):(V(\":\"),Q(10))}else V(o),f.inES5()||q(\"E034\"),n=It(),!n&&!f.inES6()&&q(\"E035\"),n&&ln(o,u,n,f.tokens.curr),i=f.tokens.next,t=Xt(),r=t[\"(params)\"],o===\"get\"&&n&&r?F(\"W076\",i,r[0],n):o===\"set\"&&n&&(!r||r.length!==1)&&F(\"W077\",i,n);else f.inES6()||F(\"W104\",f.tokens.next,\"object short notation\",\"6\"),n=It(!0),fn(u,n,f.tokens.next),Q(10);Dt(n);if(f.tokens.next.id!==\",\")break;tt({allowTrailing:!0,property:!0}),f.tokens.next.id===\",\"?F(\"W070\",f.tokens.curr):f.tokens.next.id===\"}\"&&!f.inES5()&&F(\"W070\",f.tokens.curr)}return e&&(g-=f.option.indent),V(\"}\",this),Kt(u),this},e.fud=function(){q(\"E036\",f.tokens.curr)}}(rt(\"{\"));var tn=it(\"const\",function(e){return en(\"const\",this,e)});tn.exps=!0;var nn=it(\"let\",function(e){return en(\"let\",this,e)});nn.exps=!0;var rn=it(\"var\",function(e){var t=e&&e.prefix,n=e&&e.inexport,i,o,u,a=e&&e.implied,l=!e||!e.ignore;this.first=[];for(;;){var c=[];r.contains([\"{\",\"[\"],f.tokens.next.value)?(i=Gt(),o=!1):(i=[{id:Ct(),token:f.tokens.curr}],o=!0),(!t||!a)&&l&&f.option.varstmt&&F(\"W132\",this),this.first=this.first.concat(c);for(var h in i)i.hasOwnProperty(h)&&(h=i[h],!a&&f.funct[\"(global)\"]&&(S[h.id]===!1?F(\"W079\",h.token,h.id):f.option.futurehostile===!1&&(!f.inES5()&&s.ecmaIdentifiers[5][h.id]===!1||!f.inES6()&&s.ecmaIdentifiers[6][h.id]===!1)&&F(\"W129\",h.token,h.id)),h.id&&(a===\"for\"?(f.funct[\"(scope)\"].has(h.id)||l&&F(\"W088\",h.token,h.id),f.funct[\"(scope)\"].block.use(h.id,h.token)):(f.funct[\"(scope)\"].addlabel(h.id,{type:\"var\",token:h.token}),o&&n&&f.funct[\"(scope)\"].setExported(h.id,h.token)),c.push(h.token)));f.tokens.next.id===\"=\"&&(f.nameStack.set(f.tokens.curr),V(\"=\"),!t&&l&&!f.funct[\"(loopage)\"]&&f.tokens.next.id===\"undefined\"&&F(\"W080\",f.tokens.prev,f.tokens.prev.value),W(0).id===\"=\"&&f.tokens.next.identifier&&(!t&&l&&!f.funct[\"(params)\"]||f.funct[\"(params)\"].indexOf(f.tokens.next.value)===-1)&&F(\"W120\",f.tokens.next,f.tokens.next.value),u=Q(t?120:10),o?i[0].first=u:Zt(c,u));if(f.tokens.next.id!==\",\")break;tt()}return this});rn.exps=!0,st(\"class\",function(){return sn.call(this,!0)}),st(\"function\",function(e){var t=e&&e.inexport,n=!1;f.tokens.next.value===\"*\"&&(V(\"*\"),f.inES6({strict:!0})?n=!0:F(\"W119\",f.tokens.curr,\"function*\",\"6\")),m&&F(\"W082\",f.tokens.curr);var r=Nt();return f.funct[\"(scope)\"].addlabel(r,{type:\"function\",token:f.tokens.curr}),r===undefined?F(\"W025\"):t&&f.funct[\"(scope)\"].setExported(r,f.tokens.prev),Xt({name:r,statement:this,type:n?\"generator\":null,ignoreLoopFunc:m}),f.tokens.next.id===\"(\"&&f.tokens.next.line===f.tokens.curr.line&&q(\"E039\"),this}),ut(\"function\",function(){var e=!1;f.tokens.next.value===\"*\"&&(f.inES6()||F(\"W119\",f.tokens.curr,\"function*\",\"6\"),V(\"*\"),e=!0);var t=Nt();return Xt({name:t,type:e?\"generator\":null}),this}),st(\"if\",function(){var e=f.tokens.next;$t(),f.condition=!0,V(\"(\");var t=Q(0);Jt(t);var n=null;f.option.forin&&f.forinifcheckneeded&&(f.forinifcheckneeded=!1,n=f.forinifchecks[f.forinifchecks.length-1],t.type===\"(punctuator)\"&&t.value===\"!\"?n.type=\"(negative)\":n.type=\"(positive)\"),V(\")\",e),f.condition=!1;var r=_t(!0,!0);return n&&n.type===\"(negative)\"&&r&&r[0]&&r[0].type===\"(identifier)\"&&r[0].value===\"continue\"&&(n.type=\"(negative-with-continue)\"),f.tokens.next.id===\"else\"&&(V(\"else\"),f.tokens.next.id===\"if\"||f.tokens.next.id===\"switch\"?At():_t(!0,!0)),this}),st(\"try\",function(){function t(){V(\"catch\"),V(\"(\"),f.funct[\"(scope)\"].stack(\"catchparams\");if(hn(f.tokens.next,[\"[\",\"{\"])){var e=Gt();r.each(e,function(e){e.id&&f.funct[\"(scope)\"].addParam(e.id,e,\"exception\")})}else f.tokens.next.type!==\"(identifier)\"?F(\"E030\",f.tokens.next,f.tokens.next.value):f.funct[\"(scope)\"].addParam(Ct(),f.tokens.curr,\"exception\");f.tokens.next.value===\"if\"&&(f.inMoz()||F(\"W118\",f.tokens.curr,\"catch filter\"),V(\"if\"),Q(0)),V(\")\"),_t(!1),f.funct[\"(scope)\"].unstack()}var e;_t(!0);while(f.tokens.next.id===\"catch\")$t(),e&&!f.inMoz()&&F(\"W118\",f.tokens.next,\"multiple catch blocks\"),t(),e=!0;if(f.tokens.next.id===\"finally\"){V(\"finally\"),_t(!0);return}return e||q(\"E021\",f.tokens.next,\"catch\",f.tokens.next.value),this}),st(\"while\",function(){var e=f.tokens.next;return f.funct[\"(breakage)\"]+=1,f.funct[\"(loopage)\"]+=1,$t(),V(\"(\"),Jt(Q(0)),V(\")\",e),_t(!0,!0),f.funct[\"(breakage)\"]-=1,f.funct[\"(loopage)\"]-=1,this}).labelled=!0,st(\"with\",function(){var e=f.tokens.next;return f.isStrict()?q(\"E010\",f.tokens.curr):f.option.withstmt||F(\"W085\",f.tokens.curr),V(\"(\"),Q(0),V(\")\",e),_t(!0,!0),this}),st(\"switch\",function(){var e=f.tokens.next,t=!1,n=!1;f.funct[\"(breakage)\"]+=1,V(\"(\"),Jt(Q(0)),V(\")\",e),e=f.tokens.next,V(\"{\"),f.tokens.next.from===g&&(n=!0),n||(g+=f.option.indent),this.cases=[];for(;;)switch(f.tokens.next.id){case\"case\":switch(f.funct[\"(verb)\"]){case\"yield\":case\"break\":case\"case\":case\"continue\":case\"return\":case\"switch\":case\"throw\":break;default:f.tokens.curr.caseFallsThrough||F(\"W086\",f.tokens.curr,\"case\")}V(\"case\"),this.cases.push(Q(0)),$t(),t=!0,V(\":\"),f.funct[\"(verb)\"]=\"case\";break;case\"default\":switch(f.funct[\"(verb)\"]){case\"yield\":case\"break\":case\"continue\":case\"return\":case\"throw\":break;default:this.cases.length&&(f.tokens.curr.caseFallsThrough||F(\"W086\",f.tokens.curr,\"default\"))}V(\"default\"),t=!0,V(\":\");break;case\"}\":n||(g-=f.option.indent),V(\"}\",e),f.funct[\"(breakage)\"]-=1,f.funct[\"(verb)\"]=undefined;return;case\"(end)\":q(\"E023\",f.tokens.next,\"}\");return;default:g+=f.option.indent;if(t)switch(f.tokens.curr.id){case\",\":q(\"E040\");return;case\":\":t=!1,Ot();break;default:q(\"E025\",f.tokens.curr);return}else{if(f.tokens.curr.id!==\":\"){q(\"E021\",f.tokens.next,\"case\",f.tokens.next.value);return}V(\":\"),q(\"E024\",f.tokens.curr,\":\"),Ot()}g-=f.option.indent}return this}).labelled=!0,it(\"debugger\",function(){return f.option.debug||F(\"W087\",this),this}).exps=!0,function(){var e=it(\"do\",function(){f.funct[\"(breakage)\"]+=1,f.funct[\"(loopage)\"]+=1,$t(),this.first=_t(!0,!0),V(\"while\");var e=f.tokens.next;return V(\"(\"),Jt(Q(0)),V(\")\",e),f.funct[\"(breakage)\"]-=1,f.funct[\"(loopage)\"]-=1,this});e.labelled=!0,e.exps=!0}(),st(\"for\",function(){var e,t=f.tokens.next,n=!1,i=null;t.value===\"each\"&&(i=t,V(\"each\"),f.inMoz()||F(\"W118\",f.tokens.curr,\"for each\")),$t(),V(\"(\");var s,o=0,u=[\"in\",\"of\"],a=0,l,c;hn(f.tokens.next,[\"{\",\"[\"])&&++a;do{s=W(o),++o,hn(s,[\"{\",\"[\"])?++a:hn(s,[\"}\",\"]\"])&&--a;if(a<0)break;a===0&&(!l&&pn(s,\",\")?l=s:!c&&pn(s,\"=\")&&(c=s))}while(a>0||!r.contains(u,s.value)&&s.value!==\";\"&&s.type!==\"(end)\");if(r.contains(u,s.value)){!f.inES6()&&s.value===\"of\"&&F(\"W104\",s,\"for of\",\"6\");var h=!c&&!l;c&&q(\"W133\",l,s.value,\"initializer is forbidden\"),l&&q(\"W133\",l,s.value,\"more than one ForBinding\"),f.tokens.next.id===\"var\"?(V(\"var\"),f.tokens.curr.fud({prefix:!0})):f.tokens.next.id===\"let\"||f.tokens.next.id===\"const\"?(V(f.tokens.next.id),n=!0,f.funct[\"(scope)\"].stack(),f.tokens.curr.fud({prefix:!0})):Object.create(rn).fud({prefix:!0,implied:\"for\",ignore:!h}),V(s.value),Q(20),V(\")\",t),s.value===\"in\"&&f.option.forin&&(f.forinifcheckneeded=!0,f.forinifchecks===undefined&&(f.forinifchecks=[]),f.forinifchecks.push({type:\"(none)\"})),f.funct[\"(breakage)\"]+=1,f.funct[\"(loopage)\"]+=1,e=_t(!0,!0);if(s.value===\"in\"&&f.option.forin){if(f.forinifchecks&&f.forinifchecks.length>0){var p=f.forinifchecks.pop();(e&&e.length>0&&(typeof e[0]!=\"object\"||e[0].value!==\"if\")||p.type===\"(positive)\"&&e.length>1||p.type===\"(negative)\")&&F(\"W089\",this)}f.forinifcheckneeded=!1}f.funct[\"(breakage)\"]-=1,f.funct[\"(loopage)\"]-=1}else{i&&q(\"E045\",i);if(f.tokens.next.id!==\";\")if(f.tokens.next.id===\"var\")V(\"var\"),f.tokens.curr.fud();else if(f.tokens.next.id===\"let\")V(\"let\"),n=!0,f.funct[\"(scope)\"].stack(),f.tokens.curr.fud();else for(;;){Q(0,\"for\");if(f.tokens.next.id!==\",\")break;l()}Z(f.tokens.curr),V(\";\"),f.funct[\"(loopage)\"]+=1,f.tokens.next.id!==\";\"&&Jt(Q(0)),Z(f.tokens.curr),V(\";\"),f.tokens.next.id===\";\"&&q(\"E021\",f.tokens.next,\")\",\";\");if(f.tokens.next.id!==\")\")for(;;){Q(0,\"for\");if(f.tokens.next.id!==\",\")break;l()}V(\")\",t),f.funct[\"(breakage)\"]+=1,_t(!0,!0),f.funct[\"(breakage)\"]-=1,f.funct[\"(loopage)\"]-=1}return n&&f.funct[\"(scope)\"].unstack(),this}).labelled=!0,it(\"break\",function(){var e=f.tokens.next.value;return f.option.asi||Z(this),f.tokens.next.id!==\";\"&&!f.tokens.next.reach&&f.tokens.curr.line===G(f.tokens.next)?(f.funct[\"(scope)\"].funct.hasBreakLabel(e)||F(\"W090\",f.tokens.next,e),this.first=f.tokens.next,V()):f.funct[\"(breakage)\"]===0&&F(\"W052\",f.tokens.next,this.value),kt(this),this}).exps=!0,it(\"continue\",function(){var e=f.tokens.next.value;return f.funct[\"(breakage)\"]===0&&F(\"W052\",f.tokens.next,this.value),f.funct[\"(loopage)\"]||F(\"W052\",f.tokens.next,this.value),f.option.asi||Z(this),f.tokens.next.id!==\";\"&&!f.tokens.next.reach&&f.tokens.curr.line===G(f.tokens.next)&&(f.funct[\"(scope)\"].funct.hasBreakLabel(e)||F(\"W090\",f.tokens.next,e),this.first=f.tokens.next,V()),kt(this),this}).exps=!0,it(\"return\",function(){return this.line===G(f.tokens.next)?f.tokens.next.id!==\";\"&&!f.tokens.next.reach&&(this.first=Q(0),this.first&&this.first.type===\"(punctuator)\"&&this.first.value===\"=\"&&!this.first.paren&&!f.option.boss&&I(\"W093\",this.first.line,this.first.character)):f.tokens.next.type===\"(punctuator)\"&&[\"[\",\"{\",\"+\",\"-\"].indexOf(f.tokens.next.value)>-1&&Z(this),kt(this),this}).exps=!0,function(e){e.exps=!0,e.lbp=25}(ut(\"yield\",function(){var e=f.tokens.prev;f.inES6(!0)&&!f.funct[\"(generator)\"]?(\"(catch)\"!==f.funct[\"(name)\"]||!f.funct[\"(context)\"][\"(generator)\"])&&q(\"E046\",f.tokens.curr,\"yield\"):f.inES6()||F(\"W104\",f.tokens.curr,\"yield\",\"6\"),f.funct[\"(generator)\"]=\"yielded\";var t=!1;f.tokens.next.value===\"*\"&&(t=!0,V(\"*\"));if(this.line===G(f.tokens.next)||!f.inMoz()){if(t||f.tokens.next.id!==\";\"&&!f.option.asi&&!f.tokens.next.reach&&f.tokens.next.nud)Y(f.tokens.curr,f.tokens.next),this.first=Q(10),this.first.type===\"(punctuator)\"&&this.first.value===\"=\"&&!this.first.paren&&!f.option.boss&&I(\"W093\",this.first.line,this.first.character);f.inMoz()&&f.tokens.next.id!==\")\"&&(e.lbp>30||!e.assign&&!J()||e.id===\"yield\")&&q(\"E050\",this)}else f.option.asi||Z(this);return this})),it(\"throw\",function(){return Z(this),this.first=Q(20),kt(this),this}).exps=!0,it(\"import\",function(){f.inES6()||F(\"W119\",f.tokens.curr,\"import\",\"6\");if(f.tokens.next.type===\"(string)\")return V(\"(string)\"),this;if(f.tokens.next.identifier){this.name=Ct(),f.funct[\"(scope)\"].addlabel(this.name,{type:\"const\",token:f.tokens.curr});if(f.tokens.next.value!==\",\")return V(\"from\"),V(\"(string)\"),this;V(\",\")}if(f.tokens.next.id===\"*\")V(\"*\"),V(\"as\"),f.tokens.next.identifier&&(this.name=Ct(),f.funct[\"(scope)\"].addlabel(this.name,{type:\"const\",token:f.tokens.curr}));else{V(\"{\");for(;;){if(f.tokens.next.value===\"}\"){V(\"}\");break}var e;f.tokens.next.type===\"default\"?(e=\"default\",V(\"default\")):e=Ct(),f.tokens.next.value===\"as\"&&(V(\"as\"),e=Ct()),f.funct[\"(scope)\"].addlabel(e,{type:\"const\",token:f.tokens.curr});if(f.tokens.next.value!==\",\"){if(f.tokens.next.value===\"}\"){V(\"}\");break}q(\"E024\",f.tokens.next,f.tokens.next.value);break}V(\",\")}}return V(\"from\"),V(\"(string)\"),this}).exps=!0,it(\"export\",function(){var e=!0,t,n;f.inES6()||(F(\"W119\",f.tokens.curr,\"export\",\"6\"),e=!1),f.funct[\"(scope)\"].block.isGlobal()||(q(\"E053\",f.tokens.curr),e=!1);if(f.tokens.next.value===\"*\")return V(\"*\"),V(\"from\"),V(\"(string)\"),this;if(f.tokens.next.type===\"default\"){f.nameStack.set(f.tokens.next),V(\"default\");var r=f.tokens.next.id;if(r===\"function\"||r===\"class\")this.block=!0;return t=W(),Q(10),n=t.value,this.block&&(f.funct[\"(scope)\"].addlabel(n,{type:r,token:t}),f.funct[\"(scope)\"].setExported(n,t)),this}if(f.tokens.next.value===\"{\"){V(\"{\");var i=[];for(;;){f.tokens.next.identifier||q(\"E030\",f.tokens.next,f.tokens.next.value),V(),i.push(f.tokens.curr),f.tokens.next.value===\"as\"&&(V(\"as\"),f.tokens.next.identifier||q(\"E030\",f.tokens.next,f.tokens.next.value),V());if(f.tokens.next.value!==\",\"){if(f.tokens.next.value===\"}\"){V(\"}\");break}q(\"E024\",f.tokens.next,f.tokens.next.value);break}V(\",\")}return f.tokens.next.value===\"from\"?(V(\"from\"),V(\"(string)\")):e&&i.forEach(function(e){f.funct[\"(scope)\"].setExported(e.value,e)}),this}if(f.tokens.next.id===\"var\")V(\"var\"),f.tokens.curr.fud({inexport:!0});else if(f.tokens.next.id===\"let\")V(\"let\"),f.tokens.curr.fud({inexport:!0});else if(f.tokens.next.id===\"const\")V(\"const\"),f.tokens.curr.fud({inexport:!0});else if(f.tokens.next.id===\"function\")this.block=!0,V(\"function\"),f.syntax[\"function\"].fud({inexport:!0});else if(f.tokens.next.id===\"class\"){this.block=!0,V(\"class\");var s=f.tokens.next;f.syntax[\"class\"].fud(),f.funct[\"(scope)\"].setExported(s.value,s)}else q(\"E024\",f.tokens.next,f.tokens.next.value);return this}).exps=!0,lt(\"abstract\"),lt(\"boolean\"),lt(\"byte\"),lt(\"char\"),lt(\"class\",{es5:!0,nud:sn}),lt(\"double\"),lt(\"enum\",{es5:!0}),lt(\"export\",{es5:!0}),lt(\"extends\",{es5:!0}),lt(\"final\"),lt(\"float\"),lt(\"goto\"),lt(\"implements\",{es5:!0,strictOnly:!0}),lt(\"import\",{es5:!0}),lt(\"int\"),lt(\"interface\",{es5:!0,strictOnly:!0}),lt(\"long\"),lt(\"native\"),lt(\"package\",{es5:!0,strictOnly:!0}),lt(\"private\",{es5:!0,strictOnly:!0}),lt(\"protected\",{es5:!0,strictOnly:!0}),lt(\"public\",{es5:!0,strictOnly:!0}),lt(\"short\"),lt(\"static\",{es5:!0,strictOnly:!0}),lt(\"super\",{es5:!0}),lt(\"synchronized\"),lt(\"transient\"),lt(\"volatile\");var an=function(){var e,t,n,r=-1,i=0,s={};hn(f.tokens.curr,[\"[\",\"{\"])&&(i+=1);do{n=r===-1?f.tokens.curr:e,e=r===-1?f.tokens.next:W(r),t=W(r+1),r+=1,hn(e,[\"[\",\"{\"])?i+=1:hn(e,[\"]\",\"}\"])&&(i-=1);if(i===1&&e.identifier&&e.value===\"for\"&&!pn(n,\".\")){s.isCompArray=!0,s.notJson=!0;break}if(i===0&&hn(e,[\"}\",\"]\"])){if(t.value===\"=\"){s.isDestAssign=!0,s.notJson=!0;break}if(t.value===\".\"){s.notJson=!0;break}}pn(e,\";\")&&(s.isBlock=!0,s.notJson=!0)}while(i>0&&e.id!==\"(end)\");return s},vn=function(){function i(e){var t=n.variables.filter(function(t){if(t.value===e)return t.undef=!1,e}).length;return t!==0}function s(e){var t=n.variables.filter(function(t){if(t.value===e&&!t.undef)return t.unused===!0&&(t.unused=!1),e}).length;return t===0}var e=function(){this.mode=\"use\",this.variables=[]},t=[],n;return{stack:function(){n=new e,t.push(n)},unstack:function(){n.variables.filter(function(e){e.unused&&F(\"W098\",e.token,e.raw_text||e.value),e.undef&&f.funct[\"(scope)\"].block.use(e.value,e.token)}),t.splice(-1,1),n=t[t.length-1]},setState:function(e){r.contains([\"use\",\"define\",\"generate\",\"filter\"],e)&&(n.mode=e)},check:function(e){if(!n)return;return n&&n.mode===\"use\"?(s(e)&&n.variables.push({funct:f.funct,token:f.tokens.curr,value:e,undef:!0,unused:!1}),!0):n&&n.mode===\"define\"?(i(e)||n.variables.push({funct:f.funct,token:f.tokens.curr,value:e,undef:!1,unused:!0}),!0):n&&n.mode===\"generate\"?(f.funct[\"(scope)\"].block.use(e,f.tokens.curr),!0):n&&n.mode===\"filter\"?(s(e)&&f.funct[\"(scope)\"].block.use(e,f.tokens.curr),!0):!1}}},gn=function(e){return e.replace(/[-\\/\\\\^$*+?.()|[\\]{}]/g,\"\\\\$&\")},yn=function(t,i,o){function U(e,t){if(!e)return;!Array.isArray(e)&&typeof e==\"object\"&&(e=Object.keys(e)),e.forEach(t)}var a,l,c,d,A,O,M={},P={};i=r.clone(i),f.reset(),i&&i.scope?p.scope=i.scope:(p.errors=[],p.undefs=[],p.internals=[],p.blacklist={},p.scope=\"(main)\"),S=Object.create(null),D(S,s.ecmaIdentifiers[3]),D(S,s.reservedVars),D(S,o||{}),n=Object.create(null);var j=Object.create(null);if(i){U(i.predef||null,function(e){var t,n;e[0]===\"-\"?(t=e.slice(1),p.blacklist[t]=t,delete S[t]):(n=Object.getOwnPropertyDescriptor(i.predef,e),S[e]=n?n.value:!1)}),U(i.exported||null,function(e){j[e]=!0}),delete i.predef,delete i.exported,O=Object.keys(i);for(c=0;c<O.length;c++)if(/^-W\\d{3}$/g.test(O[c]))P[O[c].slice(1)]=!0;else{var z=O[c];M[z]=i[z],(z===\"esversion\"&&i[z]===5||z===\"es5\"&&i[z])&&F(\"I003\"),O[c]===\"newcap\"&&i[z]===!1&&(M[\"(explicitNewcap)\"]=!0)}}f.option=M,f.ignored=P,f.option.indent=f.option.indent||4,f.option.maxerr=f.option.maxerr||50,g=1;var W=h(f,S,j,n);W.on(\"warning\",function(e){F.apply(null,[e.code,e.token].concat(e.data))}),W.on(\"error\",function(e){q.apply(null,[e.code,e.token].concat(e.data))}),f.funct=Rt(\"(global)\",null,{\"(global)\":!0,\"(scope)\":W,\"(comparray)\":vn(),\"(metrics)\":Vt(f.tokens.next)}),v=[f.funct],T=[],x=null,w={},E=null,m=!1,y=[];if(!L(t)&&!Array.isArray(t))return R(\"E004\",0),!1;e={get isJSON(){return f.jsonMode},getOption:function(e){return f.option[e]||null},getCache:function(e){return f.cache[e]},setCache:function(e,t){f.cache[e]=t},warn:function(e,t){I.apply(null,[e,t.line,t.char].concat(t.data))},on:function(e,t){e.split(\" \").forEach(function(e){C.on(e,t)}.bind(this))}},C.removeAllListeners(),(N||[]).forEach(function(t){t(e)}),f.tokens.prev=f.tokens.curr=f.tokens.next=f.syntax[\"(begin)\"],i&&i.ignoreDelimiters&&(Array.isArray(i.ignoreDelimiters)||(i.ignoreDelimiters=[i.ignoreDelimiters]),i.ignoreDelimiters.forEach(function(e){if(!e.start||!e.end)return;d=gn(e.start)+\"[\\\\s\\\\S]*?\"+gn(e.end),A=new RegExp(d,\"ig\"),t=t.replace(A,function(e){return e.replace(/./g,\" \")})})),b=new u(t),b.on(\"warning\",function(e){I.apply(null,[e.code,e.line,e.character].concat(e.data))}),b.on(\"error\",function(e){R.apply(null,[e.code,e.line,e.character].concat(e.data))}),b.on(\"fatal\",function(e){B(\"E041\",e.line,e.from)}),b.on(\"Identifier\",function(e){C.emit(\"Identifier\",e)}),b.on(\"String\",function(e){C.emit(\"String\",e)}),b.on(\"Number\",function(e){C.emit(\"Number\",e)}),b.start();for(var X in i)r.has(i,X)&&k(X,f.tokens.curr);H(),D(S,o||{}),tt.first=!0;try{V();switch(f.tokens.next.id){case\"{\":case\"[\":dn();break;default:Mt(),f.directive[\"use strict\"]&&f.option.strict!==\"global\"&&F(\"W097\",f.tokens.prev),Ot()}f.tokens.next.id!==\"(end)\"&&B(\"E041\",f.tokens.curr.line),f.funct[\"(scope)\"].unstack()}catch($){if(!$||$.name!==\"JSHintError\")throw $;var J=f.tokens.next||{};p.errors.push({scope:\"(main)\",raw:$.raw,code:$.code,reason:$.message,line:$.line||J.line,character:$.character||J.from},null)}if(p.scope===\"(main)\"){i=i||{};for(a=0;a<p.internals.length;a+=1)l=p.internals[a],i.scope=l.elem,yn(l.value,i,o)}return p.errors.length===0};return yn.addModule=function(e){N.push(e)},yn.addModule(l.register),yn.data=function(){var e={functions:[],options:f.option},t,n,r,i,s,o;yn.errors.length&&(e.errors=yn.errors),f.jsonMode&&(e.json=!0);var u=f.funct[\"(scope)\"].getImpliedGlobals();u.length>0&&(e.implieds=u),T.length>0&&(e.urls=T),o=f.funct[\"(scope)\"].getUsedOrDefinedGlobals(),o.length>0&&(e.globals=o);for(r=1;r<v.length;r+=1){n=v[r],t={};for(i=0;i<d.length;i+=1)t[d[i]]=[];for(i=0;i<d.length;i+=1)t[d[i]].length===0&&delete t[d[i]];t.name=n[\"(name)\"],t.param=n[\"(params)\"],t.line=n[\"(line)\"],t.character=n[\"(character)\"],t.last=n[\"(last)\"],t.lastcharacter=n[\"(lastcharacter)\"],t.metrics={complexity:n[\"(metrics)\"].ComplexityCount,parameters:n[\"(metrics)\"].arity,statements:n[\"(metrics)\"].statementCount},e.functions.push(t)}var a=f.funct[\"(scope)\"].getUnuseds();a.length>0&&(e.unused=a);for(s in w)if(typeof w[s]==\"number\"){e.member=w;break}return e},yn.jshint=yn,yn}();typeof n==\"object\"&&n&&(n.JSHINT=p)},{\"../lodash\":\"/node_modules/jshint/lodash.js\",\"./lex.js\":\"/node_modules/jshint/src/lex.js\",\"./messages.js\":\"/node_modules/jshint/src/messages.js\",\"./options.js\":\"/node_modules/jshint/src/options.js\",\"./reg.js\":\"/node_modules/jshint/src/reg.js\",\"./scope-manager.js\":\"/node_modules/jshint/src/scope-manager.js\",\"./state.js\":\"/node_modules/jshint/src/state.js\",\"./style.js\":\"/node_modules/jshint/src/style.js\",\"./vars.js\":\"/node_modules/jshint/src/vars.js\",events:\"/node_modules/browserify/node_modules/events/events.js\"}],\"/node_modules/jshint/src/lex.js\":[function(e,t,n){\"use strict\";function h(){var e=[];return{push:function(t){e.push(t)},check:function(){for(var t=0;t<e.length;++t)e[t]();e.splice(0,e.length)}}}function p(e){var t=e;typeof t==\"string\"&&(t=t.replace(/\\r\\n/g,\"\\n\").replace(/\\r/g,\"\\n\").split(\"\\n\")),t[0]&&t[0].substr(0,2)===\"#!\"&&(t[0].indexOf(\"node\")!==-1&&(o.option.node=!0),t[0]=\"\"),this.emitter=new i.EventEmitter,this.source=e,this.setLines(t),this.prereg=!0,this.line=0,this.char=1,this.from=1,this.input=\"\",this.inComment=!1,this.context=[],this.templateStarts=[];for(var n=0;n<o.option.indent;n+=1)o.tab+=\" \";this.ignoreLinterErrors=!1}var r=e(\"../lodash\"),i=e(\"events\"),s=e(\"./reg.js\"),o=e(\"./state.js\").state,u=e(\"../data/ascii-identifier-data.js\"),a=u.asciiIdentifierStartTable,f=u.asciiIdentifierPartTable,l={Identifier:1,Punctuator:2,NumericLiteral:3,StringLiteral:4,Comment:5,Keyword:6,NullLiteral:7,BooleanLiteral:8,RegExp:9,TemplateHead:10,TemplateMiddle:11,TemplateTail:12,NoSubstTemplate:13},c={Block:1,Template:2};p.prototype={_lines:[],inContext:function(e){return this.context.length>0&&this.context[this.context.length-1].type===e},pushContext:function(e){this.context.push({type:e})},popContext:function(){return this.context.pop()},isContext:function(e){return this.context.length>0&&this.context[this.context.length-1]===e},currentContext:function(){return this.context.length>0&&this.context[this.context.length-1]},getLines:function(){return this._lines=o.lines,this._lines},setLines:function(e){this._lines=e,o.lines=this._lines},peek:function(e){return this.input.charAt(e||0)},skip:function(e){e=e||1,this.char+=e,this.input=this.input.slice(e)},on:function(e,t){e.split(\" \").forEach(function(e){this.emitter.on(e,t)}.bind(this))},trigger:function(){this.emitter.emit.apply(this.emitter,Array.prototype.slice.call(arguments))},triggerAsync:function(e,t,n,r){n.push(function(){r()&&this.trigger(e,t)}.bind(this))},scanPunctuator:function(){var e=this.peek(),t,n,r;switch(e){case\".\":if(/^[0-9]$/.test(this.peek(1)))return null;if(this.peek(1)===\".\"&&this.peek(2)===\".\")return{type:l.Punctuator,value:\"...\"};case\"(\":case\")\":case\";\":case\",\":case\"[\":case\"]\":case\":\":case\"~\":case\"?\":return{type:l.Punctuator,value:e};case\"{\":return this.pushContext(c.Block),{type:l.Punctuator,value:e};case\"}\":return this.inContext(c.Block)&&this.popContext(),{type:l.Punctuator,value:e};case\"#\":return{type:l.Punctuator,value:e};case\"\":return null}return t=this.peek(1),n=this.peek(2),r=this.peek(3),e===\">\"&&t===\">\"&&n===\">\"&&r===\"=\"?{type:l.Punctuator,value:\">>>=\"}:e===\"=\"&&t===\"=\"&&n===\"=\"?{type:l.Punctuator,value:\"===\"}:e===\"!\"&&t===\"=\"&&n===\"=\"?{type:l.Punctuator,value:\"!==\"}:e===\">\"&&t===\">\"&&n===\">\"?{type:l.Punctuator,value:\">>>\"}:e===\"<\"&&t===\"<\"&&n===\"=\"?{type:l.Punctuator,value:\"<<=\"}:e===\">\"&&t===\">\"&&n===\"=\"?{type:l.Punctuator,value:\">>=\"}:e===\"=\"&&t===\">\"?{type:l.Punctuator,value:e+t}:e===t&&\"+-<>&|\".indexOf(e)>=0?{type:l.Punctuator,value:e+t}:\"<>=!+-*%&|^\".indexOf(e)>=0?t===\"=\"?{type:l.Punctuator,value:e+t}:{type:l.Punctuator,value:e}:e===\"/\"?t===\"=\"?{type:l.Punctuator,value:\"/=\"}:{type:l.Punctuator,value:\"/\"}:null},scanComments:function(){function u(e,t,n){var r=[\"jshint\",\"jslint\",\"members\",\"member\",\"globals\",\"global\",\"exported\"],i=!1,u=e+t,a=\"plain\";return n=n||{},n.isMultiline&&(u+=\"*/\"),t=t.replace(/\\n/g,\" \"),e===\"/*\"&&s.fallsThrough.test(t)&&(i=!0,a=\"falls through\"),r.forEach(function(n){if(i)return;if(e===\"//\"&&n!==\"jshint\")return;t.charAt(n.length)===\" \"&&t.substr(0,n.length)===n&&(i=!0,e+=n,t=t.substr(n.length)),!i&&t.charAt(0)===\" \"&&t.charAt(n.length+1)===\" \"&&t.substr(1,n.length)===n&&(i=!0,e=e+\" \"+n,t=t.substr(n.length+1));if(!i)return;switch(n){case\"member\":a=\"members\";break;case\"global\":a=\"globals\";break;default:var r=t.split(\":\").map(function(e){return e.replace(/^\\s+/,\"\").replace(/\\s+$/,\"\")});if(r.length===2)switch(r[0]){case\"ignore\":switch(r[1]){case\"start\":o.ignoringLinterErrors=!0,i=!1;break;case\"end\":o.ignoringLinterErrors=!1,i=!1}}a=n}}),{type:l.Comment,commentType:a,value:u,body:t,isSpecial:i,isMultiline:n.isMultiline||!1,isMalformed:n.isMalformed||!1}}var e=this.peek(),t=this.peek(1),n=this.input.substr(2),r=this.line,i=this.char,o=this;if(e===\"*\"&&t===\"/\")return this.trigger(\"error\",{code:\"E018\",line:r,character:i}),this.skip(2),null;if(e!==\"/\"||t!==\"*\"&&t!==\"/\")return null;if(t===\"/\")return this.skip(this.input.length),u(\"//\",n);var a=\"\";if(t===\"*\"){this.inComment=!0,this.skip(2);while(this.peek()!==\"*\"||this.peek(1)!==\"/\")if(this.peek()===\"\"){a+=\"\\n\";if(!this.nextLine())return this.trigger(\"error\",{code:\"E017\",line:r,character:i}),this.inComment=!1,u(\"/*\",a,{isMultiline:!0,isMalformed:!0})}else a+=this.peek(),this.skip();return this.skip(2),this.inComment=!1,u(\"/*\",a,{isMultiline:!0})}},scanKeyword:function(){var e=/^[a-zA-Z_$][a-zA-Z0-9_$]*/.exec(this.input),t=[\"if\",\"in\",\"do\",\"var\",\"for\",\"new\",\"try\",\"let\",\"this\",\"else\",\"case\",\"void\",\"with\",\"enum\",\"while\",\"break\",\"catch\",\"throw\",\"const\",\"yield\",\"class\",\"super\",\"return\",\"typeof\",\"delete\",\"switch\",\"export\",\"import\",\"default\",\"finally\",\"extends\",\"function\",\"continue\",\"debugger\",\"instanceof\"];return e&&t.indexOf(e[0])>=0?{type:l.Keyword,value:e[0]}:null},scanIdentifier:function(){function i(e){return e>256}function s(e){return e>256}function o(e){return/^[0-9a-fA-F]$/.test(e)}function p(e){return e.replace(/\\\\u([0-9a-fA-F]{4})/g,function(e,t){return String.fromCharCode(parseInt(t,16))})}var e=\"\",t=0,n,r,u=function(){t+=1;if(this.peek(t)!==\"u\")return null;var e=this.peek(t+1),n=this.peek(t+2),r=this.peek(t+3),i=this.peek(t+4),u;return o(e)&&o(n)&&o(r)&&o(i)?(u=parseInt(e+n+r+i,16),f[u]||s(u)?(t+=5,\"\\\\u\"+e+n+r+i):null):null}.bind(this),c=function(){var e=this.peek(t),n=e.charCodeAt(0);return n===92?u():n<128?a[n]?(t+=1,e):null:i(n)?(t+=1,e):null}.bind(this),h=function(){var e=this.peek(t),n=e.charCodeAt(0);return n===92?u():n<128?f[n]?(t+=1,e):null:s(n)?(t+=1,e):null}.bind(this);r=c();if(r===null)return null;e=r;for(;;){r=h();if(r===null)break;e+=r}switch(e){case\"true\":case\"false\":n=l.BooleanLiteral;break;case\"null\":n=l.NullLiteral;break;default:n=l.Identifier}return{type:n,value:p(e),text:e,tokenLength:e.length}},scanNumericLiteral:function(){function f(e){return/^[0-9]$/.test(e)}function c(e){return/^[0-7]$/.test(e)}function h(e){return/^[01]$/.test(e)}function p(e){return/^[0-9a-fA-F]$/.test(e)}function d(e){return e===\"$\"||e===\"_\"||e===\"\\\\\"||e>=\"a\"&&e<=\"z\"||e>=\"A\"&&e<=\"Z\"}var e=0,t=\"\",n=this.input.length,r=this.peek(e),i,s=f,u=10,a=!1;if(r!==\".\"&&!f(r))return null;if(r!==\".\"){t=this.peek(e),e+=1,r=this.peek(e);if(t===\"0\"){if(r===\"x\"||r===\"X\")s=p,u=16,e+=1,t+=r;if(r===\"o\"||r===\"O\")s=c,u=8,o.inES6(!0)||this.trigger(\"warning\",{code:\"W119\",line:this.line,character:this.char,data:[\"Octal integer literal\",\"6\"]}),e+=1,t+=r;if(r===\"b\"||r===\"B\")s=h,u=2,o.inES6(!0)||this.trigger(\"warning\",{code:\"W119\",line:this.line,character:this.char,data:[\"Binary integer literal\",\"6\"]}),e+=1,t+=r;c(r)&&(s=c,u=8,a=!0,i=!1,e+=1,t+=r),!c(r)&&f(r)&&(e+=1,t+=r)}while(e<n){r=this.peek(e);if(a&&f(r))i=!0;else if(!s(r))break;t+=r,e+=1}if(s!==f){if(!a&&t.length<=2)return{type:l.NumericLiteral,value:t,isMalformed:!0};if(e<n){r=this.peek(e);if(d(r))return null}return{type:l.NumericLiteral,value:t,base:u,isLegacy:a,isMalformed:!1}}}if(r===\".\"){t+=r,e+=1;while(e<n){r=this.peek(e);if(!f(r))break;t+=r,e+=1}}if(r===\"e\"||r===\"E\"){t+=r,e+=1,r=this.peek(e);if(r===\"+\"||r===\"-\")t+=this.peek(e),e+=1;r=this.peek(e);if(!f(r))return null;t+=r,e+=1;while(e<n){r=this.peek(e);if(!f(r))break;t+=r,e+=1}}if(e<n){r=this.peek(e);if(d(r))return null}return{type:l.NumericLiteral,value:t,base:u,isMalformed:!isFinite(t)}},scanEscapeSequence:function(e){var t=!1,n=1;this.skip();var r=this.peek();switch(r){case\"'\":this.triggerAsync(\"warning\",{code:\"W114\",line:this.line,character:this.char,data:[\"\\\\'\"]},e,function(){return o.jsonMode});break;case\"b\":r=\"\\\\b\";break;case\"f\":r=\"\\\\f\";break;case\"n\":r=\"\\\\n\";break;case\"r\":r=\"\\\\r\";break;case\"t\":r=\"\\\\t\";break;case\"0\":r=\"\\\\0\";var i=parseInt(this.peek(1),10);this.triggerAsync(\"warning\",{code:\"W115\",line:this.line,character:this.char},e,function(){return i>=0&&i<=7&&o.isStrict()});break;case\"u\":var s=this.input.substr(1,4),u=parseInt(s,16);isNaN(u)&&this.trigger(\"warning\",{code:\"W052\",line:this.line,character:this.char,data:[\"u\"+s]}),r=String.fromCharCode(u),n=5;break;case\"v\":this.triggerAsync(\"warning\",{code:\"W114\",line:this.line,character:this.char,data:[\"\\\\v\"]},e,function(){return o.jsonMode}),r=\"\u000b\";break;case\"x\":var a=parseInt(this.input.substr(1,2),16);this.triggerAsync(\"warning\",{code:\"W114\",line:this.line,character:this.char,data:[\"\\\\x-\"]},e,function(){return o.jsonMode}),r=String.fromCharCode(a),n=3;break;case\"\\\\\":r=\"\\\\\\\\\";break;case'\"':r='\\\\\"';break;case\"/\":break;case\"\":t=!0,r=\"\"}return{\"char\":r,jump:n,allowNewLine:t}},scanTemplateLiteral:function(e){var t,n=\"\",r,i=this.line,s=this.char,u=this.templateStarts.length;if(!o.inES6(!0))return null;if(this.peek()===\"`\")t=l.TemplateHead,this.templateStarts.push({line:this.line,\"char\":this.char}),u=this.templateStarts.length,this.skip(1),this.pushContext(c.Template);else{if(!this.inContext(c.Template)||this.peek()!==\"}\")return null;t=l.TemplateMiddle}while(this.peek()!==\"`\"){while((r=this.peek())===\"\"){n+=\"\\n\";if(!this.nextLine()){var a=this.templateStarts.pop();return this.trigger(\"error\",{code:\"E052\",line:a.line,character:a.char}),{type:t,value:n,startLine:i,startChar:s,isUnclosed:!0,depth:u,context:this.popContext()}}}if(r===\"$\"&&this.peek(1)===\"{\")return n+=\"${\",this.skip(2),{type:t,value:n,startLine:i,startChar:s,isUnclosed:!1,depth:u,context:this.currentContext()};if(r===\"\\\\\"){var f=this.scanEscapeSequence(e);n+=f.char,this.skip(f.jump)}else r!==\"`\"&&(n+=r,this.skip(1))}return t=t===l.TemplateHead?l.NoSubstTemplate:l.TemplateTail,this.skip(1),this.templateStarts.pop(),{type:t,value:n,startLine:i,startChar:s,isUnclosed:!1,depth:u,context:this.popContext()}},scanStringLiteral:function(e){var t=this.peek();if(t!=='\"'&&t!==\"'\")return null;this.triggerAsync(\"warning\",{code:\"W108\",line:this.line,character:this.char},e,function(){return o.jsonMode&&t!=='\"'});var n=\"\",r=this.line,i=this.char,s=!1;this.skip();while(this.peek()!==t)if(this.peek()===\"\"){s?(s=!1,this.triggerAsync(\"warning\",{code:\"W043\",line:this.line,character:this.char},e,function(){return!o.option.multistr}),this.triggerAsync(\"warning\",{code:\"W042\",line:this.line,character:this.char},e,function(){return o.jsonMode&&o.option.multistr})):this.trigger(\"warning\",{code:\"W112\",line:this.line,character:this.char});if(!this.nextLine())return this.trigger(\"error\",{code:\"E029\",line:r,character:i}),{type:l.StringLiteral,value:n,startLine:r,startChar:i,isUnclosed:!0,quote:t}}else{s=!1;var u=this.peek(),a=1;u<\" \"&&this.trigger(\"warning\",{code:\"W113\",line:this.line,character:this.char,data:[\"<non-printable>\"]});if(u===\"\\\\\"){var f=this.scanEscapeSequence(e);u=f.char,a=f.jump,s=f.allowNewLine}n+=u,this.skip(a)}return this.skip(),{type:l.StringLiteral,value:n,startLine:r,startChar:i,isUnclosed:!1,quote:t}},scanRegExp:function(){var e=0,t=this.input.length,n=this.peek(),r=n,i=\"\",s=[],o=!1,u=!1,a,f=function(){n<\" \"&&(o=!0,this.trigger(\"warning\",{code:\"W048\",line:this.line,character:this.char})),n===\"<\"&&(o=!0,this.trigger(\"warning\",{code:\"W049\",line:this.line,character:this.char,data:[n]}))}.bind(this);if(!this.prereg||n!==\"/\")return null;e+=1,a=!1;while(e<t){n=this.peek(e),r+=n,i+=n;if(u){n===\"]\"&&(this.peek(e-1)!==\"\\\\\"||this.peek(e-2)===\"\\\\\")&&(u=!1),n===\"\\\\\"&&(e+=1,n=this.peek(e),i+=n,r+=n,f()),e+=1;continue}if(n===\"\\\\\"){e+=1,n=this.peek(e),i+=n,r+=n,f();if(n===\"/\"){e+=1;continue}if(n===\"[\"){e+=1;continue}}if(n===\"[\"){u=!0,e+=1;continue}if(n===\"/\"){i=i.substr(0,i.length-1),a=!0,e+=1;break}e+=1}if(!a)return this.trigger(\"error\",{code:\"E015\",line:this.line,character:this.from}),void this.trigger(\"fatal\",{line:this.line,from:this.from});while(e<t){n=this.peek(e);if(!/[gim]/.test(n))break;s.push(n),r+=n,e+=1}try{new RegExp(i,s.join(\"\"))}catch(c){o=!0,this.trigger(\"error\",{code:\"E016\",line:this.line,character:this.char,data:[c.message]})}return{type:l.RegExp,value:r,flags:s,isMalformed:o}},scanNonBreakingSpaces:function(){return o.option.nonbsp?this.input.search(/(\\u00A0)/):-1},scanUnsafeChars:function(){return this.input.search(s.unsafeChars)},next:function(e){this.from=this.char;var t;if(/\\s/.test(this.peek())){t=this.char;while(/\\s/.test(this.peek()))this.from+=1,this.skip()}var n=this.scanComments()||this.scanStringLiteral(e)||this.scanTemplateLiteral(e);return n?n:(n=this.scanRegExp()||this.scanPunctuator()||this.scanKeyword()||this.scanIdentifier()||this.scanNumericLiteral(),n?(this.skip(n.tokenLength||n.value.length),n):null)},nextLine:function(){var e;if(this.line>=this.getLines().length)return!1;this.input=this.getLines()[this.line],this.line+=1,this.char=1,this.from=1;var t=this.input.trim(),n=function(){return r.some(arguments,function(e){return t.indexOf(e)===0})},i=function(){return r.some(arguments,function(e){return t.indexOf(e,t.length-e.length)!==-1})};this.ignoringLinterErrors===!0&&!n(\"/*\",\"//\")&&(!this.inComment||!i(\"*/\"))&&(this.input=\"\"),e=this.scanNonBreakingSpaces(),e>=0&&this.trigger(\"warning\",{code:\"W125\",line:this.line,character:e+1}),this.input=this.input.replace(/\\t/g,o.tab),e=this.scanUnsafeChars(),e>=0&&this.trigger(\"warning\",{code:\"W100\",line:this.line,character:e});if(!this.ignoringLinterErrors&&o.option.maxlen&&o.option.maxlen<this.input.length){var u=this.inComment||n.call(t,\"//\")||n.call(t,\"/*\"),a=!u||!s.maxlenException.test(t);a&&this.trigger(\"warning\",{code:\"W101\",line:this.line,character:this.input.length})}return!0},start:function(){this.nextLine()},token:function(){function n(e,t){if(!e.reserved)return!1;var n=e.meta;if(n&&n.isFutureReservedWord&&o.inES5()){if(!n.es5)return!1;if(n.strictOnly&&!o.option.strict&&!o.isStrict())return!1;if(t)return!1}return!0}var e=h(),t,i=function(t,i,s,u){var a;t!==\"(endline)\"&&t!==\"(end)\"&&(this.prereg=!1);if(t===\"(punctuator)\"){switch(i){case\".\":case\")\":case\"~\":case\"#\":case\"]\":case\"++\":case\"--\":this.prereg=!1;break;default:this.prereg=!0}a=Object.create(o.syntax[i]||o.syntax[\"(error)\"])}if(t===\"(identifier)\"){if(i===\"return\"||i===\"case\"||i===\"typeof\")this.prereg=!0;r.has(o.syntax,i)&&(a=Object.create(o.syntax[i]||o.syntax[\"(error)\"]),n(a,s&&t===\"(identifier)\")||(a=null))}return a||(a=Object.create(o.syntax[t])),a.identifier=t===\"(identifier)\",a.type=a.type||t,a.value=i,a.line=this.line,a.character=this.char,a.from=this.from,a.identifier&&u&&(a.raw_text=u.text||u.value),u&&u.startLine&&u.startLine!==this.line&&(a.startLine=u.startLine),u&&u.context&&(a.context=u.context),u&&u.depth&&(a.depth=u.depth),u&&u.isUnclosed&&(a.isUnclosed=u.isUnclosed),s&&a.identifier&&(a.isProperty=s),a.check=e.check,a}.bind(this);for(;;){if(!this.input.length)return this.nextLine()?i(\"(endline)\",\"\"):this.exhausted?null:(this.exhausted=!0,i(\"(end)\",\"\"));t=this.next(e);if(!t){this.input.length&&(this.trigger(\"error\",{code:\"E024\",line:this.line,character:this.char,data:[this.peek()]}),this.input=\"\");continue}switch(t.type){case l.StringLiteral:return this.triggerAsync(\"String\",{line:this.line,\"char\":this.char,from:this.from,startLine:t.startLine,startChar:t.startChar,value:t.value,quote:t.quote},e,function(){return!0}),i(\"(string)\",t.value,null,t);case l.TemplateHead:return this.trigger(\"TemplateHead\",{line:this.line,\"char\":this.char,from:this.from,startLine:t.startLine,startChar:t.startChar,value:t.value}),i(\"(template)\",t.value,null,t);case l.TemplateMiddle:return this.trigger(\"TemplateMiddle\",{line:this.line,\"char\":this.char,from:this.from,startLine:t.startLine,startChar:t.startChar,value:t.value}),i(\"(template middle)\",t.value,null,t);case l.TemplateTail:return this.trigger(\"TemplateTail\",{line:this.line,\"char\":this.char,from:this.from,startLine:t.startLine,startChar:t.startChar,value:t.value}),i(\"(template tail)\",t.value,null,t);case l.NoSubstTemplate:return this.trigger(\"NoSubstTemplate\",{line:this.line,\"char\":this.char,from:this.from,startLine:t.startLine,startChar:t.startChar,value:t.value}),i(\"(no subst template)\",t.value,null,t);case l.Identifier:this.triggerAsync(\"Identifier\",{line:this.line,\"char\":this.char,from:this.form,name:t.value,raw_name:t.text,isProperty:o.tokens.curr.id===\".\"},e,function(){return!0});case l.Keyword:case l.NullLiteral:case l.BooleanLiteral:return i(\"(identifier)\",t.value,o.tokens.curr.id===\".\",t);case l.NumericLiteral:return t.isMalformed&&this.trigger(\"warning\",{code:\"W045\",line:this.line,character:this.char,data:[t.value]}),this.triggerAsync(\"warning\",{code:\"W114\",line:this.line,character:this.char,data:[\"0x-\"]},e,function(){return t.base===16&&o.jsonMode}),this.triggerAsync(\"warning\",{code:\"W115\",line:this.line,character:this.char},e,function(){return o.isStrict()&&t.base===8&&t.isLegacy}),this.trigger(\"Number\",{line:this.line,\"char\":this.char,from:this.from,value:t.value,base:t.base,isMalformed:t.malformed}),i(\"(number)\",t.value);case l.RegExp:return i(\"(regexp)\",t.value);case l.Comment:o.tokens.curr.comment=!0;if(t.isSpecial)return{id:\"(comment)\",value:t.value,body:t.body,type:t.commentType,isSpecial:t.isSpecial,line:this.line,character:this.char,from:this.from};break;case\"\":break;default:return i(\"(punctuator)\",t.value)}}}},n.Lexer=p,n.Context=c},{\"../data/ascii-identifier-data.js\":\"/node_modules/jshint/data/ascii-identifier-data.js\",\"../lodash\":\"/node_modules/jshint/lodash.js\",\"./reg.js\":\"/node_modules/jshint/src/reg.js\",\"./state.js\":\"/node_modules/jshint/src/state.js\",events:\"/node_modules/browserify/node_modules/events/events.js\"}],\"/node_modules/jshint/src/messages.js\":[function(e,t,n){\"use strict\";var r=e(\"../lodash\"),i={E001:\"Bad option: '{a}'.\",E002:\"Bad option value.\",E003:\"Expected a JSON value.\",E004:\"Input is neither a string nor an array of strings.\",E005:\"Input is empty.\",E006:\"Unexpected early end of program.\",E007:'Missing \"use strict\" statement.',E008:\"Strict violation.\",E009:\"Option 'validthis' can't be used in a global scope.\",E010:\"'with' is not allowed in strict mode.\",E011:\"'{a}' has already been declared.\",E012:\"const '{a}' is initialized to 'undefined'.\",E013:\"Attempting to override '{a}' which is a constant.\",E014:\"A regular expression literal can be confused with '/='.\",E015:\"Unclosed regular expression.\",E016:\"Invalid regular expression.\",E017:\"Unclosed comment.\",E018:\"Unbegun comment.\",E019:\"Unmatched '{a}'.\",E020:\"Expected '{a}' to match '{b}' from line {c} and instead saw '{d}'.\",E021:\"Expected '{a}' and instead saw '{b}'.\",E022:\"Line breaking error '{a}'.\",E023:\"Missing '{a}'.\",E024:\"Unexpected '{a}'.\",E025:\"Missing ':' on a case clause.\",E026:\"Missing '}' to match '{' from line {a}.\",E027:\"Missing ']' to match '[' from line {a}.\",E028:\"Illegal comma.\",E029:\"Unclosed string.\",E030:\"Expected an identifier and instead saw '{a}'.\",E031:\"Bad assignment.\",E032:\"Expected a small integer or 'false' and instead saw '{a}'.\",E033:\"Expected an operator and instead saw '{a}'.\",E034:\"get/set are ES5 features.\",E035:\"Missing property name.\",E036:\"Expected to see a statement and instead saw a block.\",E037:null,E038:null,E039:\"Function declarations are not invocable. Wrap the whole function invocation in parens.\",E040:\"Each value should have its own case label.\",E041:\"Unrecoverable syntax error.\",E042:\"Stopping.\",E043:\"Too many errors.\",E044:null,E045:\"Invalid for each loop.\",E046:\"A yield statement shall be within a generator function (with syntax: `function*`)\",E047:null,E048:\"{a} declaration not directly within block.\",E049:\"A {a} cannot be named '{b}'.\",E050:\"Mozilla requires the yield expression to be parenthesized here.\",E051:null,E052:\"Unclosed template literal.\",E053:\"Export declaration must be in global scope.\",E054:\"Class properties must be methods. Expected '(' but instead saw '{a}'.\",E055:\"The '{a}' option cannot be set after any executable code.\",E056:\"'{a}' was used before it was declared, which is illegal for '{b}' variables.\",E057:\"Invalid meta property: '{a}.{b}'.\",E058:\"Missing semicolon.\"},s={W001:\"'hasOwnProperty' is a really bad name.\",W002:\"Value of '{a}' may be overwritten in IE 8 and earlier.\",W003:\"'{a}' was used before it was defined.\",W004:\"'{a}' is already defined.\",W005:\"A dot following a number can be confused with a decimal point.\",W006:\"Confusing minuses.\",W007:\"Confusing plusses.\",W008:\"A leading decimal point can be confused with a dot: '{a}'.\",W009:\"The array literal notation [] is preferable.\",W010:\"The object literal notation {} is preferable.\",W011:null,W012:null,W013:null,W014:\"Bad line breaking before '{a}'.\",W015:null,W016:\"Unexpected use of '{a}'.\",W017:\"Bad operand.\",W018:\"Confusing use of '{a}'.\",W019:\"Use the isNaN function to compare with NaN.\",W020:\"Read only.\",W021:\"Reassignment of '{a}', which is is a {b}. Use 'var' or 'let' to declare bindings that may change.\",W022:\"Do not assign to the exception parameter.\",W023:\"Expected an identifier in an assignment and instead saw a function invocation.\",W024:\"Expected an identifier and instead saw '{a}' (a reserved word).\",W025:\"Missing name in function declaration.\",W026:\"Inner functions should be listed at the top of the outer function.\",W027:\"Unreachable '{a}' after '{b}'.\",W028:\"Label '{a}' on {b} statement.\",W030:\"Expected an assignment or function call and instead saw an expression.\",W031:\"Do not use 'new' for side effects.\",W032:\"Unnecessary semicolon.\",W033:\"Missing semicolon.\",W034:'Unnecessary directive \"{a}\".',W035:\"Empty block.\",W036:\"Unexpected /*member '{a}'.\",W037:\"'{a}' is a statement label.\",W038:\"'{a}' used out of scope.\",W039:\"'{a}' is not allowed.\",W040:\"Possible strict violation.\",W041:\"Use '{a}' to compare with '{b}'.\",W042:\"Avoid EOL escaping.\",W043:\"Bad escaping of EOL. Use option multistr if needed.\",W044:\"Bad or unnecessary escaping.\",W045:\"Bad number '{a}'.\",W046:\"Don't use extra leading zeros '{a}'.\",W047:\"A trailing decimal point can be confused with a dot: '{a}'.\",W048:\"Unexpected control character in regular expression.\",W049:\"Unexpected escaped character '{a}' in regular expression.\",W050:\"JavaScript URL.\",W051:\"Variables should not be deleted.\",W052:\"Unexpected '{a}'.\",W053:\"Do not use {a} as a constructor.\",W054:\"The Function constructor is a form of eval.\",W055:\"A constructor name should start with an uppercase letter.\",W056:\"Bad constructor.\",W057:\"Weird construction. Is 'new' necessary?\",W058:\"Missing '()' invoking a constructor.\",W059:\"Avoid arguments.{a}.\",W060:\"document.write can be a form of eval.\",W061:\"eval can be harmful.\",W062:\"Wrap an immediate function invocation in parens to assist the reader in understanding that the expression is the result of a function, and not the function itself.\",W063:\"Math is not a function.\",W064:\"Missing 'new' prefix when invoking a constructor.\",W065:\"Missing radix parameter.\",W066:\"Implied eval. Consider passing a function instead of a string.\",W067:\"Bad invocation.\",W068:\"Wrapping non-IIFE function literals in parens is unnecessary.\",W069:\"['{a}'] is better written in dot notation.\",W070:\"Extra comma. (it breaks older versions of IE)\",W071:\"This function has too many statements. ({a})\",W072:\"This function has too many parameters. ({a})\",W073:\"Blocks are nested too deeply. ({a})\",W074:\"This function's cyclomatic complexity is too high. ({a})\",W075:\"Duplicate {a} '{b}'.\",W076:\"Unexpected parameter '{a}' in get {b} function.\",W077:\"Expected a single parameter in set {a} function.\",W078:\"Setter is defined without getter.\",W079:\"Redefinition of '{a}'.\",W080:\"It's not necessary to initialize '{a}' to 'undefined'.\",W081:null,W082:\"Function declarations should not be placed in blocks. Use a function expression or move the statement to the top of the outer function.\",W083:\"Don't make functions within a loop.\",W084:\"Assignment in conditional expression\",W085:\"Don't use 'with'.\",W086:\"Expected a 'break' statement before '{a}'.\",W087:\"Forgotten 'debugger' statement?\",W088:\"Creating global 'for' variable. Should be 'for (var {a} ...'.\",W089:\"The body of a for in should be wrapped in an if statement to filter unwanted properties from the prototype.\",W090:\"'{a}' is not a statement label.\",W091:null,W093:\"Did you mean to return a conditional instead of an assignment?\",W094:\"Unexpected comma.\",W095:\"Expected a string and instead saw {a}.\",W096:\"The '{a}' key may produce unexpected results.\",W097:'Use the function form of \"use strict\".',W098:\"'{a}' is defined but never used.\",W099:null,W100:\"This character may get silently deleted by one or more browsers.\",W101:\"Line is too long.\",W102:null,W103:\"The '{a}' property is deprecated.\",W104:\"'{a}' is available in ES{b} (use 'esversion: {b}') or Mozilla JS extensions (use moz).\",W105:\"Unexpected {a} in '{b}'.\",W106:\"Identifier '{a}' is not in camel case.\",W107:\"Script URL.\",W108:\"Strings must use doublequote.\",W109:\"Strings must use singlequote.\",W110:\"Mixed double and single quotes.\",W112:\"Unclosed string.\",W113:\"Control character in string: {a}.\",W114:\"Avoid {a}.\",W115:\"Octal literals are not allowed in strict mode.\",W116:\"Expected '{a}' and instead saw '{b}'.\",W117:\"'{a}' is not defined.\",W118:\"'{a}' is only available in Mozilla JavaScript extensions (use moz option).\",W119:\"'{a}' is only available in ES{b} (use 'esversion: {b}').\",W120:\"You might be leaking a variable ({a}) here.\",W121:\"Extending prototype of native object: '{a}'.\",W122:\"Invalid typeof value '{a}'\",W123:\"'{a}' is already defined in outer scope.\",W124:\"A generator function shall contain a yield statement.\",W125:\"This line contains non-breaking spaces: http://jshint.com/doc/options/#nonbsp\",W126:\"Unnecessary grouping operator.\",W127:\"Unexpected use of a comma operator.\",W128:\"Empty array elements require elision=true.\",W129:\"'{a}' is defined in a future version of JavaScript. Use a different variable name to avoid migration issues.\",W130:\"Invalid element after rest element.\",W131:\"Invalid parameter after rest parameter.\",W132:\"`var` declarations are forbidden. Use `let` or `const` instead.\",W133:\"Invalid for-{a} loop left-hand-side: {b}.\",W134:\"The '{a}' option is only available when linting ECMAScript {b} code.\",W135:\"{a} may not be supported by non-browser environments.\",W136:\"'{a}' must be in function scope.\",W137:\"Empty destructuring.\",W138:\"Regular parameters should not come after default parameters.\"},o={I001:\"Comma warnings can be turned off with 'laxcomma'.\",I002:null,I003:\"ES5 option is now set per default\"};n.errors={},n.warnings={},n.info={},r.each(i,function(e,t){n.errors[t]={code:t,desc:e}}),r.each(s,function(e,t){n.warnings[t]={code:t,desc:e}}),r.each(o,function(e,t){n.info[t]={code:t,desc:e}})},{\"../lodash\":\"/node_modules/jshint/lodash.js\"}],\"/node_modules/jshint/src/name-stack.js\":[function(e,t,n){\"use strict\";function r(){this._stack=[]}Object.defineProperty(r.prototype,\"length\",{get:function(){return this._stack.length}}),r.prototype.push=function(){this._stack.push(null)},r.prototype.pop=function(){this._stack.pop()},r.prototype.set=function(e){this._stack[this.length-1]=e},r.prototype.infer=function(){var e=this._stack[this.length-1],t=\"\",n;if(!e||e.type===\"class\")e=this._stack[this.length-2];return e?(n=e.type,n!==\"(string)\"&&n!==\"(number)\"&&n!==\"(identifier)\"&&n!==\"default\"?\"(expression)\":(e.accessorType&&(t=e.accessorType+\" \"),t+e.value)):\"(empty)\"},t.exports=r},{}],\"/node_modules/jshint/src/options.js\":[function(e,t,n){\"use strict\";n.bool={enforcing:{bitwise:!0,freeze:!0,camelcase:!0,curly:!0,eqeqeq:!0,futurehostile:!0,notypeof:!0,es3:!0,es5:!0,forin:!0,funcscope:!0,immed:!0,iterator:!0,newcap:!0,noarg:!0,nocomma:!0,noempty:!0,nonbsp:!0,nonew:!0,undef:!0,singleGroups:!1,varstmt:!1,enforceall:!1},relaxing:{asi:!0,multistr:!0,debug:!0,boss:!0,evil:!0,globalstrict:!0,plusplus:!0,proto:!0,scripturl:!0,sub:!0,supernew:!0,laxbreak:!0,laxcomma:!0,validthis:!0,withstmt:!0,moz:!0,noyield:!0,eqnull:!0,lastsemic:!0,loopfunc:!0,expr:!0,esnext:!0,elision:!0},environments:{mootools:!0,couch:!0,jasmine:!0,jquery:!0,node:!0,qunit:!0,rhino:!0,shelljs:!0,prototypejs:!0,yui:!0,mocha:!0,module:!0,wsh:!0,worker:!0,nonstandard:!0,browser:!0,browserify:!0,devel:!0,dojo:!0,typed:!0,phantom:!0},obsolete:{onecase:!0,regexp:!0,regexdash:!0}},n.val={maxlen:!1,indent:!1,maxerr:!1,predef:!1,globals:!1,quotmark:!1,scope:!1,maxstatements:!1,maxdepth:!1,maxparams:!1,maxcomplexity:!1,shadow:!1,strict:!0,unused:!0,latedef:!1,ignore:!1,ignoreDelimiters:!1,esversion:5},n.inverted={bitwise:!0,forin:!0,newcap:!0,plusplus:!0,regexp:!0,undef:!0,eqeqeq:!0,strict:!0},n.validNames=Object.keys(n.val).concat(Object.keys(n.bool.relaxing)).concat(Object.keys(n.bool.enforcing)).concat(Object.keys(n.bool.obsolete)).concat(Object.keys(n.bool.environments)),n.renamed={eqeq:\"eqeqeq\",windows:\"wsh\",sloppy:\"strict\"},n.removed={nomen:!0,onevar:!0,passfail:!0,white:!0,gcl:!0,smarttabs:!0,trailing:!0},n.noenforceall={varstmt:!0,strict:!0}},{}],\"/node_modules/jshint/src/reg.js\":[function(e,t,n){\"use strict\";n.unsafeString=/@cc|<\\/?|script|\\]\\s*\\]|<\\s*!|&lt/i,n.unsafeChars=/[\\u0000-\\u001f\\u007f-\\u009f\\u00ad\\u0600-\\u0604\\u070f\\u17b4\\u17b5\\u200c-\\u200f\\u2028-\\u202f\\u2060-\\u206f\\ufeff\\ufff0-\\uffff]/,n.needEsc=/[\\u0000-\\u001f&<\"\\/\\\\\\u007f-\\u009f\\u00ad\\u0600-\\u0604\\u070f\\u17b4\\u17b5\\u200c-\\u200f\\u2028-\\u202f\\u2060-\\u206f\\ufeff\\ufff0-\\uffff]/,n.needEscGlobal=/[\\u0000-\\u001f&<\"\\/\\\\\\u007f-\\u009f\\u00ad\\u0600-\\u0604\\u070f\\u17b4\\u17b5\\u200c-\\u200f\\u2028-\\u202f\\u2060-\\u206f\\ufeff\\ufff0-\\uffff]/g,n.starSlash=/\\*\\//,n.identifier=/^([a-zA-Z_$][a-zA-Z0-9_$]*)$/,n.javascriptURL=/^(?:javascript|jscript|ecmascript|vbscript|livescript)\\s*:/i,n.fallsThrough=/^\\s*falls?\\sthrough\\s*$/,n.maxlenException=/^(?:(?:\\/\\/|\\/\\*|\\*) ?)?[^ ]+$/},{}],\"/node_modules/jshint/src/scope-manager.js\":[function(e,t,n){\"use strict\";var r=e(\"../lodash\"),i=e(\"events\"),s={},o=function(e,t,n,o){function f(e){u={\"(labels)\":Object.create(null),\"(usages)\":Object.create(null),\"(breakLabels)\":Object.create(null),\"(parent)\":u,\"(type)\":e,\"(params)\":e===\"functionparams\"||e===\"catchparams\"?[]:null},a.push(u)}function v(e,t){d.emit(\"warning\",{code:e,token:t,data:r.slice(arguments,2)})}function m(e,t){d.emit(\"warning\",{code:e,token:t,data:r.slice(arguments,2)})}function g(e){u[\"(usages)\"][e]||(u[\"(usages)\"][e]={\"(modified)\":[],\"(reassigned)\":[],\"(tokens)\":[]})}function w(){if(u[\"(type)\"]===\"functionparams\"){E();return}var e=u[\"(labels)\"];for(var t in e)e[t]&&e[t][\"(type)\"]!==\"exception\"&&e[t][\"(unused)\"]&&b(t,e[t][\"(token)\"],\"var\")}function E(){var t=u[\"(params)\"];if(!t)return;var n=t.pop(),r;while(n){var i=u[\"(labels)\"][n];r=y(e.funct[\"(unusedOption)\"]);if(n===\"undefined\")return;if(i[\"(unused)\"])b(n,i[\"(token)\"],\"param\",e.funct[\"(unusedOption)\"]);else if(r===\"last-param\")return;n=t.pop()}}function S(e){for(var t=a.length-1;t>=0;--t){var n=a[t][\"(labels)\"];if(n[e])return n}}function x(e){for(var t=a.length-1;t>=0;t--){var n=a[t];if(n[\"(usages)\"][e])return n[\"(usages)\"][e];if(n===l)break}return!1}function T(t,n){if(e.option.shadow!==\"outer\")return;var r=l[\"(type)\"]===\"global\",i=u[\"(type)\"]===\"functionparams\",s=!r;for(var o=0;o<a.length;o++){var f=a[o];!i&&a[o+1]===l&&(s=!1),s&&f[\"(labels)\"][t]&&v(\"W123\",n,t),f[\"(breakLabels)\"][t]&&v(\"W123\",n,t)}}function N(t,n,r){e.option.latedef&&(e.option.latedef===!0&&t===\"function\"||t!==\"function\")&&v(\"W003\",r,n)}var u,a=[];f(\"global\"),u[\"(predefined)\"]=t;var l=u,c=Object.create(null),h=Object.create(null),p=[],d=new i.EventEmitter,y=function(t){return t===undefined&&(t=e.option.unused),t===!0&&(t=\"last-param\"),t},b=function(e,t,n,r){var i=t.line,s=t.from,o=t.raw_text||e;r=y(r);var u={vars:[\"var\"],\"last-param\":[\"var\",\"param\"],strict:[\"var\",\"param\",\"last-param\"]};r&&u[r]&&u[r].indexOf(n)!==-1&&v(\"W098\",{line:i,from:s},o),(r||n===\"var\")&&p.push({name:e,line:i,character:s})},C={on:function(e,t){e.split(\" \").forEach(function(e){d.on(e,t)})},isPredefined:function(e){return!this.has(e)&&r.has(a[0][\"(predefined)\"],e)},stack:function(e){var t=u;f(e),!e&&t[\"(type)\"]===\"functionparams\"&&(u[\"(isFuncBody)\"]=!0,u[\"(context)\"]=l,l=u)},unstack:function(){var t=a.length>1?a[a.length-2]:null,n=u===l,i=u[\"(type)\"]===\"functionparams\",f=u[\"(type)\"]===\"functionouter\",p,d,g=u[\"(usages)\"],y=u[\"(labels)\"],E=Object.keys(g);g.__proto__&&E.indexOf(\"__proto__\")===-1&&E.push(\"__proto__\");for(p=0;p<E.length;p++){var S=E[p],x=g[S],T=y[S];if(T){var N=T[\"(type)\"];if(T[\"(useOutsideOfScope)\"]&&!e.option.funcscope){var C=x[\"(tokens)\"];if(C)for(d=0;d<C.length;d++)T[\"(function)\"]===C[d][\"(function)\"]&&m(\"W038\",C[d],S)}u[\"(labels)\"][S][\"(unused)\"]=!1;if(N===\"const\"&&x[\"(modified)\"])for(d=0;d<x[\"(modified)\"].length;d++)m(\"E013\",x[\"(modified)\"][d],S);if((N===\"function\"||N===\"class\")&&x[\"(reassigned)\"])for(d=0;d<x[\"(reassigned)\"].length;d++)m(\"W021\",x[\"(reassigned)\"][d],S,N);continue}f&&(e.funct[\"(isCapturing)\"]=!0);if(t)if(!t[\"(usages)\"][S])t[\"(usages)\"][S]=x,n&&(t[\"(usages)\"][S][\"(onlyUsedSubFunction)\"]=!0);else{var k=t[\"(usages)\"][S];k[\"(modified)\"]=k[\"(modified)\"].concat(x[\"(modified)\"]),k[\"(tokens)\"]=k[\"(tokens)\"].concat(x[\"(tokens)\"]),k[\"(reassigned)\"]=k[\"(reassigned)\"].concat(x[\"(reassigned)\"]),k[\"(onlyUsedSubFunction)\"]=!1}else if(typeof u[\"(predefined)\"][S]==\"boolean\"){delete o[S],c[S]=s;if(u[\"(predefined)\"][S]===!1&&x[\"(reassigned)\"])for(d=0;d<x[\"(reassigned)\"].length;d++)v(\"W020\",x[\"(reassigned)\"][d])}else if(x[\"(tokens)\"])for(d=0;d<x[\"(tokens)\"].length;d++){var L=x[\"(tokens)\"][d];L.forgiveUndef||(e.option.undef&&!L.ignoreUndef&&v(\"W117\",L,S),h[S]?h[S].line.push(L.line):h[S]={name:S,line:[L.line]})}}t||Object.keys(o).forEach(function(e){b(e,o[e],\"var\")});if(t&&!n&&!i&&!f){var A=Object.keys(y);for(p=0;p<A.length;p++){var O=A[p];!y[O][\"(blockscoped)\"]&&y[O][\"(type)\"]!==\"exception\"&&!this.funct.has(O,{excludeCurrent:!0})&&(t[\"(labels)\"][O]=y[O],l[\"(type)\"]!==\"global\"&&(t[\"(labels)\"][O][\"(useOutsideOfScope)\"]=!0),delete y[O])}}w(),a.pop(),n&&(l=a[r.findLastIndex(a,function(e){return e[\"(isFuncBody)\"]||e[\"(type)\"]===\"global\"})]),u=t},addParam:function(t,n,i){i=i||\"param\";if(i===\"exception\"){var s=this.funct.labeltype(t);s&&s!==\"exception\"&&(e.option.node||v(\"W002\",e.tokens.next,t))}r.has(u[\"(labels)\"],t)?u[\"(labels)\"][t].duplicated=!0:(T(t,n,i),u[\"(labels)\"][t]={\"(type)\":i,\"(token)\":n,\"(unused)\":!0},u[\"(params)\"].push(t));if(r.has(u[\"(usages)\"],t)){var o=u[\"(usages)\"][t];o[\"(onlyUsedSubFunction)\"]?N(i,t,n):v(\"E056\",n,t,i)}},validateParams:function(){if(l[\"(type)\"]===\"global\")return;var t=e.isStrict(),n=l[\"(parent)\"];if(!n[\"(params)\"])return;n[\"(params)\"].forEach(function(r){var i=n[\"(labels)\"][r];i&&i.duplicated&&(t?v(\"E011\",i[\"(token)\"],r):e.option.shadow!==!0&&v(\"W004\",i[\"(token)\"],r))})},getUsedOrDefinedGlobals:function(){var e=Object.keys(c);return c.__proto__===s&&e.indexOf(\"__proto__\")===-1&&e.push(\"__proto__\"),e},getImpliedGlobals:function(){var e=r.values(h),t=!1;return h.__proto__&&(t=e.some(function(e){return e.name===\"__proto__\"}),t||e.push(h.__proto__)),e},getUnuseds:function(){return p},has:function(e){return Boolean(S(e))},labeltype:function(e){var t=S(e);return t?t[e][\"(type)\"]:null},addExported:function(e){var t=a[0][\"(labels)\"];if(r.has(o,e))delete o[e];else if(r.has(t,e))t[e][\"(unused)\"]=!1;else{for(var i=1;i<a.length;i++){var s=a[i];if(!!s[\"(type)\"])break;if(r.has(s[\"(labels)\"],e)&&!s[\"(labels)\"][e][\"(blockscoped)\"]){s[\"(labels)\"][e][\"(unused)\"]=!1;return}}n[e]=!0}},setExported:function(e,t){this.block.use(e,t)},addlabel:function(t,i){var o=i.type,a=i.token,f=o===\"let\"||o===\"const\"||o===\"class\",h=(f?u:l)[\"(type)\"]===\"global\"&&r.has(n,t);T(t,a,o);if(f){var p=u[\"(labels)\"][t];!p&&u===l&&u[\"(type)\"]!==\"global\"&&(p=!!l[\"(parent)\"][\"(labels)\"][t]);if(!p&&u[\"(usages)\"][t]){var d=u[\"(usages)\"][t];d[\"(onlyUsedSubFunction)\"]?N(o,t,a):v(\"E056\",a,t,o)}p?v(\"E011\",a,t):e.option.shadow===\"outer\"&&C.funct.has(t)&&v(\"W004\",a,t),C.block.add(t,o,a,!h)}else{var m=C.funct.has(t);!m&&x(t)&&N(o,t,a),C.funct.has(t,{onlyBlockscoped:!0})?v(\"E011\",a,t):e.option.shadow!==!0&&m&&t!==\"__proto__\"&&l[\"(type)\"]!==\"global\"&&v(\"W004\",a,t),C.funct.add(t,o,a,!h),l[\"(type)\"]===\"global\"&&(c[t]=s)}},funct:{labeltype:function(e,t){var n=t&&t.onlyBlockscoped,r=t&&t.excludeParams,i=a.length-(t&&t.excludeCurrent?2:1);for(var s=i;s>=0;s--){var o=a[s];if(o[\"(labels)\"][e]&&(!n||o[\"(labels)\"][e][\"(blockscoped)\"]))return o[\"(labels)\"][e][\"(type)\"];var u=r?a[s-1]:o;if(u&&u[\"(type)\"]===\"functionparams\")return null}return null},hasBreakLabel:function(e){for(var t=a.length-1;t>=0;t--){var n=a[t];if(n[\"(breakLabels)\"][e])return!0;if(n[\"(type)\"]===\"functionparams\")return!1}return!1},has:function(e,t){return Boolean(this.labeltype(e,t))},add:function(e,t,n,r){u[\"(labels)\"][e]={\"(type)\":t,\"(token)\":n,\"(blockscoped)\":!1,\"(function)\":l,\"(unused)\":r}}},block:{isGlobal:function(){return u[\"(type)\"]===\"global\"},use:function(t,n){var r=l[\"(parent)\"];r&&r[\"(labels)\"][t]&&r[\"(labels)\"][t][\"(type)\"]===\"param\"&&(C.funct.has(t,{excludeParams:!0,onlyBlockscoped:!0})||(r[\"(labels)\"][t][\"(unused)\"]=!1)),n&&(e.ignored.W117||e.option.undef===!1)&&(n.ignoreUndef=!0),g(t),n&&(n[\"(function)\"]=l,u[\"(usages)\"][t][\"(tokens)\"].push(n))},reassign:function(e,t){this.modify(e,t),u[\"(usages)\"][e][\"(reassigned)\"].push(t)},modify:function(e,t){g(e),u[\"(usages)\"][e][\"(modified)\"].push(t)},add:function(e,t,n,r){u[\"(labels)\"][e]={\"(type)\":t,\"(token)\":n,\"(blockscoped)\":!0,\"(unused)\":r}},addBreakLabel:function(t,n){var r=n.token;C.funct.hasBreakLabel(t)?v(\"E011\",r,t):e.option.shadow===\"outer\"&&(C.funct.has(t)?v(\"W004\",r,t):T(t,r)),u[\"(breakLabels)\"][t]=r}}};return C};t.exports=o},{\"../lodash\":\"/node_modules/jshint/lodash.js\",events:\"/node_modules/browserify/node_modules/events/events.js\"}],\"/node_modules/jshint/src/state.js\":[function(e,t,n){\"use strict\";var r=e(\"./name-stack.js\"),i={syntax:{},isStrict:function(){return this.directive[\"use strict\"]||this.inClassBody||this.option.module||this.option.strict===\"implied\"},inMoz:function(){return this.option.moz},inES6:function(){return this.option.moz||this.option.esversion>=6},inES5:function(e){return e?(!this.option.esversion||this.option.esversion===5)&&!this.option.moz:!this.option.esversion||this.option.esversion>=5||this.option.moz},reset:function(){this.tokens={prev:null,next:null,curr:null},this.option={},this.funct=null,this.ignored={},this.directive={},this.jsonMode=!1,this.jsonWarnings=[],this.lines=[],this.tab=\"\",this.cache={},this.ignoredLines={},this.forinifcheckneeded=!1,this.nameStack=new r,this.inClassBody=!1}};n.state=i},{\"./name-stack.js\":\"/node_modules/jshint/src/name-stack.js\"}],\"/node_modules/jshint/src/style.js\":[function(e,t,n){\"use strict\";n.register=function(e){e.on(\"Identifier\",function(n){if(e.getOption(\"proto\"))return;n.name===\"__proto__\"&&e.warn(\"W103\",{line:n.line,\"char\":n.char,data:[n.name,\"6\"]})}),e.on(\"Identifier\",function(n){if(e.getOption(\"iterator\"))return;n.name===\"__iterator__\"&&e.warn(\"W103\",{line:n.line,\"char\":n.char,data:[n.name]})}),e.on(\"Identifier\",function(n){if(!e.getOption(\"camelcase\"))return;n.name.replace(/^_+|_+$/g,\"\").indexOf(\"_\")>-1&&!n.name.match(/^[A-Z0-9_]*$/)&&e.warn(\"W106\",{line:n.line,\"char\":n.from,data:[n.name]})}),e.on(\"String\",function(n){var r=e.getOption(\"quotmark\"),i;if(!r)return;r===\"single\"&&n.quote!==\"'\"&&(i=\"W109\"),r===\"double\"&&n.quote!=='\"'&&(i=\"W108\"),r===!0&&(e.getCache(\"quotmark\")||e.setCache(\"quotmark\",n.quote),e.getCache(\"quotmark\")!==n.quote&&(i=\"W110\")),i&&e.warn(i,{line:n.line,\"char\":n.char})}),e.on(\"Number\",function(n){n.value.charAt(0)===\".\"&&e.warn(\"W008\",{line:n.line,\"char\":n.char,data:[n.value]}),n.value.substr(n.value.length-1)===\".\"&&e.warn(\"W047\",{line:n.line,\"char\":n.char,data:[n.value]}),/^00+/.test(n.value)&&e.warn(\"W046\",{line:n.line,\"char\":n.char,data:[n.value]})}),e.on(\"String\",function(n){var r=/^(?:javascript|jscript|ecmascript|vbscript|livescript)\\s*:/i;if(e.getOption(\"scripturl\"))return;r.test(n.value)&&e.warn(\"W107\",{line:n.line,\"char\":n.char})})}},{}],\"/node_modules/jshint/src/vars.js\":[function(e,t,n){\"use strict\";n.reservedVars={arguments:!1,NaN:!1},n.ecmaIdentifiers={3:{Array:!1,Boolean:!1,Date:!1,decodeURI:!1,decodeURIComponent:!1,encodeURI:!1,encodeURIComponent:!1,Error:!1,eval:!1,EvalError:!1,Function:!1,hasOwnProperty:!1,isFinite:!1,isNaN:!1,Math:!1,Number:!1,Object:!1,parseInt:!1,parseFloat:!1,RangeError:!1,ReferenceError:!1,RegExp:!1,String:!1,SyntaxError:!1,TypeError:!1,URIError:!1},5:{JSON:!1},6:{Map:!1,Promise:!1,Proxy:!1,Reflect:!1,Set:!1,Symbol:!1,WeakMap:!1,WeakSet:!1}},n.browser={Audio:!1,Blob:!1,addEventListener:!1,applicationCache:!1,atob:!1,blur:!1,btoa:!1,cancelAnimationFrame:!1,CanvasGradient:!1,CanvasPattern:!1,CanvasRenderingContext2D:!1,CSS:!1,clearInterval:!1,clearTimeout:!1,close:!1,closed:!1,Comment:!1,CustomEvent:!1,DOMParser:!1,defaultStatus:!1,Document:!1,document:!1,DocumentFragment:!1,Element:!1,ElementTimeControl:!1,Event:!1,event:!1,fetch:!1,FileReader:!1,FormData:!1,focus:!1,frames:!1,getComputedStyle:!1,HTMLElement:!1,HTMLAnchorElement:!1,HTMLBaseElement:!1,HTMLBlockquoteElement:!1,HTMLBodyElement:!1,HTMLBRElement:!1,HTMLButtonElement:!1,HTMLCanvasElement:!1,HTMLCollection:!1,HTMLDirectoryElement:!1,HTMLDivElement:!1,HTMLDListElement:!1,HTMLFieldSetElement:!1,HTMLFontElement:!1,HTMLFormElement:!1,HTMLFrameElement:!1,HTMLFrameSetElement:!1,HTMLHeadElement:!1,HTMLHeadingElement:!1,HTMLHRElement:!1,HTMLHtmlElement:!1,HTMLIFrameElement:!1,HTMLImageElement:!1,HTMLInputElement:!1,HTMLIsIndexElement:!1,HTMLLabelElement:!1,HTMLLayerElement:!1,HTMLLegendElement:!1,HTMLLIElement:!1,HTMLLinkElement:!1,HTMLMapElement:!1,HTMLMenuElement:!1,HTMLMetaElement:!1,HTMLModElement:!1,HTMLObjectElement:!1,HTMLOListElement:!1,HTMLOptGroupElement:!1,HTMLOptionElement:!1,HTMLParagraphElement:!1,HTMLParamElement:!1,HTMLPreElement:!1,HTMLQuoteElement:!1,HTMLScriptElement:!1,HTMLSelectElement:!1,HTMLStyleElement:!1,HTMLTableCaptionElement:!1,HTMLTableCellElement:!1,HTMLTableColElement:!1,HTMLTableElement:!1,HTMLTableRowElement:!1,HTMLTableSectionElement:!1,HTMLTemplateElement:!1,HTMLTextAreaElement:!1,HTMLTitleElement:!1,HTMLUListElement:!1,HTMLVideoElement:!1,history:!1,Image:!1,Intl:!1,length:!1,localStorage:!1,location:!1,matchMedia:!1,MessageChannel:!1,MessageEvent:!1,MessagePort:!1,MouseEvent:!1,moveBy:!1,moveTo:!1,MutationObserver:!1,name:!1,Node:!1,NodeFilter:!1,NodeList:!1,Notification:!1,navigator:!1,onbeforeunload:!0,onblur:!0,onerror:!0,onfocus:!0,onload:!0,onresize:!0,onunload:!0,open:!1,openDatabase:!1,opener:!1,Option:!1,parent:!1,performance:!1,print:!1,Range:!1,requestAnimationFrame:!1,removeEventListener:!1,resizeBy:!1,resizeTo:!1,screen:!1,scroll:!1,scrollBy:!1,scrollTo:!1,sessionStorage:!1,setInterval:!1,setTimeout:!1,SharedWorker:!1,status:!1,SVGAElement:!1,SVGAltGlyphDefElement:!1,SVGAltGlyphElement:!1,SVGAltGlyphItemElement:!1,SVGAngle:!1,SVGAnimateColorElement:!1,SVGAnimateElement:!1,SVGAnimateMotionElement:!1,SVGAnimateTransformElement:!1,SVGAnimatedAngle:!1,SVGAnimatedBoolean:!1,SVGAnimatedEnumeration:!1,SVGAnimatedInteger:!1,SVGAnimatedLength:!1,SVGAnimatedLengthList:!1,SVGAnimatedNumber:!1,SVGAnimatedNumberList:!1,SVGAnimatedPathData:!1,SVGAnimatedPoints:!1,SVGAnimatedPreserveAspectRatio:!1,SVGAnimatedRect:!1,SVGAnimatedString:!1,SVGAnimatedTransformList:!1,SVGAnimationElement:!1,SVGCSSRule:!1,SVGCircleElement:!1,SVGClipPathElement:!1,SVGColor:!1,SVGColorProfileElement:!1,SVGColorProfileRule:!1,SVGComponentTransferFunctionElement:!1,SVGCursorElement:!1,SVGDefsElement:!1,SVGDescElement:!1,SVGDocument:!1,SVGElement:!1,SVGElementInstance:!1,SVGElementInstanceList:!1,SVGEllipseElement:!1,SVGExternalResourcesRequired:!1,SVGFEBlendElement:!1,SVGFEColorMatrixElement:!1,SVGFEComponentTransferElement:!1,SVGFECompositeElement:!1,SVGFEConvolveMatrixElement:!1,SVGFEDiffuseLightingElement:!1,SVGFEDisplacementMapElement:!1,SVGFEDistantLightElement:!1,SVGFEFloodElement:!1,SVGFEFuncAElement:!1,SVGFEFuncBElement:!1,SVGFEFuncGElement:!1,SVGFEFuncRElement:!1,SVGFEGaussianBlurElement:!1,SVGFEImageElement:!1,SVGFEMergeElement:!1,SVGFEMergeNodeElement:!1,SVGFEMorphologyElement:!1,SVGFEOffsetElement:!1,SVGFEPointLightElement:!1,SVGFESpecularLightingElement:!1,SVGFESpotLightElement:!1,SVGFETileElement:!1,SVGFETurbulenceElement:!1,SVGFilterElement:!1,SVGFilterPrimitiveStandardAttributes:!1,SVGFitToViewBox:!1,SVGFontElement:!1,SVGFontFaceElement:!1,SVGFontFaceFormatElement:!1,SVGFontFaceNameElement:!1,SVGFontFaceSrcElement:!1,SVGFontFaceUriElement:!1,SVGForeignObjectElement:!1,SVGGElement:!1,SVGGlyphElement:!1,SVGGlyphRefElement:!1,SVGGradientElement:!1,SVGHKernElement:!1,SVGICCColor:!1,SVGImageElement:!1,SVGLangSpace:!1,SVGLength:!1,SVGLengthList:!1,SVGLineElement:!1,SVGLinearGradientElement:!1,SVGLocatable:!1,SVGMPathElement:!1,SVGMarkerElement:!1,SVGMaskElement:!1,SVGMatrix:!1,SVGMetadataElement:!1,SVGMissingGlyphElement:!1,SVGNumber:!1,SVGNumberList:!1,SVGPaint:!1,SVGPathElement:!1,SVGPathSeg:!1,SVGPathSegArcAbs:!1,SVGPathSegArcRel:!1,SVGPathSegClosePath:!1,SVGPathSegCurvetoCubicAbs:!1,SVGPathSegCurvetoCubicRel:!1,SVGPathSegCurvetoCubicSmoothAbs:!1,SVGPathSegCurvetoCubicSmoothRel:!1,SVGPathSegCurvetoQuadraticAbs:!1,SVGPathSegCurvetoQuadraticRel:!1,SVGPathSegCurvetoQuadraticSmoothAbs:!1,SVGPathSegCurvetoQuadraticSmoothRel:!1,SVGPathSegLinetoAbs:!1,SVGPathSegLinetoHorizontalAbs:!1,SVGPathSegLinetoHorizontalRel:!1,SVGPathSegLinetoRel:!1,SVGPathSegLinetoVerticalAbs:!1,SVGPathSegLinetoVerticalRel:!1,SVGPathSegList:!1,SVGPathSegMovetoAbs:!1,SVGPathSegMovetoRel:!1,SVGPatternElement:!1,SVGPoint:!1,SVGPointList:!1,SVGPolygonElement:!1,SVGPolylineElement:!1,SVGPreserveAspectRatio:!1,SVGRadialGradientElement:!1,SVGRect:!1,SVGRectElement:!1,SVGRenderingIntent:!1,SVGSVGElement:!1,SVGScriptElement:!1,SVGSetElement:!1,SVGStopElement:!1,SVGStringList:!1,SVGStylable:!1,SVGStyleElement:!1,SVGSwitchElement:!1,SVGSymbolElement:!1,SVGTRefElement:!1,SVGTSpanElement:!1,SVGTests:!1,SVGTextContentElement:!1,SVGTextElement:!1,SVGTextPathElement:!1,SVGTextPositioningElement:!1,SVGTitleElement:!1,SVGTransform:!1,SVGTransformList:!1,SVGTransformable:!1,SVGURIReference:!1,SVGUnitTypes:!1,SVGUseElement:!1,SVGVKernElement:!1,SVGViewElement:!1,SVGViewSpec:!1,SVGZoomAndPan:!1,Text:!1,TextDecoder:!1,TextEncoder:!1,TimeEvent:!1,top:!1,URL:!1,WebGLActiveInfo:!1,WebGLBuffer:!1,WebGLContextEvent:!1,WebGLFramebuffer:!1,WebGLProgram:!1,WebGLRenderbuffer:!1,WebGLRenderingContext:!1,WebGLShader:!1,WebGLShaderPrecisionFormat:!1,WebGLTexture:!1,WebGLUniformLocation:!1,WebSocket:!1,window:!1,Window:!1,Worker:!1,XDomainRequest:!1,XMLHttpRequest:!1,XMLSerializer:!1,XPathEvaluator:!1,XPathException:!1,XPathExpression:!1,XPathNamespace:!1,XPathNSResolver:!1,XPathResult:!1},n.devel={alert:!1,confirm:!1,console:!1,Debug:!1,opera:!1,prompt:!1},n.worker={importScripts:!0,postMessage:!0,self:!0,FileReaderSync:!0},n.nonstandard={escape:!1,unescape:!1},n.couch={require:!1,respond:!1,getRow:!1,emit:!1,send:!1,start:!1,sum:!1,log:!1,exports:!1,module:!1,provides:!1},n.node={__filename:!1,__dirname:!1,GLOBAL:!1,global:!1,module:!1,require:!1,Buffer:!0,console:!0,exports:!0,process:!0,setTimeout:!0,clearTimeout:!0,setInterval:!0,clearInterval:!0,setImmediate:!0,clearImmediate:!0},n.browserify={__filename:!1,__dirname:!1,global:!1,module:!1,require:!1,Buffer:!0,exports:!0,process:!0},n.phantom={phantom:!0,require:!0,WebPage:!0,console:!0,exports:!0},n.qunit={asyncTest:!1,deepEqual:!1,equal:!1,expect:!1,module:!1,notDeepEqual:!1,notEqual:!1,notPropEqual:!1,notStrictEqual:!1,ok:!1,propEqual:!1,QUnit:!1,raises:!1,start:!1,stop:!1,strictEqual:!1,test:!1,\"throws\":!1},n.rhino={defineClass:!1,deserialize:!1,gc:!1,help:!1,importClass:!1,importPackage:!1,java:!1,load:!1,loadClass:!1,Packages:!1,print:!1,quit:!1,readFile:!1,readUrl:!1,runCommand:!1,seal:!1,serialize:!1,spawn:!1,sync:!1,toint32:!1,version:!1},n.shelljs={target:!1,echo:!1,exit:!1,cd:!1,pwd:!1,ls:!1,find:!1,cp:!1,rm:!1,mv:!1,mkdir:!1,test:!1,cat:!1,sed:!1,grep:!1,which:!1,dirs:!1,pushd:!1,popd:!1,env:!1,exec:!1,chmod:!1,config:!1,error:!1,tempdir:!1},n.typed={ArrayBuffer:!1,ArrayBufferView:!1,DataView:!1,Float32Array:!1,Float64Array:!1,Int16Array:!1,Int32Array:!1,Int8Array:!1,Uint16Array:!1,Uint32Array:!1,Uint8Array:!1,Uint8ClampedArray:!1},n.wsh={ActiveXObject:!0,Enumerator:!0,GetObject:!0,ScriptEngine:!0,ScriptEngineBuildVersion:!0,ScriptEngineMajorVersion:!0,ScriptEngineMinorVersion:!0,VBArray:!0,WSH:!0,WScript:!0,XDomainRequest:!0},n.dojo={dojo:!1,dijit:!1,dojox:!1,define:!1,require:!1},n.jquery={$:!1,jQuery:!1},n.mootools={$:!1,$$:!1,Asset:!1,Browser:!1,Chain:!1,Class:!1,Color:!1,Cookie:!1,Core:!1,Document:!1,DomReady:!1,DOMEvent:!1,DOMReady:!1,Drag:!1,Element:!1,Elements:!1,Event:!1,Events:!1,Fx:!1,Group:!1,Hash:!1,HtmlTable:!1,IFrame:!1,IframeShim:!1,InputValidator:!1,instanceOf:!1,Keyboard:!1,Locale:!1,Mask:!1,MooTools:!1,Native:!1,Options:!1,OverText:!1,Request:!1,Scroller:!1,Slick:!1,Slider:!1,Sortables:!1,Spinner:!1,Swiff:!1,Tips:!1,Type:!1,typeOf:!1,URI:!1,Window:!1},n.prototypejs={$:!1,$$:!1,$A:!1,$F:!1,$H:!1,$R:!1,$break:!1,$continue:!1,$w:!1,Abstract:!1,Ajax:!1,Class:!1,Enumerable:!1,Element:!1,Event:!1,Field:!1,Form:!1,Hash:!1,Insertion:!1,ObjectRange:!1,PeriodicalExecuter:!1,Position:!1,Prototype:!1,Selector:!1,Template:!1,Toggle:!1,Try:!1,Autocompleter:!1,Builder:!1,Control:!1,Draggable:!1,Draggables:!1,Droppables:!1,Effect:!1,Sortable:!1,SortableObserver:!1,Sound:!1,Scriptaculous:!1},n.yui={YUI:!1,Y:!1,YUI_config:!1},n.mocha={mocha:!1,describe:!1,xdescribe:!1,it:!1,xit:!1,context:!1,xcontext:!1,before:!1,after:!1,beforeEach:!1,afterEach:!1,suite:!1,test:!1,setup:!1,teardown:!1,suiteSetup:!1,suiteTeardown:!1},n.jasmine={jasmine:!1,describe:!1,xdescribe:!1,it:!1,xit:!1,beforeEach:!1,afterEach:!1,setFixtures:!1,loadFixtures:!1,spyOn:!1,expect:!1,runs:!1,waitsFor:!1,waits:!1,beforeAll:!1,afterAll:!1,fail:!1,fdescribe:!1,fit:!1,pending:!1}},{}]},{},[\"/node_modules/jshint/src/jshint.js\"])}),define(\"ace/mode/javascript_worker\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/worker/mirror\",\"ace/mode/javascript/jshint\"],function(require,exports,module){\"use strict\";function startRegex(e){return RegExp(\"^(\"+e.join(\"|\")+\")\")}var oop=require(\"../lib/oop\"),Mirror=require(\"../worker/mirror\").Mirror,lint=require(\"./javascript/jshint\").JSHINT,disabledWarningsRe=startRegex([\"Bad for in variable '(.+)'.\",'Missing \"use strict\"']),errorsRe=startRegex([\"Unexpected\",\"Expected \",\"Confusing (plus|minus)\",\"\\\\{a\\\\} unterminated regular expression\",\"Unclosed \",\"Unmatched \",\"Unbegun comment\",\"Bad invocation\",\"Missing space after\",\"Missing operator at\"]),infoRe=startRegex([\"Expected an assignment\",\"Bad escapement of EOL\",\"Unexpected comma\",\"Unexpected space\",\"Missing radix parameter.\",\"A leading decimal point can\",\"\\\\['{a}'\\\\] is better written in dot notation.\",\"'{a}' used out of scope\"]),JavaScriptWorker=exports.JavaScriptWorker=function(e){Mirror.call(this,e),this.setTimeout(500),this.setOptions()};oop.inherits(JavaScriptWorker,Mirror),function(){this.setOptions=function(e){this.options=e||{esnext:!0,moz:!0,devel:!0,browser:!0,node:!0,laxcomma:!0,laxbreak:!0,lastsemic:!0,onevar:!1,passfail:!1,maxerr:100,expr:!0,multistr:!0,globalstrict:!0},this.doc.getValue()&&this.deferredUpdate.schedule(100)},this.changeOptions=function(e){oop.mixin(this.options,e),this.doc.getValue()&&this.deferredUpdate.schedule(100)},this.isValidJS=function(str){try{eval(\"throw 0;\"+str)}catch(e){if(e===0)return!0}return!1},this.onUpdate=function(){var e=this.doc.getValue();e=e.replace(/^#!.*\\n/,\"\\n\");if(!e)return this.sender.emit(\"annotate\",[]);var t=[],n=this.isValidJS(e)?\"warning\":\"error\";lint(e,this.options,this.options.globals);var r=lint.errors,i=!1;for(var s=0;s<r.length;s++){var o=r[s];if(!o)continue;var u=o.raw,a=\"warning\";if(u==\"Missing semicolon.\"){var f=o.evidence.substr(o.character);f=f.charAt(f.search(/\\S/)),n==\"error\"&&f&&/[\\w\\d{(['\"]/.test(f)?(o.reason='Missing \";\" before statement',a=\"error\"):a=\"info\"}else{if(disabledWarningsRe.test(u))continue;infoRe.test(u)?a=\"info\":errorsRe.test(u)?(i=!0,a=n):u==\"'{a}' is not defined.\"?a=\"warning\":u==\"'{a}' is defined but never used.\"&&(a=\"info\")}t.push({row:o.line-1,column:o.character-1,text:o.reason,type:a,raw:u}),i}this.sender.emit(\"annotate\",t)}}.call(JavaScriptWorker.prototype)}),define(\"ace/lib/es5-shim\",[\"require\",\"exports\",\"module\"],function(e,t,n){function r(){}function w(e){try{return Object.defineProperty(e,\"sentinel\",{}),\"sentinel\"in e}catch(t){}}function H(e){return e=+e,e!==e?e=0:e!==0&&e!==1/0&&e!==-1/0&&(e=(e>0||-1)*Math.floor(Math.abs(e))),e}function B(e){var t=typeof e;return e===null||t===\"undefined\"||t===\"boolean\"||t===\"number\"||t===\"string\"}function j(e){var t,n,r;if(B(e))return e;n=e.valueOf;if(typeof n==\"function\"){t=n.call(e);if(B(t))return t}r=e.toString;if(typeof r==\"function\"){t=r.call(e);if(B(t))return t}throw new TypeError}Function.prototype.bind||(Function.prototype.bind=function(t){var n=this;if(typeof n!=\"function\")throw new TypeError(\"Function.prototype.bind called on incompatible \"+n);var i=u.call(arguments,1),s=function(){if(this instanceof s){var e=n.apply(this,i.concat(u.call(arguments)));return Object(e)===e?e:this}return n.apply(t,i.concat(u.call(arguments)))};return n.prototype&&(r.prototype=n.prototype,s.prototype=new r,r.prototype=null),s});var i=Function.prototype.call,s=Array.prototype,o=Object.prototype,u=s.slice,a=i.bind(o.toString),f=i.bind(o.hasOwnProperty),l,c,h,p,d;if(d=f(o,\"__defineGetter__\"))l=i.bind(o.__defineGetter__),c=i.bind(o.__defineSetter__),h=i.bind(o.__lookupGetter__),p=i.bind(o.__lookupSetter__);if([1,2].splice(0).length!=2)if(!function(){function e(e){var t=new Array(e+2);return t[0]=t[1]=0,t}var t=[],n;t.splice.apply(t,e(20)),t.splice.apply(t,e(26)),n=t.length,t.splice(5,0,\"XXX\"),n+1==t.length;if(n+1==t.length)return!0}())Array.prototype.splice=function(e,t){var n=this.length;e>0?e>n&&(e=n):e==void 0?e=0:e<0&&(e=Math.max(n+e,0)),e+t<n||(t=n-e);var r=this.slice(e,e+t),i=u.call(arguments,2),s=i.length;if(e===n)s&&this.push.apply(this,i);else{var o=Math.min(t,n-e),a=e+o,f=a+s-o,l=n-a,c=n-o;if(f<a)for(var h=0;h<l;++h)this[f+h]=this[a+h];else if(f>a)for(h=l;h--;)this[f+h]=this[a+h];if(s&&e===c)this.length=c,this.push.apply(this,i);else{this.length=c+s;for(h=0;h<s;++h)this[e+h]=i[h]}}return r};else{var v=Array.prototype.splice;Array.prototype.splice=function(e,t){return arguments.length?v.apply(this,[e===void 0?0:e,t===void 0?this.length-e:t].concat(u.call(arguments,2))):[]}}Array.isArray||(Array.isArray=function(t){return a(t)==\"[object Array]\"});var m=Object(\"a\"),g=m[0]!=\"a\"||!(0 in m);Array.prototype.forEach||(Array.prototype.forEach=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=arguments[1],s=-1,o=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError;while(++s<o)s in r&&t.call(i,r[s],s,n)}),Array.prototype.map||(Array.prototype.map=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=Array(i),o=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var u=0;u<i;u++)u in r&&(s[u]=t.call(o,r[u],u,n));return s}),Array.prototype.filter||(Array.prototype.filter=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=[],o,u=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var f=0;f<i;f++)f in r&&(o=r[f],t.call(u,o,f,n)&&s.push(o));return s}),Array.prototype.every||(Array.prototype.every=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&!t.call(s,r[o],o,n))return!1;return!0}),Array.prototype.some||(Array.prototype.some=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&t.call(s,r[o],o,n))return!0;return!1}),Array.prototype.reduce||(Array.prototype.reduce=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduce of empty array with no initial value\");var s=0,o;if(arguments.length>=2)o=arguments[1];else do{if(s in r){o=r[s++];break}if(++s>=i)throw new TypeError(\"reduce of empty array with no initial value\")}while(!0);for(;s<i;s++)s in r&&(o=t.call(void 0,o,r[s],s,n));return o}),Array.prototype.reduceRight||(Array.prototype.reduceRight=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduceRight of empty array with no initial value\");var s,o=i-1;if(arguments.length>=2)s=arguments[1];else do{if(o in r){s=r[o--];break}if(--o<0)throw new TypeError(\"reduceRight of empty array with no initial value\")}while(!0);do o in this&&(s=t.call(void 0,s,r[o],o,n));while(o--);return s});if(!Array.prototype.indexOf||[0,1].indexOf(1,2)!=-1)Array.prototype.indexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=0;arguments.length>1&&(i=H(arguments[1])),i=i>=0?i:Math.max(0,r+i);for(;i<r;i++)if(i in n&&n[i]===t)return i;return-1};if(!Array.prototype.lastIndexOf||[0,1].lastIndexOf(0,-3)!=-1)Array.prototype.lastIndexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=r-1;arguments.length>1&&(i=Math.min(i,H(arguments[1]))),i=i>=0?i:r-Math.abs(i);for(;i>=0;i--)if(i in n&&t===n[i])return i;return-1};Object.getPrototypeOf||(Object.getPrototypeOf=function(t){return t.__proto__||(t.constructor?t.constructor.prototype:o)});if(!Object.getOwnPropertyDescriptor){var y=\"Object.getOwnPropertyDescriptor called on a non-object: \";Object.getOwnPropertyDescriptor=function(t,n){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(y+t);if(!f(t,n))return;var r,i,s;r={enumerable:!0,configurable:!0};if(d){var u=t.__proto__;t.__proto__=o;var i=h(t,n),s=p(t,n);t.__proto__=u;if(i||s)return i&&(r.get=i),s&&(r.set=s),r}return r.value=t[n],r}}Object.getOwnPropertyNames||(Object.getOwnPropertyNames=function(t){return Object.keys(t)});if(!Object.create){var b;Object.prototype.__proto__===null?b=function(){return{__proto__:null}}:b=function(){var e={};for(var t in e)e[t]=null;return e.constructor=e.hasOwnProperty=e.propertyIsEnumerable=e.isPrototypeOf=e.toLocaleString=e.toString=e.valueOf=e.__proto__=null,e},Object.create=function(t,n){var r;if(t===null)r=b();else{if(typeof t!=\"object\")throw new TypeError(\"typeof prototype[\"+typeof t+\"] != 'object'\");var i=function(){};i.prototype=t,r=new i,r.__proto__=t}return n!==void 0&&Object.defineProperties(r,n),r}}if(Object.defineProperty){var E=w({}),S=typeof document==\"undefined\"||w(document.createElement(\"div\"));if(!E||!S)var x=Object.defineProperty}if(!Object.defineProperty||x){var T=\"Property description must be an object: \",N=\"Object.defineProperty called on non-object: \",C=\"getters & setters can not be defined on this javascript engine\";Object.defineProperty=function(t,n,r){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(N+t);if(typeof r!=\"object\"&&typeof r!=\"function\"||r===null)throw new TypeError(T+r);if(x)try{return x.call(Object,t,n,r)}catch(i){}if(f(r,\"value\"))if(d&&(h(t,n)||p(t,n))){var s=t.__proto__;t.__proto__=o,delete t[n],t[n]=r.value,t.__proto__=s}else t[n]=r.value;else{if(!d)throw new TypeError(C);f(r,\"get\")&&l(t,n,r.get),f(r,\"set\")&&c(t,n,r.set)}return t}}Object.defineProperties||(Object.defineProperties=function(t,n){for(var r in n)f(n,r)&&Object.defineProperty(t,r,n[r]);return t}),Object.seal||(Object.seal=function(t){return t}),Object.freeze||(Object.freeze=function(t){return t});try{Object.freeze(function(){})}catch(k){Object.freeze=function(t){return function(n){return typeof n==\"function\"?n:t(n)}}(Object.freeze)}Object.preventExtensions||(Object.preventExtensions=function(t){return t}),Object.isSealed||(Object.isSealed=function(t){return!1}),Object.isFrozen||(Object.isFrozen=function(t){return!1}),Object.isExtensible||(Object.isExtensible=function(t){if(Object(t)===t)throw new TypeError;var n=\"\";while(f(t,n))n+=\"?\";t[n]=!0;var r=f(t,n);return delete t[n],r});if(!Object.keys){var L=!0,A=[\"toString\",\"toLocaleString\",\"valueOf\",\"hasOwnProperty\",\"isPrototypeOf\",\"propertyIsEnumerable\",\"constructor\"],O=A.length;for(var M in{toString:null})L=!1;Object.keys=function I(e){if(typeof e!=\"object\"&&typeof e!=\"function\"||e===null)throw new TypeError(\"Object.keys called on a non-object\");var I=[];for(var t in e)f(e,t)&&I.push(t);if(L)for(var n=0,r=O;n<r;n++){var i=A[n];f(e,i)&&I.push(i)}return I}}Date.now||(Date.now=function(){return(new Date).getTime()});var _=\"\t\\n\u000b\\f\\r \\u00a0\\u1680\\u180e\\u2000\\u2001\\u2002\\u2003\\u2004\\u2005\\u2006\\u2007\\u2008\\u2009\\u200a\\u202f\\u205f\\u3000\\u2028\\u2029\\ufeff\";if(!String.prototype.trim||_.trim()){_=\"[\"+_+\"]\";var D=new RegExp(\"^\"+_+_+\"*\"),P=new RegExp(_+_+\"*$\");String.prototype.trim=function(){return String(this).replace(D,\"\").replace(P,\"\")}}var F=function(e){if(e==null)throw new TypeError(\"can't convert \"+e+\" to object\");return Object(e)}})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/worker-json.js",
    "content": "\"no use strict\";(function(e){function t(e,t){var n=e,r=\"\";while(n){var i=t[n];if(typeof i==\"string\")return i+r;if(i)return i.location.replace(/\\/*$/,\"/\")+(r||i.main||i.name);if(i===!1)return\"\";var s=n.lastIndexOf(\"/\");if(s===-1)break;r=n.substr(s)+r,n=n.slice(0,s)}return e}if(typeof e.window!=\"undefined\"&&e.document)return;if(e.require&&e.define)return;e.console||(e.console=function(){var e=Array.prototype.slice.call(arguments,0);postMessage({type:\"log\",data:e})},e.console.error=e.console.warn=e.console.log=e.console.trace=e.console),e.window=e,e.ace=e,e.onerror=function(e,t,n,r,i){postMessage({type:\"error\",data:{message:e,data:i.data,file:t,line:n,col:r,stack:i.stack}})},e.normalizeModule=function(t,n){if(n.indexOf(\"!\")!==-1){var r=n.split(\"!\");return e.normalizeModule(t,r[0])+\"!\"+e.normalizeModule(t,r[1])}if(n.charAt(0)==\".\"){var i=t.split(\"/\").slice(0,-1).join(\"/\");n=(i?i+\"/\":\"\")+n;while(n.indexOf(\".\")!==-1&&s!=n){var s=n;n=n.replace(/^\\.\\//,\"\").replace(/\\/\\.\\//,\"/\").replace(/[^\\/]+\\/\\.\\.\\//,\"\")}}return n},e.require=function(r,i){i||(i=r,r=null);if(!i.charAt)throw new Error(\"worker.js require() accepts only (parentId, id) as arguments\");i=e.normalizeModule(r,i);var s=e.require.modules[i];if(s)return s.initialized||(s.initialized=!0,s.exports=s.factory().exports),s.exports;if(!e.require.tlns)return console.log(\"unable to load \"+i);var o=t(i,e.require.tlns);return o.slice(-3)!=\".js\"&&(o+=\".js\"),e.require.id=i,e.require.modules[i]={},importScripts(o),e.require(r,i)},e.require.modules={},e.require.tlns={},e.define=function(t,n,r){arguments.length==2?(r=n,typeof t!=\"string\"&&(n=t,t=e.require.id)):arguments.length==1&&(r=t,n=[],t=e.require.id);if(typeof r!=\"function\"){e.require.modules[t]={exports:r,initialized:!0};return}n.length||(n=[\"require\",\"exports\",\"module\"]);var i=function(n){return e.require(t,n)};e.require.modules[t]={exports:{},factory:function(){var e=this,t=r.apply(this,n.map(function(t){switch(t){case\"require\":return i;case\"exports\":return e.exports;case\"module\":return e;default:return i(t)}}));return t&&(e.exports=t),e}}},e.define.amd={},require.tlns={},e.initBaseUrls=function(t){for(var n in t)require.tlns[n]=t[n]},e.initSender=function(){var n=e.require(\"ace/lib/event_emitter\").EventEmitter,r=e.require(\"ace/lib/oop\"),i=function(){};return function(){r.implement(this,n),this.callback=function(e,t){postMessage({type:\"call\",id:t,data:e})},this.emit=function(e,t){postMessage({type:\"event\",name:e,data:t})}}.call(i.prototype),new i};var n=e.main=null,r=e.sender=null;e.onmessage=function(t){var i=t.data;if(i.event&&r)r._signal(i.event,i.data);else if(i.command)if(n[i.command])n[i.command].apply(n,i.args);else{if(!e[i.command])throw new Error(\"Unknown command:\"+i.command);e[i.command].apply(e,i.args)}else if(i.init){e.initBaseUrls(i.tlns),require(\"ace/lib/es5-shim\"),r=e.sender=e.initSender();var s=require(i.module)[i.classname];n=e.main=new s(r)}}})(this),define(\"ace/lib/oop\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.inherits=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})},t.mixin=function(e,t){for(var n in t)e[n]=t[n];return e},t.implement=function(e,n){t.mixin(e,n)}}),define(\"ace/range\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(e,t){return e.row-t.row||e.column-t.column},i=function(e,t,n,r){this.start={row:e,column:t},this.end={row:n,column:r}};(function(){this.isEqual=function(e){return this.start.row===e.start.row&&this.end.row===e.end.row&&this.start.column===e.start.column&&this.end.column===e.end.column},this.toString=function(){return\"Range: [\"+this.start.row+\"/\"+this.start.column+\"] -> [\"+this.end.row+\"/\"+this.end.column+\"]\"},this.contains=function(e,t){return this.compare(e,t)==0},this.compareRange=function(e){var t,n=e.end,r=e.start;return t=this.compare(n.row,n.column),t==1?(t=this.compare(r.row,r.column),t==1?2:t==0?1:0):t==-1?-2:(t=this.compare(r.row,r.column),t==-1?-1:t==1?42:0)},this.comparePoint=function(e){return this.compare(e.row,e.column)},this.containsRange=function(e){return this.comparePoint(e.start)==0&&this.comparePoint(e.end)==0},this.intersects=function(e){var t=this.compareRange(e);return t==-1||t==0||t==1},this.isEnd=function(e,t){return this.end.row==e&&this.end.column==t},this.isStart=function(e,t){return this.start.row==e&&this.start.column==t},this.setStart=function(e,t){typeof e==\"object\"?(this.start.column=e.column,this.start.row=e.row):(this.start.row=e,this.start.column=t)},this.setEnd=function(e,t){typeof e==\"object\"?(this.end.column=e.column,this.end.row=e.row):(this.end.row=e,this.end.column=t)},this.inside=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)||this.isStart(e,t)?!1:!0:!1},this.insideStart=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)?!1:!0:!1},this.insideEnd=function(e,t){return this.compare(e,t)==0?this.isStart(e,t)?!1:!0:!1},this.compare=function(e,t){return!this.isMultiLine()&&e===this.start.row?t<this.start.column?-1:t>this.end.column?1:0:e<this.start.row?-1:e>this.end.row?1:this.start.row===e?t>=this.start.column?0:-1:this.end.row===e?t<=this.end.column?0:1:0},this.compareStart=function(e,t){return this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.compareEnd=function(e,t){return this.end.row==e&&this.end.column==t?1:this.compare(e,t)},this.compareInside=function(e,t){return this.end.row==e&&this.end.column==t?1:this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.clipRows=function(e,t){if(this.end.row>t)var n={row:t+1,column:0};else if(this.end.row<e)var n={row:e,column:0};if(this.start.row>t)var r={row:t+1,column:0};else if(this.start.row<e)var r={row:e,column:0};return i.fromPoints(r||this.start,n||this.end)},this.extend=function(e,t){var n=this.compare(e,t);if(n==0)return this;if(n==-1)var r={row:e,column:t};else var s={row:e,column:t};return i.fromPoints(r||this.start,s||this.end)},this.isEmpty=function(){return this.start.row===this.end.row&&this.start.column===this.end.column},this.isMultiLine=function(){return this.start.row!==this.end.row},this.clone=function(){return i.fromPoints(this.start,this.end)},this.collapseRows=function(){return this.end.column==0?new i(this.start.row,0,Math.max(this.start.row,this.end.row-1),0):new i(this.start.row,0,this.end.row,0)},this.toScreenRange=function(e){var t=e.documentToScreenPosition(this.start),n=e.documentToScreenPosition(this.end);return new i(t.row,t.column,n.row,n.column)},this.moveBy=function(e,t){this.start.row+=e,this.start.column+=t,this.end.row+=e,this.end.column+=t}}).call(i.prototype),i.fromPoints=function(e,t){return new i(e.row,e.column,t.row,t.column)},i.comparePoints=r,i.comparePoints=function(e,t){return e.row-t.row||e.column-t.column},t.Range=i}),define(\"ace/apply_delta\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function r(e,t){throw console.log(\"Invalid Delta:\",e),\"Invalid Delta: \"+t}function i(e,t){return t.row>=0&&t.row<e.length&&t.column>=0&&t.column<=e[t.row].length}function s(e,t){t.action!=\"insert\"&&t.action!=\"remove\"&&r(t,\"delta.action must be 'insert' or 'remove'\"),t.lines instanceof Array||r(t,\"delta.lines must be an Array\"),(!t.start||!t.end)&&r(t,\"delta.start/end must be an present\");var n=t.start;i(e,t.start)||r(t,\"delta.start must be contained in document\");var s=t.end;t.action==\"remove\"&&!i(e,s)&&r(t,\"delta.end must contained in document for 'remove' actions\");var o=s.row-n.row,u=s.column-(o==0?n.column:0);(o!=t.lines.length-1||t.lines[o].length!=u)&&r(t,\"delta.range must match delta lines\")}t.applyDelta=function(e,t,n){var r=t.start.row,i=t.start.column,s=e[r]||\"\";switch(t.action){case\"insert\":var o=t.lines;if(o.length===1)e[r]=s.substring(0,i)+t.lines[0]+s.substring(i);else{var u=[r,1].concat(t.lines);e.splice.apply(e,u),e[r]=s.substring(0,i)+e[r],e[r+t.lines.length-1]+=s.substring(i)}break;case\"remove\":var a=t.end.column,f=t.end.row;r===f?e[r]=s.substring(0,i)+s.substring(a):e.splice(r,f-r+1,s.substring(0,i)+e[f].substring(a))}}}),define(\"ace/lib/event_emitter\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={},i=function(){this.propagationStopped=!0},s=function(){this.defaultPrevented=!0};r._emit=r._dispatchEvent=function(e,t){this._eventRegistry||(this._eventRegistry={}),this._defaultHandlers||(this._defaultHandlers={});var n=this._eventRegistry[e]||[],r=this._defaultHandlers[e];if(!n.length&&!r)return;if(typeof t!=\"object\"||!t)t={};t.type||(t.type=e),t.stopPropagation||(t.stopPropagation=i),t.preventDefault||(t.preventDefault=s),n=n.slice();for(var o=0;o<n.length;o++){n[o](t,this);if(t.propagationStopped)break}if(r&&!t.defaultPrevented)return r(t,this)},r._signal=function(e,t){var n=(this._eventRegistry||{})[e];if(!n)return;n=n.slice();for(var r=0;r<n.length;r++)n[r](t,this)},r.once=function(e,t){var n=this;t&&this.addEventListener(e,function r(){n.removeEventListener(e,r),t.apply(null,arguments)})},r.setDefaultHandler=function(e,t){var n=this._defaultHandlers;n||(n=this._defaultHandlers={_disabled_:{}});if(n[e]){var r=n[e],i=n._disabled_[e];i||(n._disabled_[e]=i=[]),i.push(r);var s=i.indexOf(t);s!=-1&&i.splice(s,1)}n[e]=t},r.removeDefaultHandler=function(e,t){var n=this._defaultHandlers;if(!n)return;var r=n._disabled_[e];if(n[e]==t){var i=n[e];r&&this.setDefaultHandler(e,r.pop())}else if(r){var s=r.indexOf(t);s!=-1&&r.splice(s,1)}},r.on=r.addEventListener=function(e,t,n){this._eventRegistry=this._eventRegistry||{};var r=this._eventRegistry[e];return r||(r=this._eventRegistry[e]=[]),r.indexOf(t)==-1&&r[n?\"unshift\":\"push\"](t),t},r.off=r.removeListener=r.removeEventListener=function(e,t){this._eventRegistry=this._eventRegistry||{};var n=this._eventRegistry[e];if(!n)return;var r=n.indexOf(t);r!==-1&&n.splice(r,1)},r.removeAllListeners=function(e){this._eventRegistry&&(this._eventRegistry[e]=[])},t.EventEmitter=r}),define(\"ace/anchor\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/event_emitter\").EventEmitter,s=t.Anchor=function(e,t,n){this.$onChange=this.onChange.bind(this),this.attach(e),typeof n==\"undefined\"?this.setPosition(t.row,t.column):this.setPosition(t,n)};(function(){function e(e,t,n){var r=n?e.column<=t.column:e.column<t.column;return e.row<t.row||e.row==t.row&&r}function t(t,n,r){var i=t.action==\"insert\",s=(i?1:-1)*(t.end.row-t.start.row),o=(i?1:-1)*(t.end.column-t.start.column),u=t.start,a=i?u:t.end;return e(n,u,r)?{row:n.row,column:n.column}:e(a,n,!r)?{row:n.row+s,column:n.column+(n.row==a.row?o:0)}:{row:u.row,column:u.column}}r.implement(this,i),this.getPosition=function(){return this.$clipPositionToDocument(this.row,this.column)},this.getDocument=function(){return this.document},this.$insertRight=!1,this.onChange=function(e){if(e.start.row==e.end.row&&e.start.row!=this.row)return;if(e.start.row>this.row)return;var n=t(e,{row:this.row,column:this.column},this.$insertRight);this.setPosition(n.row,n.column,!0)},this.setPosition=function(e,t,n){var r;n?r={row:e,column:t}:r=this.$clipPositionToDocument(e,t);if(this.row==r.row&&this.column==r.column)return;var i={row:this.row,column:this.column};this.row=r.row,this.column=r.column,this._signal(\"change\",{old:i,value:r})},this.detach=function(){this.document.removeEventListener(\"change\",this.$onChange)},this.attach=function(e){this.document=e||this.document,this.document.on(\"change\",this.$onChange)},this.$clipPositionToDocument=function(e,t){var n={};return e>=this.document.getLength()?(n.row=Math.max(0,this.document.getLength()-1),n.column=this.document.getLine(n.row).length):e<0?(n.row=0,n.column=0):(n.row=e,n.column=Math.min(this.document.getLine(n.row).length,Math.max(0,t))),t<0&&(n.column=0),n}}).call(s.prototype)}),define(\"ace/document\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/apply_delta\",\"ace/lib/event_emitter\",\"ace/range\",\"ace/anchor\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./apply_delta\").applyDelta,s=e(\"./lib/event_emitter\").EventEmitter,o=e(\"./range\").Range,u=e(\"./anchor\").Anchor,a=function(e){this.$lines=[\"\"],e.length===0?this.$lines=[\"\"]:Array.isArray(e)?this.insertMergedLines({row:0,column:0},e):this.insert({row:0,column:0},e)};(function(){r.implement(this,s),this.setValue=function(e){var t=this.getLength()-1;this.remove(new o(0,0,t,this.getLine(t).length)),this.insert({row:0,column:0},e)},this.getValue=function(){return this.getAllLines().join(this.getNewLineCharacter())},this.createAnchor=function(e,t){return new u(this,e,t)},\"aaa\".split(/a/).length===0?this.$split=function(e){return e.replace(/\\r\\n|\\r/g,\"\\n\").split(\"\\n\")}:this.$split=function(e){return e.split(/\\r\\n|\\r|\\n/)},this.$detectNewLine=function(e){var t=e.match(/^.*?(\\r\\n|\\r|\\n)/m);this.$autoNewLine=t?t[1]:\"\\n\",this._signal(\"changeNewLineMode\")},this.getNewLineCharacter=function(){switch(this.$newLineMode){case\"windows\":return\"\\r\\n\";case\"unix\":return\"\\n\";default:return this.$autoNewLine||\"\\n\"}},this.$autoNewLine=\"\",this.$newLineMode=\"auto\",this.setNewLineMode=function(e){if(this.$newLineMode===e)return;this.$newLineMode=e,this._signal(\"changeNewLineMode\")},this.getNewLineMode=function(){return this.$newLineMode},this.isNewLine=function(e){return e==\"\\r\\n\"||e==\"\\r\"||e==\"\\n\"},this.getLine=function(e){return this.$lines[e]||\"\"},this.getLines=function(e,t){return this.$lines.slice(e,t+1)},this.getAllLines=function(){return this.getLines(0,this.getLength())},this.getLength=function(){return this.$lines.length},this.getTextRange=function(e){return this.getLinesForRange(e).join(this.getNewLineCharacter())},this.getLinesForRange=function(e){var t;if(e.start.row===e.end.row)t=[this.getLine(e.start.row).substring(e.start.column,e.end.column)];else{t=this.getLines(e.start.row,e.end.row),t[0]=(t[0]||\"\").substring(e.start.column);var n=t.length-1;e.end.row-e.start.row==n&&(t[n]=t[n].substring(0,e.end.column))}return t},this.insertLines=function(e,t){return console.warn(\"Use of document.insertLines is deprecated. Use the insertFullLines method instead.\"),this.insertFullLines(e,t)},this.removeLines=function(e,t){return console.warn(\"Use of document.removeLines is deprecated. Use the removeFullLines method instead.\"),this.removeFullLines(e,t)},this.insertNewLine=function(e){return console.warn(\"Use of document.insertNewLine is deprecated. Use insertMergedLines(position, ['', '']) instead.\"),this.insertMergedLines(e,[\"\",\"\"])},this.insert=function(e,t){return this.getLength()<=1&&this.$detectNewLine(t),this.insertMergedLines(e,this.$split(t))},this.insertInLine=function(e,t){var n=this.clippedPos(e.row,e.column),r=this.pos(e.row,e.column+t.length);return this.applyDelta({start:n,end:r,action:\"insert\",lines:[t]},!0),this.clonePos(r)},this.clippedPos=function(e,t){var n=this.getLength();e===undefined?e=n:e<0?e=0:e>=n&&(e=n-1,t=undefined);var r=this.getLine(e);return t==undefined&&(t=r.length),t=Math.min(Math.max(t,0),r.length),{row:e,column:t}},this.clonePos=function(e){return{row:e.row,column:e.column}},this.pos=function(e,t){return{row:e,column:t}},this.$clipPosition=function(e){var t=this.getLength();return e.row>=t?(e.row=Math.max(0,t-1),e.column=this.getLine(t-1).length):(e.row=Math.max(0,e.row),e.column=Math.min(Math.max(e.column,0),this.getLine(e.row).length)),e},this.insertFullLines=function(e,t){e=Math.min(Math.max(e,0),this.getLength());var n=0;e<this.getLength()?(t=t.concat([\"\"]),n=0):(t=[\"\"].concat(t),e--,n=this.$lines[e].length),this.insertMergedLines({row:e,column:n},t)},this.insertMergedLines=function(e,t){var n=this.clippedPos(e.row,e.column),r={row:n.row+t.length-1,column:(t.length==1?n.column:0)+t[t.length-1].length};return this.applyDelta({start:n,end:r,action:\"insert\",lines:t}),this.clonePos(r)},this.remove=function(e){var t=this.clippedPos(e.start.row,e.start.column),n=this.clippedPos(e.end.row,e.end.column);return this.applyDelta({start:t,end:n,action:\"remove\",lines:this.getLinesForRange({start:t,end:n})}),this.clonePos(t)},this.removeInLine=function(e,t,n){var r=this.clippedPos(e,t),i=this.clippedPos(e,n);return this.applyDelta({start:r,end:i,action:\"remove\",lines:this.getLinesForRange({start:r,end:i})},!0),this.clonePos(r)},this.removeFullLines=function(e,t){e=Math.min(Math.max(0,e),this.getLength()-1),t=Math.min(Math.max(0,t),this.getLength()-1);var n=t==this.getLength()-1&&e>0,r=t<this.getLength()-1,i=n?e-1:e,s=n?this.getLine(i).length:0,u=r?t+1:t,a=r?0:this.getLine(u).length,f=new o(i,s,u,a),l=this.$lines.slice(e,t+1);return this.applyDelta({start:f.start,end:f.end,action:\"remove\",lines:this.getLinesForRange(f)}),l},this.removeNewLine=function(e){e<this.getLength()-1&&e>=0&&this.applyDelta({start:this.pos(e,this.getLine(e).length),end:this.pos(e+1,0),action:\"remove\",lines:[\"\",\"\"]})},this.replace=function(e,t){e instanceof o||(e=o.fromPoints(e.start,e.end));if(t.length===0&&e.isEmpty())return e.start;if(t==this.getTextRange(e))return e.end;this.remove(e);var n;return t?n=this.insert(e.start,t):n=e.start,n},this.applyDeltas=function(e){for(var t=0;t<e.length;t++)this.applyDelta(e[t])},this.revertDeltas=function(e){for(var t=e.length-1;t>=0;t--)this.revertDelta(e[t])},this.applyDelta=function(e,t){var n=e.action==\"insert\";if(n?e.lines.length<=1&&!e.lines[0]:!o.comparePoints(e.start,e.end))return;n&&e.lines.length>2e4&&this.$splitAndapplyLargeDelta(e,2e4),i(this.$lines,e,t),this._signal(\"change\",e)},this.$splitAndapplyLargeDelta=function(e,t){var n=e.lines,r=n.length,i=e.start.row,s=e.start.column,o=0,u=0;do{o=u,u+=t-1;var a=n.slice(o,u);if(u>r){e.lines=a,e.start.row=i+o,e.start.column=s;break}a.push(\"\"),this.applyDelta({start:this.pos(i+o,s),end:this.pos(i+u,s=0),action:e.action,lines:a},!0)}while(!0)},this.revertDelta=function(e){this.applyDelta({start:this.clonePos(e.start),end:this.clonePos(e.end),action:e.action==\"insert\"?\"remove\":\"insert\",lines:e.lines.slice()})},this.indexToPosition=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length;for(var i=t||0,s=n.length;i<s;i++){e-=n[i].length+r;if(e<0)return{row:i,column:e+n[i].length+r}}return{row:s-1,column:n[s-1].length}},this.positionToIndex=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length,i=0,s=Math.min(e.row,n.length);for(var o=t||0;o<s;++o)i+=n[o].length+r;return i+e.column}}).call(a.prototype),t.Document=a}),define(\"ace/lib/lang\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.last=function(e){return e[e.length-1]},t.stringReverse=function(e){return e.split(\"\").reverse().join(\"\")},t.stringRepeat=function(e,t){var n=\"\";while(t>0){t&1&&(n+=e);if(t>>=1)e+=e}return n};var r=/^\\s\\s*/,i=/\\s\\s*$/;t.stringTrimLeft=function(e){return e.replace(r,\"\")},t.stringTrimRight=function(e){return e.replace(i,\"\")},t.copyObject=function(e){var t={};for(var n in e)t[n]=e[n];return t},t.copyArray=function(e){var t=[];for(var n=0,r=e.length;n<r;n++)e[n]&&typeof e[n]==\"object\"?t[n]=this.copyObject(e[n]):t[n]=e[n];return t},t.deepCopy=function s(e){if(typeof e!=\"object\"||!e)return e;var t;if(Array.isArray(e)){t=[];for(var n=0;n<e.length;n++)t[n]=s(e[n]);return t}if(Object.prototype.toString.call(e)!==\"[object Object]\")return e;t={};for(var n in e)t[n]=s(e[n]);return t},t.arrayToMap=function(e){var t={};for(var n=0;n<e.length;n++)t[e[n]]=1;return t},t.createMap=function(e){var t=Object.create(null);for(var n in e)t[n]=e[n];return t},t.arrayRemove=function(e,t){for(var n=0;n<=e.length;n++)t===e[n]&&e.splice(n,1)},t.escapeRegExp=function(e){return e.replace(/([.*+?^${}()|[\\]\\/\\\\])/g,\"\\\\$1\")},t.escapeHTML=function(e){return e.replace(/&/g,\"&#38;\").replace(/\"/g,\"&#34;\").replace(/'/g,\"&#39;\").replace(/</g,\"&#60;\")},t.getMatchOffsets=function(e,t){var n=[];return e.replace(t,function(e){n.push({offset:arguments[arguments.length-2],length:e.length})}),n},t.deferredCall=function(e){var t=null,n=function(){t=null,e()},r=function(e){return r.cancel(),t=setTimeout(n,e||0),r};return r.schedule=r,r.call=function(){return this.cancel(),e(),r},r.cancel=function(){return clearTimeout(t),t=null,r},r.isPending=function(){return t},r},t.delayedCall=function(e,t){var n=null,r=function(){n=null,e()},i=function(e){n==null&&(n=setTimeout(r,e||t))};return i.delay=function(e){n&&clearTimeout(n),n=setTimeout(r,e||t)},i.schedule=i,i.call=function(){this.cancel(),e()},i.cancel=function(){n&&clearTimeout(n),n=null},i.isPending=function(){return n},i}}),define(\"ace/worker/mirror\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/document\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=e(\"../document\").Document,s=e(\"../lib/lang\"),o=t.Mirror=function(e){this.sender=e;var t=this.doc=new i(\"\"),n=this.deferredUpdate=s.delayedCall(this.onUpdate.bind(this)),r=this;e.on(\"change\",function(e){var i=e.data;if(i[0].start)t.applyDeltas(i);else for(var s=0;s<i.length;s+=2){if(Array.isArray(i[s+1]))var o={action:\"insert\",start:i[s],lines:i[s+1]};else var o={action:\"remove\",start:i[s],end:i[s+1]};t.applyDelta(o,!0)}if(r.$timeout)return n.schedule(r.$timeout);r.onUpdate()})};(function(){this.$timeout=500,this.setTimeout=function(e){this.$timeout=e},this.setValue=function(e){this.doc.setValue(e),this.deferredUpdate.schedule(this.$timeout)},this.getValue=function(e){this.sender.callback(this.doc.getValue(),e)},this.onUpdate=function(){},this.isPending=function(){return this.deferredUpdate.isPending()}}).call(o.prototype)}),define(\"ace/mode/json/json_parse\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r,i,s={'\"':'\"',\"\\\\\":\"\\\\\",\"/\":\"/\",b:\"\\b\",f:\"\\f\",n:\"\\n\",r:\"\\r\",t:\"\t\"},o,u=function(e){throw{name:\"SyntaxError\",message:e,at:r,text:o}},a=function(e){return e&&e!==i&&u(\"Expected '\"+e+\"' instead of '\"+i+\"'\"),i=o.charAt(r),r+=1,i},f=function(){var e,t=\"\";i===\"-\"&&(t=\"-\",a(\"-\"));while(i>=\"0\"&&i<=\"9\")t+=i,a();if(i===\".\"){t+=\".\";while(a()&&i>=\"0\"&&i<=\"9\")t+=i}if(i===\"e\"||i===\"E\"){t+=i,a();if(i===\"-\"||i===\"+\")t+=i,a();while(i>=\"0\"&&i<=\"9\")t+=i,a()}e=+t;if(!isNaN(e))return e;u(\"Bad number\")},l=function(){var e,t,n=\"\",r;if(i==='\"')while(a()){if(i==='\"')return a(),n;if(i===\"\\\\\"){a();if(i===\"u\"){r=0;for(t=0;t<4;t+=1){e=parseInt(a(),16);if(!isFinite(e))break;r=r*16+e}n+=String.fromCharCode(r)}else{if(typeof s[i]!=\"string\")break;n+=s[i]}}else n+=i}u(\"Bad string\")},c=function(){while(i&&i<=\" \")a()},h=function(){switch(i){case\"t\":return a(\"t\"),a(\"r\"),a(\"u\"),a(\"e\"),!0;case\"f\":return a(\"f\"),a(\"a\"),a(\"l\"),a(\"s\"),a(\"e\"),!1;case\"n\":return a(\"n\"),a(\"u\"),a(\"l\"),a(\"l\"),null}u(\"Unexpected '\"+i+\"'\")},p,d=function(){var e=[];if(i===\"[\"){a(\"[\"),c();if(i===\"]\")return a(\"]\"),e;while(i){e.push(p()),c();if(i===\"]\")return a(\"]\"),e;a(\",\"),c()}}u(\"Bad array\")},v=function(){var e,t={};if(i===\"{\"){a(\"{\"),c();if(i===\"}\")return a(\"}\"),t;while(i){e=l(),c(),a(\":\"),Object.hasOwnProperty.call(t,e)&&u('Duplicate key \"'+e+'\"'),t[e]=p(),c();if(i===\"}\")return a(\"}\"),t;a(\",\"),c()}}u(\"Bad object\")};return p=function(){c();switch(i){case\"{\":return v();case\"[\":return d();case'\"':return l();case\"-\":return f();default:return i>=\"0\"&&i<=\"9\"?f():h()}},function(e,t){var n;return o=e,r=0,i=\" \",n=p(),c(),i&&u(\"Syntax error\"),typeof t==\"function\"?function s(e,n){var r,i,o=e[n];if(o&&typeof o==\"object\")for(r in o)Object.hasOwnProperty.call(o,r)&&(i=s(o,r),i!==undefined?o[r]=i:delete o[r]);return t.call(e,n,o)}({\"\":n},\"\"):n}}),define(\"ace/mode/json_worker\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/worker/mirror\",\"ace/mode/json/json_parse\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../worker/mirror\").Mirror,s=e(\"./json/json_parse\"),o=t.JsonWorker=function(e){i.call(this,e),this.setTimeout(200)};r.inherits(o,i),function(){this.onUpdate=function(){var e=this.doc.getValue(),t=[];try{e&&s(e)}catch(n){var r=this.doc.indexToPosition(n.at-1);t.push({row:r.row,column:r.column,text:n.message,type:\"error\"})}this.sender.emit(\"annotate\",t)}}.call(o.prototype)}),define(\"ace/lib/es5-shim\",[\"require\",\"exports\",\"module\"],function(e,t,n){function r(){}function w(e){try{return Object.defineProperty(e,\"sentinel\",{}),\"sentinel\"in e}catch(t){}}function H(e){return e=+e,e!==e?e=0:e!==0&&e!==1/0&&e!==-1/0&&(e=(e>0||-1)*Math.floor(Math.abs(e))),e}function B(e){var t=typeof e;return e===null||t===\"undefined\"||t===\"boolean\"||t===\"number\"||t===\"string\"}function j(e){var t,n,r;if(B(e))return e;n=e.valueOf;if(typeof n==\"function\"){t=n.call(e);if(B(t))return t}r=e.toString;if(typeof r==\"function\"){t=r.call(e);if(B(t))return t}throw new TypeError}Function.prototype.bind||(Function.prototype.bind=function(t){var n=this;if(typeof n!=\"function\")throw new TypeError(\"Function.prototype.bind called on incompatible \"+n);var i=u.call(arguments,1),s=function(){if(this instanceof s){var e=n.apply(this,i.concat(u.call(arguments)));return Object(e)===e?e:this}return n.apply(t,i.concat(u.call(arguments)))};return n.prototype&&(r.prototype=n.prototype,s.prototype=new r,r.prototype=null),s});var i=Function.prototype.call,s=Array.prototype,o=Object.prototype,u=s.slice,a=i.bind(o.toString),f=i.bind(o.hasOwnProperty),l,c,h,p,d;if(d=f(o,\"__defineGetter__\"))l=i.bind(o.__defineGetter__),c=i.bind(o.__defineSetter__),h=i.bind(o.__lookupGetter__),p=i.bind(o.__lookupSetter__);if([1,2].splice(0).length!=2)if(!function(){function e(e){var t=new Array(e+2);return t[0]=t[1]=0,t}var t=[],n;t.splice.apply(t,e(20)),t.splice.apply(t,e(26)),n=t.length,t.splice(5,0,\"XXX\"),n+1==t.length;if(n+1==t.length)return!0}())Array.prototype.splice=function(e,t){var n=this.length;e>0?e>n&&(e=n):e==void 0?e=0:e<0&&(e=Math.max(n+e,0)),e+t<n||(t=n-e);var r=this.slice(e,e+t),i=u.call(arguments,2),s=i.length;if(e===n)s&&this.push.apply(this,i);else{var o=Math.min(t,n-e),a=e+o,f=a+s-o,l=n-a,c=n-o;if(f<a)for(var h=0;h<l;++h)this[f+h]=this[a+h];else if(f>a)for(h=l;h--;)this[f+h]=this[a+h];if(s&&e===c)this.length=c,this.push.apply(this,i);else{this.length=c+s;for(h=0;h<s;++h)this[e+h]=i[h]}}return r};else{var v=Array.prototype.splice;Array.prototype.splice=function(e,t){return arguments.length?v.apply(this,[e===void 0?0:e,t===void 0?this.length-e:t].concat(u.call(arguments,2))):[]}}Array.isArray||(Array.isArray=function(t){return a(t)==\"[object Array]\"});var m=Object(\"a\"),g=m[0]!=\"a\"||!(0 in m);Array.prototype.forEach||(Array.prototype.forEach=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=arguments[1],s=-1,o=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError;while(++s<o)s in r&&t.call(i,r[s],s,n)}),Array.prototype.map||(Array.prototype.map=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=Array(i),o=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var u=0;u<i;u++)u in r&&(s[u]=t.call(o,r[u],u,n));return s}),Array.prototype.filter||(Array.prototype.filter=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=[],o,u=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var f=0;f<i;f++)f in r&&(o=r[f],t.call(u,o,f,n)&&s.push(o));return s}),Array.prototype.every||(Array.prototype.every=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&!t.call(s,r[o],o,n))return!1;return!0}),Array.prototype.some||(Array.prototype.some=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&t.call(s,r[o],o,n))return!0;return!1}),Array.prototype.reduce||(Array.prototype.reduce=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduce of empty array with no initial value\");var s=0,o;if(arguments.length>=2)o=arguments[1];else do{if(s in r){o=r[s++];break}if(++s>=i)throw new TypeError(\"reduce of empty array with no initial value\")}while(!0);for(;s<i;s++)s in r&&(o=t.call(void 0,o,r[s],s,n));return o}),Array.prototype.reduceRight||(Array.prototype.reduceRight=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduceRight of empty array with no initial value\");var s,o=i-1;if(arguments.length>=2)s=arguments[1];else do{if(o in r){s=r[o--];break}if(--o<0)throw new TypeError(\"reduceRight of empty array with no initial value\")}while(!0);do o in this&&(s=t.call(void 0,s,r[o],o,n));while(o--);return s});if(!Array.prototype.indexOf||[0,1].indexOf(1,2)!=-1)Array.prototype.indexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=0;arguments.length>1&&(i=H(arguments[1])),i=i>=0?i:Math.max(0,r+i);for(;i<r;i++)if(i in n&&n[i]===t)return i;return-1};if(!Array.prototype.lastIndexOf||[0,1].lastIndexOf(0,-3)!=-1)Array.prototype.lastIndexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=r-1;arguments.length>1&&(i=Math.min(i,H(arguments[1]))),i=i>=0?i:r-Math.abs(i);for(;i>=0;i--)if(i in n&&t===n[i])return i;return-1};Object.getPrototypeOf||(Object.getPrototypeOf=function(t){return t.__proto__||(t.constructor?t.constructor.prototype:o)});if(!Object.getOwnPropertyDescriptor){var y=\"Object.getOwnPropertyDescriptor called on a non-object: \";Object.getOwnPropertyDescriptor=function(t,n){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(y+t);if(!f(t,n))return;var r,i,s;r={enumerable:!0,configurable:!0};if(d){var u=t.__proto__;t.__proto__=o;var i=h(t,n),s=p(t,n);t.__proto__=u;if(i||s)return i&&(r.get=i),s&&(r.set=s),r}return r.value=t[n],r}}Object.getOwnPropertyNames||(Object.getOwnPropertyNames=function(t){return Object.keys(t)});if(!Object.create){var b;Object.prototype.__proto__===null?b=function(){return{__proto__:null}}:b=function(){var e={};for(var t in e)e[t]=null;return e.constructor=e.hasOwnProperty=e.propertyIsEnumerable=e.isPrototypeOf=e.toLocaleString=e.toString=e.valueOf=e.__proto__=null,e},Object.create=function(t,n){var r;if(t===null)r=b();else{if(typeof t!=\"object\")throw new TypeError(\"typeof prototype[\"+typeof t+\"] != 'object'\");var i=function(){};i.prototype=t,r=new i,r.__proto__=t}return n!==void 0&&Object.defineProperties(r,n),r}}if(Object.defineProperty){var E=w({}),S=typeof document==\"undefined\"||w(document.createElement(\"div\"));if(!E||!S)var x=Object.defineProperty}if(!Object.defineProperty||x){var T=\"Property description must be an object: \",N=\"Object.defineProperty called on non-object: \",C=\"getters & setters can not be defined on this javascript engine\";Object.defineProperty=function(t,n,r){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(N+t);if(typeof r!=\"object\"&&typeof r!=\"function\"||r===null)throw new TypeError(T+r);if(x)try{return x.call(Object,t,n,r)}catch(i){}if(f(r,\"value\"))if(d&&(h(t,n)||p(t,n))){var s=t.__proto__;t.__proto__=o,delete t[n],t[n]=r.value,t.__proto__=s}else t[n]=r.value;else{if(!d)throw new TypeError(C);f(r,\"get\")&&l(t,n,r.get),f(r,\"set\")&&c(t,n,r.set)}return t}}Object.defineProperties||(Object.defineProperties=function(t,n){for(var r in n)f(n,r)&&Object.defineProperty(t,r,n[r]);return t}),Object.seal||(Object.seal=function(t){return t}),Object.freeze||(Object.freeze=function(t){return t});try{Object.freeze(function(){})}catch(k){Object.freeze=function(t){return function(n){return typeof n==\"function\"?n:t(n)}}(Object.freeze)}Object.preventExtensions||(Object.preventExtensions=function(t){return t}),Object.isSealed||(Object.isSealed=function(t){return!1}),Object.isFrozen||(Object.isFrozen=function(t){return!1}),Object.isExtensible||(Object.isExtensible=function(t){if(Object(t)===t)throw new TypeError;var n=\"\";while(f(t,n))n+=\"?\";t[n]=!0;var r=f(t,n);return delete t[n],r});if(!Object.keys){var L=!0,A=[\"toString\",\"toLocaleString\",\"valueOf\",\"hasOwnProperty\",\"isPrototypeOf\",\"propertyIsEnumerable\",\"constructor\"],O=A.length;for(var M in{toString:null})L=!1;Object.keys=function I(e){if(typeof e!=\"object\"&&typeof e!=\"function\"||e===null)throw new TypeError(\"Object.keys called on a non-object\");var I=[];for(var t in e)f(e,t)&&I.push(t);if(L)for(var n=0,r=O;n<r;n++){var i=A[n];f(e,i)&&I.push(i)}return I}}Date.now||(Date.now=function(){return(new Date).getTime()});var _=\"\t\\n\u000b\\f\\r \\u00a0\\u1680\\u180e\\u2000\\u2001\\u2002\\u2003\\u2004\\u2005\\u2006\\u2007\\u2008\\u2009\\u200a\\u202f\\u205f\\u3000\\u2028\\u2029\\ufeff\";if(!String.prototype.trim||_.trim()){_=\"[\"+_+\"]\";var D=new RegExp(\"^\"+_+_+\"*\"),P=new RegExp(_+_+\"*$\");String.prototype.trim=function(){return String(this).replace(D,\"\").replace(P,\"\")}}var F=function(e){if(e==null)throw new TypeError(\"can't convert \"+e+\" to object\");return Object(e)}})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/worker-lua.js",
    "content": "\"no use strict\";(function(e){function t(e,t){var n=e,r=\"\";while(n){var i=t[n];if(typeof i==\"string\")return i+r;if(i)return i.location.replace(/\\/*$/,\"/\")+(r||i.main||i.name);if(i===!1)return\"\";var s=n.lastIndexOf(\"/\");if(s===-1)break;r=n.substr(s)+r,n=n.slice(0,s)}return e}if(typeof e.window!=\"undefined\"&&e.document)return;if(e.require&&e.define)return;e.console||(e.console=function(){var e=Array.prototype.slice.call(arguments,0);postMessage({type:\"log\",data:e})},e.console.error=e.console.warn=e.console.log=e.console.trace=e.console),e.window=e,e.ace=e,e.onerror=function(e,t,n,r,i){postMessage({type:\"error\",data:{message:e,data:i.data,file:t,line:n,col:r,stack:i.stack}})},e.normalizeModule=function(t,n){if(n.indexOf(\"!\")!==-1){var r=n.split(\"!\");return e.normalizeModule(t,r[0])+\"!\"+e.normalizeModule(t,r[1])}if(n.charAt(0)==\".\"){var i=t.split(\"/\").slice(0,-1).join(\"/\");n=(i?i+\"/\":\"\")+n;while(n.indexOf(\".\")!==-1&&s!=n){var s=n;n=n.replace(/^\\.\\//,\"\").replace(/\\/\\.\\//,\"/\").replace(/[^\\/]+\\/\\.\\.\\//,\"\")}}return n},e.require=function(r,i){i||(i=r,r=null);if(!i.charAt)throw new Error(\"worker.js require() accepts only (parentId, id) as arguments\");i=e.normalizeModule(r,i);var s=e.require.modules[i];if(s)return s.initialized||(s.initialized=!0,s.exports=s.factory().exports),s.exports;if(!e.require.tlns)return console.log(\"unable to load \"+i);var o=t(i,e.require.tlns);return o.slice(-3)!=\".js\"&&(o+=\".js\"),e.require.id=i,e.require.modules[i]={},importScripts(o),e.require(r,i)},e.require.modules={},e.require.tlns={},e.define=function(t,n,r){arguments.length==2?(r=n,typeof t!=\"string\"&&(n=t,t=e.require.id)):arguments.length==1&&(r=t,n=[],t=e.require.id);if(typeof r!=\"function\"){e.require.modules[t]={exports:r,initialized:!0};return}n.length||(n=[\"require\",\"exports\",\"module\"]);var i=function(n){return e.require(t,n)};e.require.modules[t]={exports:{},factory:function(){var e=this,t=r.apply(this,n.map(function(t){switch(t){case\"require\":return i;case\"exports\":return e.exports;case\"module\":return e;default:return i(t)}}));return t&&(e.exports=t),e}}},e.define.amd={},require.tlns={},e.initBaseUrls=function(t){for(var n in t)require.tlns[n]=t[n]},e.initSender=function(){var n=e.require(\"ace/lib/event_emitter\").EventEmitter,r=e.require(\"ace/lib/oop\"),i=function(){};return function(){r.implement(this,n),this.callback=function(e,t){postMessage({type:\"call\",id:t,data:e})},this.emit=function(e,t){postMessage({type:\"event\",name:e,data:t})}}.call(i.prototype),new i};var n=e.main=null,r=e.sender=null;e.onmessage=function(t){var i=t.data;if(i.event&&r)r._signal(i.event,i.data);else if(i.command)if(n[i.command])n[i.command].apply(n,i.args);else{if(!e[i.command])throw new Error(\"Unknown command:\"+i.command);e[i.command].apply(e,i.args)}else if(i.init){e.initBaseUrls(i.tlns),require(\"ace/lib/es5-shim\"),r=e.sender=e.initSender();var s=require(i.module)[i.classname];n=e.main=new s(r)}}})(this),define(\"ace/lib/oop\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.inherits=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})},t.mixin=function(e,t){for(var n in t)e[n]=t[n];return e},t.implement=function(e,n){t.mixin(e,n)}}),define(\"ace/range\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(e,t){return e.row-t.row||e.column-t.column},i=function(e,t,n,r){this.start={row:e,column:t},this.end={row:n,column:r}};(function(){this.isEqual=function(e){return this.start.row===e.start.row&&this.end.row===e.end.row&&this.start.column===e.start.column&&this.end.column===e.end.column},this.toString=function(){return\"Range: [\"+this.start.row+\"/\"+this.start.column+\"] -> [\"+this.end.row+\"/\"+this.end.column+\"]\"},this.contains=function(e,t){return this.compare(e,t)==0},this.compareRange=function(e){var t,n=e.end,r=e.start;return t=this.compare(n.row,n.column),t==1?(t=this.compare(r.row,r.column),t==1?2:t==0?1:0):t==-1?-2:(t=this.compare(r.row,r.column),t==-1?-1:t==1?42:0)},this.comparePoint=function(e){return this.compare(e.row,e.column)},this.containsRange=function(e){return this.comparePoint(e.start)==0&&this.comparePoint(e.end)==0},this.intersects=function(e){var t=this.compareRange(e);return t==-1||t==0||t==1},this.isEnd=function(e,t){return this.end.row==e&&this.end.column==t},this.isStart=function(e,t){return this.start.row==e&&this.start.column==t},this.setStart=function(e,t){typeof e==\"object\"?(this.start.column=e.column,this.start.row=e.row):(this.start.row=e,this.start.column=t)},this.setEnd=function(e,t){typeof e==\"object\"?(this.end.column=e.column,this.end.row=e.row):(this.end.row=e,this.end.column=t)},this.inside=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)||this.isStart(e,t)?!1:!0:!1},this.insideStart=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)?!1:!0:!1},this.insideEnd=function(e,t){return this.compare(e,t)==0?this.isStart(e,t)?!1:!0:!1},this.compare=function(e,t){return!this.isMultiLine()&&e===this.start.row?t<this.start.column?-1:t>this.end.column?1:0:e<this.start.row?-1:e>this.end.row?1:this.start.row===e?t>=this.start.column?0:-1:this.end.row===e?t<=this.end.column?0:1:0},this.compareStart=function(e,t){return this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.compareEnd=function(e,t){return this.end.row==e&&this.end.column==t?1:this.compare(e,t)},this.compareInside=function(e,t){return this.end.row==e&&this.end.column==t?1:this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.clipRows=function(e,t){if(this.end.row>t)var n={row:t+1,column:0};else if(this.end.row<e)var n={row:e,column:0};if(this.start.row>t)var r={row:t+1,column:0};else if(this.start.row<e)var r={row:e,column:0};return i.fromPoints(r||this.start,n||this.end)},this.extend=function(e,t){var n=this.compare(e,t);if(n==0)return this;if(n==-1)var r={row:e,column:t};else var s={row:e,column:t};return i.fromPoints(r||this.start,s||this.end)},this.isEmpty=function(){return this.start.row===this.end.row&&this.start.column===this.end.column},this.isMultiLine=function(){return this.start.row!==this.end.row},this.clone=function(){return i.fromPoints(this.start,this.end)},this.collapseRows=function(){return this.end.column==0?new i(this.start.row,0,Math.max(this.start.row,this.end.row-1),0):new i(this.start.row,0,this.end.row,0)},this.toScreenRange=function(e){var t=e.documentToScreenPosition(this.start),n=e.documentToScreenPosition(this.end);return new i(t.row,t.column,n.row,n.column)},this.moveBy=function(e,t){this.start.row+=e,this.start.column+=t,this.end.row+=e,this.end.column+=t}}).call(i.prototype),i.fromPoints=function(e,t){return new i(e.row,e.column,t.row,t.column)},i.comparePoints=r,i.comparePoints=function(e,t){return e.row-t.row||e.column-t.column},t.Range=i}),define(\"ace/apply_delta\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function r(e,t){throw console.log(\"Invalid Delta:\",e),\"Invalid Delta: \"+t}function i(e,t){return t.row>=0&&t.row<e.length&&t.column>=0&&t.column<=e[t.row].length}function s(e,t){t.action!=\"insert\"&&t.action!=\"remove\"&&r(t,\"delta.action must be 'insert' or 'remove'\"),t.lines instanceof Array||r(t,\"delta.lines must be an Array\"),(!t.start||!t.end)&&r(t,\"delta.start/end must be an present\");var n=t.start;i(e,t.start)||r(t,\"delta.start must be contained in document\");var s=t.end;t.action==\"remove\"&&!i(e,s)&&r(t,\"delta.end must contained in document for 'remove' actions\");var o=s.row-n.row,u=s.column-(o==0?n.column:0);(o!=t.lines.length-1||t.lines[o].length!=u)&&r(t,\"delta.range must match delta lines\")}t.applyDelta=function(e,t,n){var r=t.start.row,i=t.start.column,s=e[r]||\"\";switch(t.action){case\"insert\":var o=t.lines;if(o.length===1)e[r]=s.substring(0,i)+t.lines[0]+s.substring(i);else{var u=[r,1].concat(t.lines);e.splice.apply(e,u),e[r]=s.substring(0,i)+e[r],e[r+t.lines.length-1]+=s.substring(i)}break;case\"remove\":var a=t.end.column,f=t.end.row;r===f?e[r]=s.substring(0,i)+s.substring(a):e.splice(r,f-r+1,s.substring(0,i)+e[f].substring(a))}}}),define(\"ace/lib/event_emitter\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={},i=function(){this.propagationStopped=!0},s=function(){this.defaultPrevented=!0};r._emit=r._dispatchEvent=function(e,t){this._eventRegistry||(this._eventRegistry={}),this._defaultHandlers||(this._defaultHandlers={});var n=this._eventRegistry[e]||[],r=this._defaultHandlers[e];if(!n.length&&!r)return;if(typeof t!=\"object\"||!t)t={};t.type||(t.type=e),t.stopPropagation||(t.stopPropagation=i),t.preventDefault||(t.preventDefault=s),n=n.slice();for(var o=0;o<n.length;o++){n[o](t,this);if(t.propagationStopped)break}if(r&&!t.defaultPrevented)return r(t,this)},r._signal=function(e,t){var n=(this._eventRegistry||{})[e];if(!n)return;n=n.slice();for(var r=0;r<n.length;r++)n[r](t,this)},r.once=function(e,t){var n=this;t&&this.addEventListener(e,function r(){n.removeEventListener(e,r),t.apply(null,arguments)})},r.setDefaultHandler=function(e,t){var n=this._defaultHandlers;n||(n=this._defaultHandlers={_disabled_:{}});if(n[e]){var r=n[e],i=n._disabled_[e];i||(n._disabled_[e]=i=[]),i.push(r);var s=i.indexOf(t);s!=-1&&i.splice(s,1)}n[e]=t},r.removeDefaultHandler=function(e,t){var n=this._defaultHandlers;if(!n)return;var r=n._disabled_[e];if(n[e]==t){var i=n[e];r&&this.setDefaultHandler(e,r.pop())}else if(r){var s=r.indexOf(t);s!=-1&&r.splice(s,1)}},r.on=r.addEventListener=function(e,t,n){this._eventRegistry=this._eventRegistry||{};var r=this._eventRegistry[e];return r||(r=this._eventRegistry[e]=[]),r.indexOf(t)==-1&&r[n?\"unshift\":\"push\"](t),t},r.off=r.removeListener=r.removeEventListener=function(e,t){this._eventRegistry=this._eventRegistry||{};var n=this._eventRegistry[e];if(!n)return;var r=n.indexOf(t);r!==-1&&n.splice(r,1)},r.removeAllListeners=function(e){this._eventRegistry&&(this._eventRegistry[e]=[])},t.EventEmitter=r}),define(\"ace/anchor\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/event_emitter\").EventEmitter,s=t.Anchor=function(e,t,n){this.$onChange=this.onChange.bind(this),this.attach(e),typeof n==\"undefined\"?this.setPosition(t.row,t.column):this.setPosition(t,n)};(function(){function e(e,t,n){var r=n?e.column<=t.column:e.column<t.column;return e.row<t.row||e.row==t.row&&r}function t(t,n,r){var i=t.action==\"insert\",s=(i?1:-1)*(t.end.row-t.start.row),o=(i?1:-1)*(t.end.column-t.start.column),u=t.start,a=i?u:t.end;return e(n,u,r)?{row:n.row,column:n.column}:e(a,n,!r)?{row:n.row+s,column:n.column+(n.row==a.row?o:0)}:{row:u.row,column:u.column}}r.implement(this,i),this.getPosition=function(){return this.$clipPositionToDocument(this.row,this.column)},this.getDocument=function(){return this.document},this.$insertRight=!1,this.onChange=function(e){if(e.start.row==e.end.row&&e.start.row!=this.row)return;if(e.start.row>this.row)return;var n=t(e,{row:this.row,column:this.column},this.$insertRight);this.setPosition(n.row,n.column,!0)},this.setPosition=function(e,t,n){var r;n?r={row:e,column:t}:r=this.$clipPositionToDocument(e,t);if(this.row==r.row&&this.column==r.column)return;var i={row:this.row,column:this.column};this.row=r.row,this.column=r.column,this._signal(\"change\",{old:i,value:r})},this.detach=function(){this.document.removeEventListener(\"change\",this.$onChange)},this.attach=function(e){this.document=e||this.document,this.document.on(\"change\",this.$onChange)},this.$clipPositionToDocument=function(e,t){var n={};return e>=this.document.getLength()?(n.row=Math.max(0,this.document.getLength()-1),n.column=this.document.getLine(n.row).length):e<0?(n.row=0,n.column=0):(n.row=e,n.column=Math.min(this.document.getLine(n.row).length,Math.max(0,t))),t<0&&(n.column=0),n}}).call(s.prototype)}),define(\"ace/document\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/apply_delta\",\"ace/lib/event_emitter\",\"ace/range\",\"ace/anchor\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./apply_delta\").applyDelta,s=e(\"./lib/event_emitter\").EventEmitter,o=e(\"./range\").Range,u=e(\"./anchor\").Anchor,a=function(e){this.$lines=[\"\"],e.length===0?this.$lines=[\"\"]:Array.isArray(e)?this.insertMergedLines({row:0,column:0},e):this.insert({row:0,column:0},e)};(function(){r.implement(this,s),this.setValue=function(e){var t=this.getLength()-1;this.remove(new o(0,0,t,this.getLine(t).length)),this.insert({row:0,column:0},e)},this.getValue=function(){return this.getAllLines().join(this.getNewLineCharacter())},this.createAnchor=function(e,t){return new u(this,e,t)},\"aaa\".split(/a/).length===0?this.$split=function(e){return e.replace(/\\r\\n|\\r/g,\"\\n\").split(\"\\n\")}:this.$split=function(e){return e.split(/\\r\\n|\\r|\\n/)},this.$detectNewLine=function(e){var t=e.match(/^.*?(\\r\\n|\\r|\\n)/m);this.$autoNewLine=t?t[1]:\"\\n\",this._signal(\"changeNewLineMode\")},this.getNewLineCharacter=function(){switch(this.$newLineMode){case\"windows\":return\"\\r\\n\";case\"unix\":return\"\\n\";default:return this.$autoNewLine||\"\\n\"}},this.$autoNewLine=\"\",this.$newLineMode=\"auto\",this.setNewLineMode=function(e){if(this.$newLineMode===e)return;this.$newLineMode=e,this._signal(\"changeNewLineMode\")},this.getNewLineMode=function(){return this.$newLineMode},this.isNewLine=function(e){return e==\"\\r\\n\"||e==\"\\r\"||e==\"\\n\"},this.getLine=function(e){return this.$lines[e]||\"\"},this.getLines=function(e,t){return this.$lines.slice(e,t+1)},this.getAllLines=function(){return this.getLines(0,this.getLength())},this.getLength=function(){return this.$lines.length},this.getTextRange=function(e){return this.getLinesForRange(e).join(this.getNewLineCharacter())},this.getLinesForRange=function(e){var t;if(e.start.row===e.end.row)t=[this.getLine(e.start.row).substring(e.start.column,e.end.column)];else{t=this.getLines(e.start.row,e.end.row),t[0]=(t[0]||\"\").substring(e.start.column);var n=t.length-1;e.end.row-e.start.row==n&&(t[n]=t[n].substring(0,e.end.column))}return t},this.insertLines=function(e,t){return console.warn(\"Use of document.insertLines is deprecated. Use the insertFullLines method instead.\"),this.insertFullLines(e,t)},this.removeLines=function(e,t){return console.warn(\"Use of document.removeLines is deprecated. Use the removeFullLines method instead.\"),this.removeFullLines(e,t)},this.insertNewLine=function(e){return console.warn(\"Use of document.insertNewLine is deprecated. Use insertMergedLines(position, ['', '']) instead.\"),this.insertMergedLines(e,[\"\",\"\"])},this.insert=function(e,t){return this.getLength()<=1&&this.$detectNewLine(t),this.insertMergedLines(e,this.$split(t))},this.insertInLine=function(e,t){var n=this.clippedPos(e.row,e.column),r=this.pos(e.row,e.column+t.length);return this.applyDelta({start:n,end:r,action:\"insert\",lines:[t]},!0),this.clonePos(r)},this.clippedPos=function(e,t){var n=this.getLength();e===undefined?e=n:e<0?e=0:e>=n&&(e=n-1,t=undefined);var r=this.getLine(e);return t==undefined&&(t=r.length),t=Math.min(Math.max(t,0),r.length),{row:e,column:t}},this.clonePos=function(e){return{row:e.row,column:e.column}},this.pos=function(e,t){return{row:e,column:t}},this.$clipPosition=function(e){var t=this.getLength();return e.row>=t?(e.row=Math.max(0,t-1),e.column=this.getLine(t-1).length):(e.row=Math.max(0,e.row),e.column=Math.min(Math.max(e.column,0),this.getLine(e.row).length)),e},this.insertFullLines=function(e,t){e=Math.min(Math.max(e,0),this.getLength());var n=0;e<this.getLength()?(t=t.concat([\"\"]),n=0):(t=[\"\"].concat(t),e--,n=this.$lines[e].length),this.insertMergedLines({row:e,column:n},t)},this.insertMergedLines=function(e,t){var n=this.clippedPos(e.row,e.column),r={row:n.row+t.length-1,column:(t.length==1?n.column:0)+t[t.length-1].length};return this.applyDelta({start:n,end:r,action:\"insert\",lines:t}),this.clonePos(r)},this.remove=function(e){var t=this.clippedPos(e.start.row,e.start.column),n=this.clippedPos(e.end.row,e.end.column);return this.applyDelta({start:t,end:n,action:\"remove\",lines:this.getLinesForRange({start:t,end:n})}),this.clonePos(t)},this.removeInLine=function(e,t,n){var r=this.clippedPos(e,t),i=this.clippedPos(e,n);return this.applyDelta({start:r,end:i,action:\"remove\",lines:this.getLinesForRange({start:r,end:i})},!0),this.clonePos(r)},this.removeFullLines=function(e,t){e=Math.min(Math.max(0,e),this.getLength()-1),t=Math.min(Math.max(0,t),this.getLength()-1);var n=t==this.getLength()-1&&e>0,r=t<this.getLength()-1,i=n?e-1:e,s=n?this.getLine(i).length:0,u=r?t+1:t,a=r?0:this.getLine(u).length,f=new o(i,s,u,a),l=this.$lines.slice(e,t+1);return this.applyDelta({start:f.start,end:f.end,action:\"remove\",lines:this.getLinesForRange(f)}),l},this.removeNewLine=function(e){e<this.getLength()-1&&e>=0&&this.applyDelta({start:this.pos(e,this.getLine(e).length),end:this.pos(e+1,0),action:\"remove\",lines:[\"\",\"\"]})},this.replace=function(e,t){e instanceof o||(e=o.fromPoints(e.start,e.end));if(t.length===0&&e.isEmpty())return e.start;if(t==this.getTextRange(e))return e.end;this.remove(e);var n;return t?n=this.insert(e.start,t):n=e.start,n},this.applyDeltas=function(e){for(var t=0;t<e.length;t++)this.applyDelta(e[t])},this.revertDeltas=function(e){for(var t=e.length-1;t>=0;t--)this.revertDelta(e[t])},this.applyDelta=function(e,t){var n=e.action==\"insert\";if(n?e.lines.length<=1&&!e.lines[0]:!o.comparePoints(e.start,e.end))return;n&&e.lines.length>2e4&&this.$splitAndapplyLargeDelta(e,2e4),i(this.$lines,e,t),this._signal(\"change\",e)},this.$splitAndapplyLargeDelta=function(e,t){var n=e.lines,r=n.length,i=e.start.row,s=e.start.column,o=0,u=0;do{o=u,u+=t-1;var a=n.slice(o,u);if(u>r){e.lines=a,e.start.row=i+o,e.start.column=s;break}a.push(\"\"),this.applyDelta({start:this.pos(i+o,s),end:this.pos(i+u,s=0),action:e.action,lines:a},!0)}while(!0)},this.revertDelta=function(e){this.applyDelta({start:this.clonePos(e.start),end:this.clonePos(e.end),action:e.action==\"insert\"?\"remove\":\"insert\",lines:e.lines.slice()})},this.indexToPosition=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length;for(var i=t||0,s=n.length;i<s;i++){e-=n[i].length+r;if(e<0)return{row:i,column:e+n[i].length+r}}return{row:s-1,column:n[s-1].length}},this.positionToIndex=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length,i=0,s=Math.min(e.row,n.length);for(var o=t||0;o<s;++o)i+=n[o].length+r;return i+e.column}}).call(a.prototype),t.Document=a}),define(\"ace/lib/lang\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.last=function(e){return e[e.length-1]},t.stringReverse=function(e){return e.split(\"\").reverse().join(\"\")},t.stringRepeat=function(e,t){var n=\"\";while(t>0){t&1&&(n+=e);if(t>>=1)e+=e}return n};var r=/^\\s\\s*/,i=/\\s\\s*$/;t.stringTrimLeft=function(e){return e.replace(r,\"\")},t.stringTrimRight=function(e){return e.replace(i,\"\")},t.copyObject=function(e){var t={};for(var n in e)t[n]=e[n];return t},t.copyArray=function(e){var t=[];for(var n=0,r=e.length;n<r;n++)e[n]&&typeof e[n]==\"object\"?t[n]=this.copyObject(e[n]):t[n]=e[n];return t},t.deepCopy=function s(e){if(typeof e!=\"object\"||!e)return e;var t;if(Array.isArray(e)){t=[];for(var n=0;n<e.length;n++)t[n]=s(e[n]);return t}if(Object.prototype.toString.call(e)!==\"[object Object]\")return e;t={};for(var n in e)t[n]=s(e[n]);return t},t.arrayToMap=function(e){var t={};for(var n=0;n<e.length;n++)t[e[n]]=1;return t},t.createMap=function(e){var t=Object.create(null);for(var n in e)t[n]=e[n];return t},t.arrayRemove=function(e,t){for(var n=0;n<=e.length;n++)t===e[n]&&e.splice(n,1)},t.escapeRegExp=function(e){return e.replace(/([.*+?^${}()|[\\]\\/\\\\])/g,\"\\\\$1\")},t.escapeHTML=function(e){return e.replace(/&/g,\"&#38;\").replace(/\"/g,\"&#34;\").replace(/'/g,\"&#39;\").replace(/</g,\"&#60;\")},t.getMatchOffsets=function(e,t){var n=[];return e.replace(t,function(e){n.push({offset:arguments[arguments.length-2],length:e.length})}),n},t.deferredCall=function(e){var t=null,n=function(){t=null,e()},r=function(e){return r.cancel(),t=setTimeout(n,e||0),r};return r.schedule=r,r.call=function(){return this.cancel(),e(),r},r.cancel=function(){return clearTimeout(t),t=null,r},r.isPending=function(){return t},r},t.delayedCall=function(e,t){var n=null,r=function(){n=null,e()},i=function(e){n==null&&(n=setTimeout(r,e||t))};return i.delay=function(e){n&&clearTimeout(n),n=setTimeout(r,e||t)},i.schedule=i,i.call=function(){this.cancel(),e()},i.cancel=function(){n&&clearTimeout(n),n=null},i.isPending=function(){return n},i}}),define(\"ace/worker/mirror\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/document\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=e(\"../document\").Document,s=e(\"../lib/lang\"),o=t.Mirror=function(e){this.sender=e;var t=this.doc=new i(\"\"),n=this.deferredUpdate=s.delayedCall(this.onUpdate.bind(this)),r=this;e.on(\"change\",function(e){var i=e.data;if(i[0].start)t.applyDeltas(i);else for(var s=0;s<i.length;s+=2){if(Array.isArray(i[s+1]))var o={action:\"insert\",start:i[s],lines:i[s+1]};else var o={action:\"remove\",start:i[s],end:i[s+1]};t.applyDelta(o,!0)}if(r.$timeout)return n.schedule(r.$timeout);r.onUpdate()})};(function(){this.$timeout=500,this.setTimeout=function(e){this.$timeout=e},this.setValue=function(e){this.doc.setValue(e),this.deferredUpdate.schedule(this.$timeout)},this.getValue=function(e){this.sender.callback(this.doc.getValue(),e)},this.onUpdate=function(){},this.isPending=function(){return this.deferredUpdate.isPending()}}).call(o.prototype)}),define(\"ace/mode/lua/luaparse\",[\"require\",\"exports\",\"module\"],function(e,t,n){(function(e,n,r){r(t)})(this,\"luaparse\",function(e){\"use strict\";function m(e){if(mt){var t=vt.pop();t.complete(),n.locations&&(e.loc=t.loc),n.ranges&&(e.range=t.range)}return e}function w(e,t,n){for(var r=0,i=e.length;r<i;r++)if(e[r][t]===n)return r;return-1}function E(e){var t=g.call(arguments,1);return e=e.replace(/%(\\d)/g,function(e,n){return\"\"+t[n-1]||\"\"}),e}function S(){var e=g.call(arguments),t={},n,r;for(var i=0,s=e.length;i<s;i++){n=e[i];for(r in n)n.hasOwnProperty(r)&&(t[r]=n[r])}return t}function x(e){var t=E.apply(null,g.call(arguments,1)),n,r;throw\"undefined\"!=typeof e.line?(r=e.range[0]-e.lineStart,n=new SyntaxError(E(\"[%1:%2] %3\",e.line,r,t)),n.line=e.line,n.index=e.range[0],n.column=r):(r=C-D+1,n=new SyntaxError(E(\"[%1:%2] %3\",_,r,t)),n.index=C,n.line=_,n.column=r),n}function T(e,t){x(t,d.expectedToken,e,t.value)}function N(e,t){\"undefined\"==typeof t&&(t=A.value);if(\"undefined\"!=typeof e.type){var n;switch(e.type){case o:n=\"string\";break;case u:n=\"keyword\";break;case a:n=\"identifier\";break;case f:n=\"number\";break;case l:n=\"symbol\";break;case c:n=\"boolean\";break;case h:return x(e,d.unexpected,\"symbol\",\"nil\",t)}return x(e,d.unexpected,n,e.value,t)}return x(e,d.unexpected,\"symbol\",e,t)}function P(){H();while(45===t.charCodeAt(C)&&45===t.charCodeAt(C+1))X(),H();if(C>=r)return{type:s,value:\"<eof>\",line:_,lineStart:D,range:[C,C]};var e=t.charCodeAt(C),n=t.charCodeAt(C+1);M=C;if(et(e))return B();switch(e){case 39:case 34:return I();case 48:case 49:case 50:case 51:case 52:case 53:case 54:case 55:case 56:case 57:return R();case 46:if(Y(n))return R();if(46===n)return 46===t.charCodeAt(C+2)?F():j(\"..\");return j(\".\");case 61:if(61===n)return j(\"==\");return j(\"=\");case 62:if(61===n)return j(\">=\");return j(\">\");case 60:if(61===n)return j(\"<=\");return j(\"<\");case 126:if(61===n)return j(\"~=\");return x({},d.expected,\"=\",\"~\");case 58:if(58===n)return j(\"::\");return j(\":\");case 91:if(91===n||61===n)return q();return j(\"[\");case 42:case 47:case 94:case 37:case 44:case 123:case 125:case 93:case 40:case 41:case 59:case 35:case 45:case 43:return j(t.charAt(C))}return N(t.charAt(C))}function H(){while(C<r){var e=t.charCodeAt(C);if(Q(e))C++;else{if(!G(e))break;_++,D=++C}}}function B(){var e,n;while(tt(t.charCodeAt(++C)));return e=t.slice(M,C),nt(e)?n=u:\"true\"===e||\"false\"===e?(n=c,e=\"true\"===e):\"nil\"===e?(n=h,e=null):n=a,{type:n,value:e,line:_,lineStart:D,range:[M,C]}}function j(e){return C+=e.length,{type:l,value:e,line:_,lineStart:D,range:[M,C]}}function F(){return C+=3,{type:p,value:\"...\",line:_,lineStart:D,range:[M,C]}}function I(){var e=t.charCodeAt(C++),n=C,i=\"\",s;while(C<r){s=t.charCodeAt(C++);if(e===s)break;if(92===s)i+=t.slice(n,C-1)+W(),n=C;else if(C>=r||G(s))i+=t.slice(n,C-1),x({},d.unfinishedString,i+String.fromCharCode(s))}return i+=t.slice(n,C-1),{type:o,value:i,line:_,lineStart:D,range:[M,C]}}function q(){var e=V();return!1===e&&x(k,d.expected,\"[\",k.value),{type:o,value:e,line:_,lineStart:D,range:[M,C]}}function R(){var e=t.charAt(C),n=t.charAt(C+1),r=\"0\"===e&&\"xX\".indexOf(n||null)>=0?U():z();return{type:f,value:r,line:_,lineStart:D,range:[M,C]}}function U(){var e=0,n=1,r=1,i,s,o,u;u=C+=2,Z(t.charCodeAt(C))||x({},d.malformedNumber,t.slice(M,C));while(Z(t.charCodeAt(C)))C++;i=parseInt(t.slice(u,C),16);if(\".\"===t.charAt(C)){s=++C;while(Z(t.charCodeAt(C)))C++;e=t.slice(s,C),e=s===C?0:parseInt(e,16)/Math.pow(16,C-s)}if(\"pP\".indexOf(t.charAt(C)||null)>=0){C++,\"+-\".indexOf(t.charAt(C)||null)>=0&&(r=\"+\"===t.charAt(C++)?1:-1),o=C,Y(t.charCodeAt(C))||x({},d.malformedNumber,t.slice(M,C));while(Y(t.charCodeAt(C)))C++;n=t.slice(o,C),n=Math.pow(2,n*r)}return(i+e)*n}function z(){while(Y(t.charCodeAt(C)))C++;if(\".\"===t.charAt(C)){C++;while(Y(t.charCodeAt(C)))C++}if(\"eE\".indexOf(t.charAt(C)||null)>=0){C++,\"+-\".indexOf(t.charAt(C)||null)>=0&&C++,Y(t.charCodeAt(C))||x({},d.malformedNumber,t.slice(M,C));while(Y(t.charCodeAt(C)))C++}return parseFloat(t.slice(M,C))}function W(){var e=C;switch(t.charAt(C)){case\"n\":return C++,\"\\n\";case\"r\":return C++,\"\\r\";case\"t\":return C++,\"\t\";case\"v\":return C++,\"\u000b\";case\"b\":return C++,\"\\b\";case\"f\":return C++,\"\\f\";case\"z\":return C++,H(),\"\";case\"x\":if(Z(t.charCodeAt(C+1))&&Z(t.charCodeAt(C+2)))return C+=3,\"\\\\\"+t.slice(e,C);return\"\\\\\"+t.charAt(C++);default:if(Y(t.charCodeAt(C))){while(Y(t.charCodeAt(++C)));return\"\\\\\"+t.slice(e,C)}return t.charAt(C++)}}function X(){M=C,C+=2;var e=t.charAt(C),i=\"\",s=!1,o=C,u=D,a=_;\"[\"===e&&(i=V(),!1===i?i=e:s=!0);if(!s){while(C<r){if(G(t.charCodeAt(C)))break;C++}n.comments&&(i=t.slice(o,C))}if(n.comments){var f=v.comment(i,t.slice(M,C));n.locations&&(f.loc={start:{line:a,column:M-u},end:{line:_,column:C-D}}),n.ranges&&(f.range=[M,C]),O.push(f)}}function V(){var e=0,n=\"\",i=!1,s,o;C++;while(\"=\"===t.charAt(C+e))e++;if(\"[\"!==t.charAt(C+e))return!1;C+=e+1,G(t.charCodeAt(C))&&(_++,D=C++),o=C;while(C<r){s=t.charAt(C++),G(s.charCodeAt(0))&&(_++,D=C);if(\"]\"===s){i=!0;for(var u=0;u<e;u++)\"=\"!==t.charAt(C+u)&&(i=!1);\"]\"!==t.charAt(C+e)&&(i=!1)}if(i)break}return n+=t.slice(o,C-1),C+=e+1,n}function $(){L=k,k=A,A=P()}function J(e){return e===k.value?($(),!0):!1}function K(e){e===k.value?$():x(k,d.expected,e,k.value)}function Q(e){return 9===e||32===e||11===e||12===e}function G(e){return 10===e||13===e}function Y(e){return e>=48&&e<=57}function Z(e){return e>=48&&e<=57||e>=97&&e<=102||e>=65&&e<=70}function et(e){return e>=65&&e<=90||e>=97&&e<=122||95===e}function tt(e){return e>=65&&e<=90||e>=97&&e<=122||95===e||e>=48&&e<=57}function nt(e){switch(e.length){case 2:return\"do\"===e||\"if\"===e||\"in\"===e||\"or\"===e;case 3:return\"and\"===e||\"end\"===e||\"for\"===e||\"not\"===e;case 4:return\"else\"===e||\"goto\"===e||\"then\"===e;case 5:return\"break\"===e||\"local\"===e||\"until\"===e||\"while\"===e;case 6:return\"elseif\"===e||\"repeat\"===e||\"return\"===e;case 8:return\"function\"===e}return!1}function rt(e){return l===e.type?\"#-\".indexOf(e.value)>=0:u===e.type?\"not\"===e.value:!1}function it(e){switch(e.type){case\"CallExpression\":case\"TableCallExpression\":case\"StringCallExpression\":return!0}return!1}function st(e){if(s===e.type)return!0;if(u!==e.type)return!1;switch(e.value){case\"else\":case\"elseif\":case\"end\":case\"until\":return!0;default:return!1}}function ft(){ot.push(Array.apply(null,ot[ut++]))}function lt(){ot.pop(),ut--}function ct(e){if(-1!==b(ot[ut],e))return;ot[ut].push(e)}function ht(e){ct(e.name),pt(e,!0)}function pt(e,t){!t&&-1===w(at,\"name\",e.name)&&at.push(e),e.isLocal=t}function dt(e){return-1!==b(ot[ut],e)}function gt(){return new yt(k)}function yt(e){n.locations&&(this.loc={start:{line:e.line,column:e.range[0]-e.lineStart},end:{line:0,column:0}}),n.ranges&&(this.range=[e.range[0],0])}function bt(){mt&&vt.push(gt())}function wt(e){mt&&vt.push(e)}function Et(){$(),bt();var e=St();return s!==k.type&&N(k),mt&&!e.length&&(L=k),m(v.chunk(e))}function St(e){var t=[],r;n.scope&&ft();while(!st(k)){if(\"return\"===k.value){t.push(xt());break}r=xt(),r&&t.push(r)}return n.scope&&lt(),t}function xt(){bt();if(u===k.type)switch(k.value){case\"local\":return $(),Dt();case\"if\":return $(),Mt();case\"return\":return $(),Ot();case\"function\":$();var e=jt();return Bt(e);case\"while\":return $(),Lt();case\"for\":return $(),_t();case\"repeat\":return $(),At();case\"break\":return $(),Nt();case\"do\":return $(),kt();case\"goto\":return $(),Ct()}if(l===k.type&&J(\"::\"))return Tt();mt&&vt.pop();if(J(\";\"))return;return Pt()}function Tt(){var e=k.value,t=Ht();return n.scope&&(ct(\"::\"+e+\"::\"),pt(t,!0)),K(\"::\"),m(v.labelStatement(t))}function Nt(){return m(v.breakStatement())}function Ct(){var e=k.value,t=Ht();return n.scope&&(t.isLabel=dt(\"::\"+e+\"::\")),m(v.gotoStatement(t))}function kt(){var e=St();return K(\"end\"),m(v.doStatement(e))}function Lt(){var e=qt();K(\"do\");var t=St();return K(\"end\"),m(v.whileStatement(e,t))}function At(){var e=St();K(\"until\");var t=qt();return m(v.repeatStatement(t,e))}function Ot(){var e=[];if(\"end\"!==k.value){var t=It();null!=t&&e.push(t);while(J(\",\"))t=qt(),e.push(t);J(\";\")}return m(v.returnStatement(e))}function Mt(){var e=[],t,n,r;mt&&(r=vt[vt.length-1],vt.push(r)),t=qt(),K(\"then\"),n=St(),e.push(m(v.ifClause(t,n))),mt&&(r=gt());while(J(\"elseif\"))wt(r),t=qt(),K(\"then\"),n=St(),e.push(m(v.elseifClause(t,n))),mt&&(r=gt());return J(\"else\")&&(mt&&(r=new yt(L),vt.push(r)),n=St(),e.push(m(v.elseClause(n)))),K(\"end\"),m(v.ifStatement(e))}function _t(){var e=Ht(),t;n.scope&&ht(e);if(J(\"=\")){var r=qt();K(\",\");var i=qt(),s=J(\",\")?qt():null;return K(\"do\"),t=St(),K(\"end\"),m(v.forNumericStatement(e,r,i,s,t))}var o=[e];while(J(\",\"))e=Ht(),n.scope&&ht(e),o.push(e);K(\"in\");var u=[];do{var a=qt();u.push(a)}while(J(\",\"));return K(\"do\"),t=St(),K(\"end\"),m(v.forGenericStatement(o,u,t))}function Dt(){var e;if(a===k.type){var t=[],r=[];do e=Ht(),t.push(e);while(J(\",\"));if(J(\"=\"))do{var i=qt();r.push(i)}while(J(\",\"));if(n.scope)for(var s=0,o=t.length;s<o;s++)ht(t[s]);return m(v.localStatement(t,r))}if(J(\"function\"))return e=Ht(),n.scope&&ht(e),Bt(e,!0);T(\"<name>\",k)}function Pt(){var e=k,t,n;mt&&(n=gt()),t=zt();if(null==t)return N(k);if(\",=\".indexOf(k.value)>=0){var r=[t],i=[],s;while(J(\",\"))s=zt(),null==s&&T(\"<expression>\",k),r.push(s);K(\"=\");do s=qt(),i.push(s);while(J(\",\"));return wt(n),m(v.assignmentStatement(r,i))}return it(t)?(wt(n),m(v.callStatement(t))):N(e)}function Ht(){bt();var e=k.value;return a!==k.type&&T(\"<name>\",k),$(),m(v.identifier(e))}function Bt(e,t){var r=[];K(\"(\");if(!J(\")\"))for(;;)if(a===k.type){var i=Ht();n.scope&&ht(i),r.push(i);if(J(\",\"))continue;if(J(\")\"))break}else{if(p===k.type){r.push(Xt()),K(\")\");break}T(\"<name> or '...'\",k)}var s=St();return K(\"end\"),t=t||!1,m(v.functionStatement(e,r,t,s))}function jt(){var e,t,r;mt&&(r=gt()),e=Ht(),n.scope&&pt(e,!1);while(J(\".\"))wt(r),t=Ht(),n.scope&&pt(t,!1),e=m(v.memberExpression(e,\".\",t));return J(\":\")&&(wt(r),t=Ht(),n.scope&&pt(t,!1),e=m(v.memberExpression(e,\":\",t))),e}function Ft(){var e=[],t,n;for(;;){bt();if(l===k.type&&J(\"[\"))t=qt(),K(\"]\"),K(\"=\"),n=qt(),e.push(m(v.tableKey(t,n)));else if(a===k.type)t=qt(),J(\"=\")?(n=qt(),e.push(m(v.tableKeyString(t,n)))):e.push(m(v.tableValue(t)));else{if(null==(n=It())){vt.pop();break}e.push(m(v.tableValue(n)))}if(\",;\".indexOf(k.value)>=0){$();continue}if(\"}\"===k.value)break}return K(\"}\"),m(v.tableConstructorExpression(e))}function It(){var e=Ut(0);return e}function qt(){var e=It();if(null!=e)return e;T(\"<expression>\",k)}function Rt(e){var t=e.charCodeAt(0),n=e.length;if(1===n)switch(t){case 94:return 10;case 42:case 47:case 37:return 7;case 43:case 45:return 6;case 60:case 62:return 3}else if(2===n)switch(t){case 46:return 5;case 60:case 62:case 61:case 126:return 3;case 111:return 1}else if(97===t&&\"and\"===e)return 2;return 0}function Ut(e){var t=k.value,n,r;mt&&(r=gt());if(rt(k)){bt(),$();var i=Ut(8);i==null&&T(\"<expression>\",k),n=m(v.unaryExpression(t,i))}null==n&&(n=Xt(),null==n&&(n=zt()));if(null==n)return null;var s;for(;;){t=k.value,s=l===k.type||u===k.type?Rt(t):0;if(s===0||s<=e)break;(\"^\"===t||\"..\"===t)&&s--,$();var o=Ut(s);null==o&&T(\"<expression>\",k),mt&&vt.push(r),n=m(v.binaryExpression(t,n,o))}return n}function zt(){var e,t,r,i;mt&&(r=gt());if(a===k.type)t=k.value,e=Ht(),n.scope&&pt(e,i=dt(t));else{if(!J(\"(\"))return null;e=qt(),K(\")\"),n.scope&&(i=e.isLocal)}var s,u;for(;;)if(l===k.type)switch(k.value){case\"[\":wt(r),$(),s=qt(),e=m(v.indexExpression(e,s)),K(\"]\");break;case\".\":wt(r),$(),u=Ht(),n.scope&&pt(u,i),e=m(v.memberExpression(e,\".\",u));break;case\":\":wt(r),$(),u=Ht(),n.scope&&pt(u,i),e=m(v.memberExpression(e,\":\",u)),wt(r),e=Wt(e);break;case\"(\":case\"{\":wt(r),e=Wt(e);break;default:return e}else{if(o!==k.type)break;wt(r),e=Wt(e)}return e}function Wt(e){if(l===k.type)switch(k.value){case\"(\":$();var t=[],n=It();null!=n&&t.push(n);while(J(\",\"))n=qt(),t.push(n);return K(\")\"),m(v.callExpression(e,t));case\"{\":bt(),$();var r=Ft();return m(v.tableCallExpression(e,r))}else if(o===k.type)return m(v.stringCallExpression(e,Xt()));T(\"function arguments\",k)}function Xt(){var e=o|f|c|h|p,n=k.value,r=k.type,i;mt&&(i=gt());if(r&e){wt(i);var s=t.slice(k.range[0],k.range[1]);return $(),m(v.literal(r,n,s))}if(u===r&&\"function\"===n)return wt(i),$(),Bt(null);if(J(\"{\"))return wt(i),Ft()}function Vt(s,o){return\"undefined\"==typeof o&&\"object\"==typeof s&&(o=s,s=undefined),o||(o={}),t=s||\"\",n=S(i,o),C=0,_=1,D=0,r=t.length,ot=[[]],ut=0,at=[],vt=[],n.comments&&(O=[]),n.wait?e:Jt()}function $t(n){return t+=String(n),r=t.length,e}function Jt(e){\"undefined\"!=typeof e&&$t(e),r=t.length,mt=n.locations||n.ranges,A=P();var i=Et();n.comments&&(i.comments=O),n.scope&&(i.globals=at);if(vt.length>0)throw new Error(\"Location tracking failed. This is most likely a bug in luaparse\");return i}e.version=\"0.1.4\";var t,n,r,i=e.defaultOptions={wait:!1,comments:!0,scope:!1,locations:!1,ranges:!1},s=1,o=2,u=4,a=8,f=16,l=32,c=64,h=128,p=256;e.tokenTypes={EOF:s,StringLiteral:o,Keyword:u,Identifier:a,NumericLiteral:f,Punctuator:l,BooleanLiteral:c,NilLiteral:h,VarargLiteral:p};var d=e.errors={unexpected:\"Unexpected %1 '%2' near '%3'\",expected:\"'%1' expected near '%2'\",expectedToken:\"%1 expected near '%2'\",unfinishedString:\"unfinished string near '%1'\",malformedNumber:\"malformed number near '%1'\"},v=e.ast={labelStatement:function(e){return{type:\"LabelStatement\",label:e}},breakStatement:function(){return{type:\"BreakStatement\"}},gotoStatement:function(e){return{type:\"GotoStatement\",label:e}},returnStatement:function(e){return{type:\"ReturnStatement\",arguments:e}},ifStatement:function(e){return{type:\"IfStatement\",clauses:e}},ifClause:function(e,t){return{type:\"IfClause\",condition:e,body:t}},elseifClause:function(e,t){return{type:\"ElseifClause\",condition:e,body:t}},elseClause:function(e){return{type:\"ElseClause\",body:e}},whileStatement:function(e,t){return{type:\"WhileStatement\",condition:e,body:t}},doStatement:function(e){return{type:\"DoStatement\",body:e}},repeatStatement:function(e,t){return{type:\"RepeatStatement\",condition:e,body:t}},localStatement:function(e,t){return{type:\"LocalStatement\",variables:e,init:t}},assignmentStatement:function(e,t){return{type:\"AssignmentStatement\",variables:e,init:t}},callStatement:function(e){return{type:\"CallStatement\",expression:e}},functionStatement:function(e,t,n,r){return{type:\"FunctionDeclaration\",identifier:e,isLocal:n,parameters:t,body:r}},forNumericStatement:function(e,t,n,r,i){return{type:\"ForNumericStatement\",variable:e,start:t,end:n,step:r,body:i}},forGenericStatement:function(e,t,n){return{type:\"ForGenericStatement\",variables:e,iterators:t,body:n}},chunk:function(e){return{type:\"Chunk\",body:e}},identifier:function(e){return{type:\"Identifier\",name:e}},literal:function(e,t,n){return e=e===o?\"StringLiteral\":e===f?\"NumericLiteral\":e===c?\"BooleanLiteral\":e===h?\"NilLiteral\":\"VarargLiteral\",{type:e,value:t,raw:n}},tableKey:function(e,t){return{type:\"TableKey\",key:e,value:t}},tableKeyString:function(e,t){return{type:\"TableKeyString\",key:e,value:t}},tableValue:function(e){return{type:\"TableValue\",value:e}},tableConstructorExpression:function(e){return{type:\"TableConstructorExpression\",fields:e}},binaryExpression:function(e,t,n){var r=\"and\"===e||\"or\"===e?\"LogicalExpression\":\"BinaryExpression\";return{type:r,operator:e,left:t,right:n}},unaryExpression:function(e,t){return{type:\"UnaryExpression\",operator:e,argument:t}},memberExpression:function(e,t,n){return{type:\"MemberExpression\",indexer:t,identifier:n,base:e}},indexExpression:function(e,t){return{type:\"IndexExpression\",base:e,index:t}},callExpression:function(e,t){return{type:\"CallExpression\",base:e,arguments:t}},tableCallExpression:function(e,t){return{type:\"TableCallExpression\",base:e,arguments:t}},stringCallExpression:function(e,t){return{type:\"StringCallExpression\",base:e,argument:t}},comment:function(e,t){return{type:\"Comment\",value:e,raw:t}}},g=Array.prototype.slice,y=Object.prototype.toString,b=function(t,n){for(var r=0,i=t.length;r<i;r++)if(t[r]===n)return r;return-1},C,k,L,A,O,M,_,D;e.lex=P;var ot,ut,at,vt=[],mt;yt.prototype.complete=function(){n.locations&&(this.loc.end.line=L.line,this.loc.end.column=L.range[1]-L.lineStart),n.ranges&&(this.range[1]=L.range[1])},e.parse=Vt,e.write=$t,e.end=Jt})}),define(\"ace/mode/lua_worker\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/worker/mirror\",\"ace/mode/lua/luaparse\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../worker/mirror\").Mirror,s=e(\"../mode/lua/luaparse\"),o=t.Worker=function(e){i.call(this,e),this.setTimeout(500)};r.inherits(o,i),function(){this.onUpdate=function(){var e=this.doc.getValue(),t=[];try{s.parse(e)}catch(n){n instanceof SyntaxError&&t.push({row:n.line-1,column:n.column,text:n.message,type:\"error\"})}this.sender.emit(\"annotate\",t)}}.call(o.prototype)}),define(\"ace/lib/es5-shim\",[\"require\",\"exports\",\"module\"],function(e,t,n){function r(){}function w(e){try{return Object.defineProperty(e,\"sentinel\",{}),\"sentinel\"in e}catch(t){}}function H(e){return e=+e,e!==e?e=0:e!==0&&e!==1/0&&e!==-1/0&&(e=(e>0||-1)*Math.floor(Math.abs(e))),e}function B(e){var t=typeof e;return e===null||t===\"undefined\"||t===\"boolean\"||t===\"number\"||t===\"string\"}function j(e){var t,n,r;if(B(e))return e;n=e.valueOf;if(typeof n==\"function\"){t=n.call(e);if(B(t))return t}r=e.toString;if(typeof r==\"function\"){t=r.call(e);if(B(t))return t}throw new TypeError}Function.prototype.bind||(Function.prototype.bind=function(t){var n=this;if(typeof n!=\"function\")throw new TypeError(\"Function.prototype.bind called on incompatible \"+n);var i=u.call(arguments,1),s=function(){if(this instanceof s){var e=n.apply(this,i.concat(u.call(arguments)));return Object(e)===e?e:this}return n.apply(t,i.concat(u.call(arguments)))};return n.prototype&&(r.prototype=n.prototype,s.prototype=new r,r.prototype=null),s});var i=Function.prototype.call,s=Array.prototype,o=Object.prototype,u=s.slice,a=i.bind(o.toString),f=i.bind(o.hasOwnProperty),l,c,h,p,d;if(d=f(o,\"__defineGetter__\"))l=i.bind(o.__defineGetter__),c=i.bind(o.__defineSetter__),h=i.bind(o.__lookupGetter__),p=i.bind(o.__lookupSetter__);if([1,2].splice(0).length!=2)if(!function(){function e(e){var t=new Array(e+2);return t[0]=t[1]=0,t}var t=[],n;t.splice.apply(t,e(20)),t.splice.apply(t,e(26)),n=t.length,t.splice(5,0,\"XXX\"),n+1==t.length;if(n+1==t.length)return!0}())Array.prototype.splice=function(e,t){var n=this.length;e>0?e>n&&(e=n):e==void 0?e=0:e<0&&(e=Math.max(n+e,0)),e+t<n||(t=n-e);var r=this.slice(e,e+t),i=u.call(arguments,2),s=i.length;if(e===n)s&&this.push.apply(this,i);else{var o=Math.min(t,n-e),a=e+o,f=a+s-o,l=n-a,c=n-o;if(f<a)for(var h=0;h<l;++h)this[f+h]=this[a+h];else if(f>a)for(h=l;h--;)this[f+h]=this[a+h];if(s&&e===c)this.length=c,this.push.apply(this,i);else{this.length=c+s;for(h=0;h<s;++h)this[e+h]=i[h]}}return r};else{var v=Array.prototype.splice;Array.prototype.splice=function(e,t){return arguments.length?v.apply(this,[e===void 0?0:e,t===void 0?this.length-e:t].concat(u.call(arguments,2))):[]}}Array.isArray||(Array.isArray=function(t){return a(t)==\"[object Array]\"});var m=Object(\"a\"),g=m[0]!=\"a\"||!(0 in m);Array.prototype.forEach||(Array.prototype.forEach=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=arguments[1],s=-1,o=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError;while(++s<o)s in r&&t.call(i,r[s],s,n)}),Array.prototype.map||(Array.prototype.map=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=Array(i),o=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var u=0;u<i;u++)u in r&&(s[u]=t.call(o,r[u],u,n));return s}),Array.prototype.filter||(Array.prototype.filter=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=[],o,u=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var f=0;f<i;f++)f in r&&(o=r[f],t.call(u,o,f,n)&&s.push(o));return s}),Array.prototype.every||(Array.prototype.every=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&!t.call(s,r[o],o,n))return!1;return!0}),Array.prototype.some||(Array.prototype.some=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&t.call(s,r[o],o,n))return!0;return!1}),Array.prototype.reduce||(Array.prototype.reduce=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduce of empty array with no initial value\");var s=0,o;if(arguments.length>=2)o=arguments[1];else do{if(s in r){o=r[s++];break}if(++s>=i)throw new TypeError(\"reduce of empty array with no initial value\")}while(!0);for(;s<i;s++)s in r&&(o=t.call(void 0,o,r[s],s,n));return o}),Array.prototype.reduceRight||(Array.prototype.reduceRight=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduceRight of empty array with no initial value\");var s,o=i-1;if(arguments.length>=2)s=arguments[1];else do{if(o in r){s=r[o--];break}if(--o<0)throw new TypeError(\"reduceRight of empty array with no initial value\")}while(!0);do o in this&&(s=t.call(void 0,s,r[o],o,n));while(o--);return s});if(!Array.prototype.indexOf||[0,1].indexOf(1,2)!=-1)Array.prototype.indexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=0;arguments.length>1&&(i=H(arguments[1])),i=i>=0?i:Math.max(0,r+i);for(;i<r;i++)if(i in n&&n[i]===t)return i;return-1};if(!Array.prototype.lastIndexOf||[0,1].lastIndexOf(0,-3)!=-1)Array.prototype.lastIndexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=r-1;arguments.length>1&&(i=Math.min(i,H(arguments[1]))),i=i>=0?i:r-Math.abs(i);for(;i>=0;i--)if(i in n&&t===n[i])return i;return-1};Object.getPrototypeOf||(Object.getPrototypeOf=function(t){return t.__proto__||(t.constructor?t.constructor.prototype:o)});if(!Object.getOwnPropertyDescriptor){var y=\"Object.getOwnPropertyDescriptor called on a non-object: \";Object.getOwnPropertyDescriptor=function(t,n){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(y+t);if(!f(t,n))return;var r,i,s;r={enumerable:!0,configurable:!0};if(d){var u=t.__proto__;t.__proto__=o;var i=h(t,n),s=p(t,n);t.__proto__=u;if(i||s)return i&&(r.get=i),s&&(r.set=s),r}return r.value=t[n],r}}Object.getOwnPropertyNames||(Object.getOwnPropertyNames=function(t){return Object.keys(t)});if(!Object.create){var b;Object.prototype.__proto__===null?b=function(){return{__proto__:null}}:b=function(){var e={};for(var t in e)e[t]=null;return e.constructor=e.hasOwnProperty=e.propertyIsEnumerable=e.isPrototypeOf=e.toLocaleString=e.toString=e.valueOf=e.__proto__=null,e},Object.create=function(t,n){var r;if(t===null)r=b();else{if(typeof t!=\"object\")throw new TypeError(\"typeof prototype[\"+typeof t+\"] != 'object'\");var i=function(){};i.prototype=t,r=new i,r.__proto__=t}return n!==void 0&&Object.defineProperties(r,n),r}}if(Object.defineProperty){var E=w({}),S=typeof document==\"undefined\"||w(document.createElement(\"div\"));if(!E||!S)var x=Object.defineProperty}if(!Object.defineProperty||x){var T=\"Property description must be an object: \",N=\"Object.defineProperty called on non-object: \",C=\"getters & setters can not be defined on this javascript engine\";Object.defineProperty=function(t,n,r){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(N+t);if(typeof r!=\"object\"&&typeof r!=\"function\"||r===null)throw new TypeError(T+r);if(x)try{return x.call(Object,t,n,r)}catch(i){}if(f(r,\"value\"))if(d&&(h(t,n)||p(t,n))){var s=t.__proto__;t.__proto__=o,delete t[n],t[n]=r.value,t.__proto__=s}else t[n]=r.value;else{if(!d)throw new TypeError(C);f(r,\"get\")&&l(t,n,r.get),f(r,\"set\")&&c(t,n,r.set)}return t}}Object.defineProperties||(Object.defineProperties=function(t,n){for(var r in n)f(n,r)&&Object.defineProperty(t,r,n[r]);return t}),Object.seal||(Object.seal=function(t){return t}),Object.freeze||(Object.freeze=function(t){return t});try{Object.freeze(function(){})}catch(k){Object.freeze=function(t){return function(n){return typeof n==\"function\"?n:t(n)}}(Object.freeze)}Object.preventExtensions||(Object.preventExtensions=function(t){return t}),Object.isSealed||(Object.isSealed=function(t){return!1}),Object.isFrozen||(Object.isFrozen=function(t){return!1}),Object.isExtensible||(Object.isExtensible=function(t){if(Object(t)===t)throw new TypeError;var n=\"\";while(f(t,n))n+=\"?\";t[n]=!0;var r=f(t,n);return delete t[n],r});if(!Object.keys){var L=!0,A=[\"toString\",\"toLocaleString\",\"valueOf\",\"hasOwnProperty\",\"isPrototypeOf\",\"propertyIsEnumerable\",\"constructor\"],O=A.length;for(var M in{toString:null})L=!1;Object.keys=function I(e){if(typeof e!=\"object\"&&typeof e!=\"function\"||e===null)throw new TypeError(\"Object.keys called on a non-object\");var I=[];for(var t in e)f(e,t)&&I.push(t);if(L)for(var n=0,r=O;n<r;n++){var i=A[n];f(e,i)&&I.push(i)}return I}}Date.now||(Date.now=function(){return(new Date).getTime()});var _=\"\t\\n\u000b\\f\\r \\u00a0\\u1680\\u180e\\u2000\\u2001\\u2002\\u2003\\u2004\\u2005\\u2006\\u2007\\u2008\\u2009\\u200a\\u202f\\u205f\\u3000\\u2028\\u2029\\ufeff\";if(!String.prototype.trim||_.trim()){_=\"[\"+_+\"]\";var D=new RegExp(\"^\"+_+_+\"*\"),P=new RegExp(_+_+\"*$\");String.prototype.trim=function(){return String(this).replace(D,\"\").replace(P,\"\")}}var F=function(e){if(e==null)throw new TypeError(\"can't convert \"+e+\" to object\");return Object(e)}})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/worker-php.js",
    "content": "\"no use strict\";(function(e){function t(e,t){var n=e,r=\"\";while(n){var i=t[n];if(typeof i==\"string\")return i+r;if(i)return i.location.replace(/\\/*$/,\"/\")+(r||i.main||i.name);if(i===!1)return\"\";var s=n.lastIndexOf(\"/\");if(s===-1)break;r=n.substr(s)+r,n=n.slice(0,s)}return e}if(typeof e.window!=\"undefined\"&&e.document)return;if(e.require&&e.define)return;e.console||(e.console=function(){var e=Array.prototype.slice.call(arguments,0);postMessage({type:\"log\",data:e})},e.console.error=e.console.warn=e.console.log=e.console.trace=e.console),e.window=e,e.ace=e,e.onerror=function(e,t,n,r,i){postMessage({type:\"error\",data:{message:e,data:i.data,file:t,line:n,col:r,stack:i.stack}})},e.normalizeModule=function(t,n){if(n.indexOf(\"!\")!==-1){var r=n.split(\"!\");return e.normalizeModule(t,r[0])+\"!\"+e.normalizeModule(t,r[1])}if(n.charAt(0)==\".\"){var i=t.split(\"/\").slice(0,-1).join(\"/\");n=(i?i+\"/\":\"\")+n;while(n.indexOf(\".\")!==-1&&s!=n){var s=n;n=n.replace(/^\\.\\//,\"\").replace(/\\/\\.\\//,\"/\").replace(/[^\\/]+\\/\\.\\.\\//,\"\")}}return n},e.require=function(r,i){i||(i=r,r=null);if(!i.charAt)throw new Error(\"worker.js require() accepts only (parentId, id) as arguments\");i=e.normalizeModule(r,i);var s=e.require.modules[i];if(s)return s.initialized||(s.initialized=!0,s.exports=s.factory().exports),s.exports;if(!e.require.tlns)return console.log(\"unable to load \"+i);var o=t(i,e.require.tlns);return o.slice(-3)!=\".js\"&&(o+=\".js\"),e.require.id=i,e.require.modules[i]={},importScripts(o),e.require(r,i)},e.require.modules={},e.require.tlns={},e.define=function(t,n,r){arguments.length==2?(r=n,typeof t!=\"string\"&&(n=t,t=e.require.id)):arguments.length==1&&(r=t,n=[],t=e.require.id);if(typeof r!=\"function\"){e.require.modules[t]={exports:r,initialized:!0};return}n.length||(n=[\"require\",\"exports\",\"module\"]);var i=function(n){return e.require(t,n)};e.require.modules[t]={exports:{},factory:function(){var e=this,t=r.apply(this,n.map(function(t){switch(t){case\"require\":return i;case\"exports\":return e.exports;case\"module\":return e;default:return i(t)}}));return t&&(e.exports=t),e}}},e.define.amd={},require.tlns={},e.initBaseUrls=function(t){for(var n in t)require.tlns[n]=t[n]},e.initSender=function(){var n=e.require(\"ace/lib/event_emitter\").EventEmitter,r=e.require(\"ace/lib/oop\"),i=function(){};return function(){r.implement(this,n),this.callback=function(e,t){postMessage({type:\"call\",id:t,data:e})},this.emit=function(e,t){postMessage({type:\"event\",name:e,data:t})}}.call(i.prototype),new i};var n=e.main=null,r=e.sender=null;e.onmessage=function(t){var i=t.data;if(i.event&&r)r._signal(i.event,i.data);else if(i.command)if(n[i.command])n[i.command].apply(n,i.args);else{if(!e[i.command])throw new Error(\"Unknown command:\"+i.command);e[i.command].apply(e,i.args)}else if(i.init){e.initBaseUrls(i.tlns),require(\"ace/lib/es5-shim\"),r=e.sender=e.initSender();var s=require(i.module)[i.classname];n=e.main=new s(r)}}})(this),define(\"ace/lib/oop\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.inherits=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})},t.mixin=function(e,t){for(var n in t)e[n]=t[n];return e},t.implement=function(e,n){t.mixin(e,n)}}),define(\"ace/range\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(e,t){return e.row-t.row||e.column-t.column},i=function(e,t,n,r){this.start={row:e,column:t},this.end={row:n,column:r}};(function(){this.isEqual=function(e){return this.start.row===e.start.row&&this.end.row===e.end.row&&this.start.column===e.start.column&&this.end.column===e.end.column},this.toString=function(){return\"Range: [\"+this.start.row+\"/\"+this.start.column+\"] -> [\"+this.end.row+\"/\"+this.end.column+\"]\"},this.contains=function(e,t){return this.compare(e,t)==0},this.compareRange=function(e){var t,n=e.end,r=e.start;return t=this.compare(n.row,n.column),t==1?(t=this.compare(r.row,r.column),t==1?2:t==0?1:0):t==-1?-2:(t=this.compare(r.row,r.column),t==-1?-1:t==1?42:0)},this.comparePoint=function(e){return this.compare(e.row,e.column)},this.containsRange=function(e){return this.comparePoint(e.start)==0&&this.comparePoint(e.end)==0},this.intersects=function(e){var t=this.compareRange(e);return t==-1||t==0||t==1},this.isEnd=function(e,t){return this.end.row==e&&this.end.column==t},this.isStart=function(e,t){return this.start.row==e&&this.start.column==t},this.setStart=function(e,t){typeof e==\"object\"?(this.start.column=e.column,this.start.row=e.row):(this.start.row=e,this.start.column=t)},this.setEnd=function(e,t){typeof e==\"object\"?(this.end.column=e.column,this.end.row=e.row):(this.end.row=e,this.end.column=t)},this.inside=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)||this.isStart(e,t)?!1:!0:!1},this.insideStart=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)?!1:!0:!1},this.insideEnd=function(e,t){return this.compare(e,t)==0?this.isStart(e,t)?!1:!0:!1},this.compare=function(e,t){return!this.isMultiLine()&&e===this.start.row?t<this.start.column?-1:t>this.end.column?1:0:e<this.start.row?-1:e>this.end.row?1:this.start.row===e?t>=this.start.column?0:-1:this.end.row===e?t<=this.end.column?0:1:0},this.compareStart=function(e,t){return this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.compareEnd=function(e,t){return this.end.row==e&&this.end.column==t?1:this.compare(e,t)},this.compareInside=function(e,t){return this.end.row==e&&this.end.column==t?1:this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.clipRows=function(e,t){if(this.end.row>t)var n={row:t+1,column:0};else if(this.end.row<e)var n={row:e,column:0};if(this.start.row>t)var r={row:t+1,column:0};else if(this.start.row<e)var r={row:e,column:0};return i.fromPoints(r||this.start,n||this.end)},this.extend=function(e,t){var n=this.compare(e,t);if(n==0)return this;if(n==-1)var r={row:e,column:t};else var s={row:e,column:t};return i.fromPoints(r||this.start,s||this.end)},this.isEmpty=function(){return this.start.row===this.end.row&&this.start.column===this.end.column},this.isMultiLine=function(){return this.start.row!==this.end.row},this.clone=function(){return i.fromPoints(this.start,this.end)},this.collapseRows=function(){return this.end.column==0?new i(this.start.row,0,Math.max(this.start.row,this.end.row-1),0):new i(this.start.row,0,this.end.row,0)},this.toScreenRange=function(e){var t=e.documentToScreenPosition(this.start),n=e.documentToScreenPosition(this.end);return new i(t.row,t.column,n.row,n.column)},this.moveBy=function(e,t){this.start.row+=e,this.start.column+=t,this.end.row+=e,this.end.column+=t}}).call(i.prototype),i.fromPoints=function(e,t){return new i(e.row,e.column,t.row,t.column)},i.comparePoints=r,i.comparePoints=function(e,t){return e.row-t.row||e.column-t.column},t.Range=i}),define(\"ace/apply_delta\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function r(e,t){throw console.log(\"Invalid Delta:\",e),\"Invalid Delta: \"+t}function i(e,t){return t.row>=0&&t.row<e.length&&t.column>=0&&t.column<=e[t.row].length}function s(e,t){t.action!=\"insert\"&&t.action!=\"remove\"&&r(t,\"delta.action must be 'insert' or 'remove'\"),t.lines instanceof Array||r(t,\"delta.lines must be an Array\"),(!t.start||!t.end)&&r(t,\"delta.start/end must be an present\");var n=t.start;i(e,t.start)||r(t,\"delta.start must be contained in document\");var s=t.end;t.action==\"remove\"&&!i(e,s)&&r(t,\"delta.end must contained in document for 'remove' actions\");var o=s.row-n.row,u=s.column-(o==0?n.column:0);(o!=t.lines.length-1||t.lines[o].length!=u)&&r(t,\"delta.range must match delta lines\")}t.applyDelta=function(e,t,n){var r=t.start.row,i=t.start.column,s=e[r]||\"\";switch(t.action){case\"insert\":var o=t.lines;if(o.length===1)e[r]=s.substring(0,i)+t.lines[0]+s.substring(i);else{var u=[r,1].concat(t.lines);e.splice.apply(e,u),e[r]=s.substring(0,i)+e[r],e[r+t.lines.length-1]+=s.substring(i)}break;case\"remove\":var a=t.end.column,f=t.end.row;r===f?e[r]=s.substring(0,i)+s.substring(a):e.splice(r,f-r+1,s.substring(0,i)+e[f].substring(a))}}}),define(\"ace/lib/event_emitter\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={},i=function(){this.propagationStopped=!0},s=function(){this.defaultPrevented=!0};r._emit=r._dispatchEvent=function(e,t){this._eventRegistry||(this._eventRegistry={}),this._defaultHandlers||(this._defaultHandlers={});var n=this._eventRegistry[e]||[],r=this._defaultHandlers[e];if(!n.length&&!r)return;if(typeof t!=\"object\"||!t)t={};t.type||(t.type=e),t.stopPropagation||(t.stopPropagation=i),t.preventDefault||(t.preventDefault=s),n=n.slice();for(var o=0;o<n.length;o++){n[o](t,this);if(t.propagationStopped)break}if(r&&!t.defaultPrevented)return r(t,this)},r._signal=function(e,t){var n=(this._eventRegistry||{})[e];if(!n)return;n=n.slice();for(var r=0;r<n.length;r++)n[r](t,this)},r.once=function(e,t){var n=this;t&&this.addEventListener(e,function r(){n.removeEventListener(e,r),t.apply(null,arguments)})},r.setDefaultHandler=function(e,t){var n=this._defaultHandlers;n||(n=this._defaultHandlers={_disabled_:{}});if(n[e]){var r=n[e],i=n._disabled_[e];i||(n._disabled_[e]=i=[]),i.push(r);var s=i.indexOf(t);s!=-1&&i.splice(s,1)}n[e]=t},r.removeDefaultHandler=function(e,t){var n=this._defaultHandlers;if(!n)return;var r=n._disabled_[e];if(n[e]==t){var i=n[e];r&&this.setDefaultHandler(e,r.pop())}else if(r){var s=r.indexOf(t);s!=-1&&r.splice(s,1)}},r.on=r.addEventListener=function(e,t,n){this._eventRegistry=this._eventRegistry||{};var r=this._eventRegistry[e];return r||(r=this._eventRegistry[e]=[]),r.indexOf(t)==-1&&r[n?\"unshift\":\"push\"](t),t},r.off=r.removeListener=r.removeEventListener=function(e,t){this._eventRegistry=this._eventRegistry||{};var n=this._eventRegistry[e];if(!n)return;var r=n.indexOf(t);r!==-1&&n.splice(r,1)},r.removeAllListeners=function(e){this._eventRegistry&&(this._eventRegistry[e]=[])},t.EventEmitter=r}),define(\"ace/anchor\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/event_emitter\").EventEmitter,s=t.Anchor=function(e,t,n){this.$onChange=this.onChange.bind(this),this.attach(e),typeof n==\"undefined\"?this.setPosition(t.row,t.column):this.setPosition(t,n)};(function(){function e(e,t,n){var r=n?e.column<=t.column:e.column<t.column;return e.row<t.row||e.row==t.row&&r}function t(t,n,r){var i=t.action==\"insert\",s=(i?1:-1)*(t.end.row-t.start.row),o=(i?1:-1)*(t.end.column-t.start.column),u=t.start,a=i?u:t.end;return e(n,u,r)?{row:n.row,column:n.column}:e(a,n,!r)?{row:n.row+s,column:n.column+(n.row==a.row?o:0)}:{row:u.row,column:u.column}}r.implement(this,i),this.getPosition=function(){return this.$clipPositionToDocument(this.row,this.column)},this.getDocument=function(){return this.document},this.$insertRight=!1,this.onChange=function(e){if(e.start.row==e.end.row&&e.start.row!=this.row)return;if(e.start.row>this.row)return;var n=t(e,{row:this.row,column:this.column},this.$insertRight);this.setPosition(n.row,n.column,!0)},this.setPosition=function(e,t,n){var r;n?r={row:e,column:t}:r=this.$clipPositionToDocument(e,t);if(this.row==r.row&&this.column==r.column)return;var i={row:this.row,column:this.column};this.row=r.row,this.column=r.column,this._signal(\"change\",{old:i,value:r})},this.detach=function(){this.document.removeEventListener(\"change\",this.$onChange)},this.attach=function(e){this.document=e||this.document,this.document.on(\"change\",this.$onChange)},this.$clipPositionToDocument=function(e,t){var n={};return e>=this.document.getLength()?(n.row=Math.max(0,this.document.getLength()-1),n.column=this.document.getLine(n.row).length):e<0?(n.row=0,n.column=0):(n.row=e,n.column=Math.min(this.document.getLine(n.row).length,Math.max(0,t))),t<0&&(n.column=0),n}}).call(s.prototype)}),define(\"ace/document\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/apply_delta\",\"ace/lib/event_emitter\",\"ace/range\",\"ace/anchor\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./apply_delta\").applyDelta,s=e(\"./lib/event_emitter\").EventEmitter,o=e(\"./range\").Range,u=e(\"./anchor\").Anchor,a=function(e){this.$lines=[\"\"],e.length===0?this.$lines=[\"\"]:Array.isArray(e)?this.insertMergedLines({row:0,column:0},e):this.insert({row:0,column:0},e)};(function(){r.implement(this,s),this.setValue=function(e){var t=this.getLength()-1;this.remove(new o(0,0,t,this.getLine(t).length)),this.insert({row:0,column:0},e)},this.getValue=function(){return this.getAllLines().join(this.getNewLineCharacter())},this.createAnchor=function(e,t){return new u(this,e,t)},\"aaa\".split(/a/).length===0?this.$split=function(e){return e.replace(/\\r\\n|\\r/g,\"\\n\").split(\"\\n\")}:this.$split=function(e){return e.split(/\\r\\n|\\r|\\n/)},this.$detectNewLine=function(e){var t=e.match(/^.*?(\\r\\n|\\r|\\n)/m);this.$autoNewLine=t?t[1]:\"\\n\",this._signal(\"changeNewLineMode\")},this.getNewLineCharacter=function(){switch(this.$newLineMode){case\"windows\":return\"\\r\\n\";case\"unix\":return\"\\n\";default:return this.$autoNewLine||\"\\n\"}},this.$autoNewLine=\"\",this.$newLineMode=\"auto\",this.setNewLineMode=function(e){if(this.$newLineMode===e)return;this.$newLineMode=e,this._signal(\"changeNewLineMode\")},this.getNewLineMode=function(){return this.$newLineMode},this.isNewLine=function(e){return e==\"\\r\\n\"||e==\"\\r\"||e==\"\\n\"},this.getLine=function(e){return this.$lines[e]||\"\"},this.getLines=function(e,t){return this.$lines.slice(e,t+1)},this.getAllLines=function(){return this.getLines(0,this.getLength())},this.getLength=function(){return this.$lines.length},this.getTextRange=function(e){return this.getLinesForRange(e).join(this.getNewLineCharacter())},this.getLinesForRange=function(e){var t;if(e.start.row===e.end.row)t=[this.getLine(e.start.row).substring(e.start.column,e.end.column)];else{t=this.getLines(e.start.row,e.end.row),t[0]=(t[0]||\"\").substring(e.start.column);var n=t.length-1;e.end.row-e.start.row==n&&(t[n]=t[n].substring(0,e.end.column))}return t},this.insertLines=function(e,t){return console.warn(\"Use of document.insertLines is deprecated. Use the insertFullLines method instead.\"),this.insertFullLines(e,t)},this.removeLines=function(e,t){return console.warn(\"Use of document.removeLines is deprecated. Use the removeFullLines method instead.\"),this.removeFullLines(e,t)},this.insertNewLine=function(e){return console.warn(\"Use of document.insertNewLine is deprecated. Use insertMergedLines(position, ['', '']) instead.\"),this.insertMergedLines(e,[\"\",\"\"])},this.insert=function(e,t){return this.getLength()<=1&&this.$detectNewLine(t),this.insertMergedLines(e,this.$split(t))},this.insertInLine=function(e,t){var n=this.clippedPos(e.row,e.column),r=this.pos(e.row,e.column+t.length);return this.applyDelta({start:n,end:r,action:\"insert\",lines:[t]},!0),this.clonePos(r)},this.clippedPos=function(e,t){var n=this.getLength();e===undefined?e=n:e<0?e=0:e>=n&&(e=n-1,t=undefined);var r=this.getLine(e);return t==undefined&&(t=r.length),t=Math.min(Math.max(t,0),r.length),{row:e,column:t}},this.clonePos=function(e){return{row:e.row,column:e.column}},this.pos=function(e,t){return{row:e,column:t}},this.$clipPosition=function(e){var t=this.getLength();return e.row>=t?(e.row=Math.max(0,t-1),e.column=this.getLine(t-1).length):(e.row=Math.max(0,e.row),e.column=Math.min(Math.max(e.column,0),this.getLine(e.row).length)),e},this.insertFullLines=function(e,t){e=Math.min(Math.max(e,0),this.getLength());var n=0;e<this.getLength()?(t=t.concat([\"\"]),n=0):(t=[\"\"].concat(t),e--,n=this.$lines[e].length),this.insertMergedLines({row:e,column:n},t)},this.insertMergedLines=function(e,t){var n=this.clippedPos(e.row,e.column),r={row:n.row+t.length-1,column:(t.length==1?n.column:0)+t[t.length-1].length};return this.applyDelta({start:n,end:r,action:\"insert\",lines:t}),this.clonePos(r)},this.remove=function(e){var t=this.clippedPos(e.start.row,e.start.column),n=this.clippedPos(e.end.row,e.end.column);return this.applyDelta({start:t,end:n,action:\"remove\",lines:this.getLinesForRange({start:t,end:n})}),this.clonePos(t)},this.removeInLine=function(e,t,n){var r=this.clippedPos(e,t),i=this.clippedPos(e,n);return this.applyDelta({start:r,end:i,action:\"remove\",lines:this.getLinesForRange({start:r,end:i})},!0),this.clonePos(r)},this.removeFullLines=function(e,t){e=Math.min(Math.max(0,e),this.getLength()-1),t=Math.min(Math.max(0,t),this.getLength()-1);var n=t==this.getLength()-1&&e>0,r=t<this.getLength()-1,i=n?e-1:e,s=n?this.getLine(i).length:0,u=r?t+1:t,a=r?0:this.getLine(u).length,f=new o(i,s,u,a),l=this.$lines.slice(e,t+1);return this.applyDelta({start:f.start,end:f.end,action:\"remove\",lines:this.getLinesForRange(f)}),l},this.removeNewLine=function(e){e<this.getLength()-1&&e>=0&&this.applyDelta({start:this.pos(e,this.getLine(e).length),end:this.pos(e+1,0),action:\"remove\",lines:[\"\",\"\"]})},this.replace=function(e,t){e instanceof o||(e=o.fromPoints(e.start,e.end));if(t.length===0&&e.isEmpty())return e.start;if(t==this.getTextRange(e))return e.end;this.remove(e);var n;return t?n=this.insert(e.start,t):n=e.start,n},this.applyDeltas=function(e){for(var t=0;t<e.length;t++)this.applyDelta(e[t])},this.revertDeltas=function(e){for(var t=e.length-1;t>=0;t--)this.revertDelta(e[t])},this.applyDelta=function(e,t){var n=e.action==\"insert\";if(n?e.lines.length<=1&&!e.lines[0]:!o.comparePoints(e.start,e.end))return;n&&e.lines.length>2e4&&this.$splitAndapplyLargeDelta(e,2e4),i(this.$lines,e,t),this._signal(\"change\",e)},this.$splitAndapplyLargeDelta=function(e,t){var n=e.lines,r=n.length,i=e.start.row,s=e.start.column,o=0,u=0;do{o=u,u+=t-1;var a=n.slice(o,u);if(u>r){e.lines=a,e.start.row=i+o,e.start.column=s;break}a.push(\"\"),this.applyDelta({start:this.pos(i+o,s),end:this.pos(i+u,s=0),action:e.action,lines:a},!0)}while(!0)},this.revertDelta=function(e){this.applyDelta({start:this.clonePos(e.start),end:this.clonePos(e.end),action:e.action==\"insert\"?\"remove\":\"insert\",lines:e.lines.slice()})},this.indexToPosition=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length;for(var i=t||0,s=n.length;i<s;i++){e-=n[i].length+r;if(e<0)return{row:i,column:e+n[i].length+r}}return{row:s-1,column:n[s-1].length}},this.positionToIndex=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length,i=0,s=Math.min(e.row,n.length);for(var o=t||0;o<s;++o)i+=n[o].length+r;return i+e.column}}).call(a.prototype),t.Document=a}),define(\"ace/lib/lang\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.last=function(e){return e[e.length-1]},t.stringReverse=function(e){return e.split(\"\").reverse().join(\"\")},t.stringRepeat=function(e,t){var n=\"\";while(t>0){t&1&&(n+=e);if(t>>=1)e+=e}return n};var r=/^\\s\\s*/,i=/\\s\\s*$/;t.stringTrimLeft=function(e){return e.replace(r,\"\")},t.stringTrimRight=function(e){return e.replace(i,\"\")},t.copyObject=function(e){var t={};for(var n in e)t[n]=e[n];return t},t.copyArray=function(e){var t=[];for(var n=0,r=e.length;n<r;n++)e[n]&&typeof e[n]==\"object\"?t[n]=this.copyObject(e[n]):t[n]=e[n];return t},t.deepCopy=function s(e){if(typeof e!=\"object\"||!e)return e;var t;if(Array.isArray(e)){t=[];for(var n=0;n<e.length;n++)t[n]=s(e[n]);return t}if(Object.prototype.toString.call(e)!==\"[object Object]\")return e;t={};for(var n in e)t[n]=s(e[n]);return t},t.arrayToMap=function(e){var t={};for(var n=0;n<e.length;n++)t[e[n]]=1;return t},t.createMap=function(e){var t=Object.create(null);for(var n in e)t[n]=e[n];return t},t.arrayRemove=function(e,t){for(var n=0;n<=e.length;n++)t===e[n]&&e.splice(n,1)},t.escapeRegExp=function(e){return e.replace(/([.*+?^${}()|[\\]\\/\\\\])/g,\"\\\\$1\")},t.escapeHTML=function(e){return e.replace(/&/g,\"&#38;\").replace(/\"/g,\"&#34;\").replace(/'/g,\"&#39;\").replace(/</g,\"&#60;\")},t.getMatchOffsets=function(e,t){var n=[];return e.replace(t,function(e){n.push({offset:arguments[arguments.length-2],length:e.length})}),n},t.deferredCall=function(e){var t=null,n=function(){t=null,e()},r=function(e){return r.cancel(),t=setTimeout(n,e||0),r};return r.schedule=r,r.call=function(){return this.cancel(),e(),r},r.cancel=function(){return clearTimeout(t),t=null,r},r.isPending=function(){return t},r},t.delayedCall=function(e,t){var n=null,r=function(){n=null,e()},i=function(e){n==null&&(n=setTimeout(r,e||t))};return i.delay=function(e){n&&clearTimeout(n),n=setTimeout(r,e||t)},i.schedule=i,i.call=function(){this.cancel(),e()},i.cancel=function(){n&&clearTimeout(n),n=null},i.isPending=function(){return n},i}}),define(\"ace/worker/mirror\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/document\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=e(\"../document\").Document,s=e(\"../lib/lang\"),o=t.Mirror=function(e){this.sender=e;var t=this.doc=new i(\"\"),n=this.deferredUpdate=s.delayedCall(this.onUpdate.bind(this)),r=this;e.on(\"change\",function(e){var i=e.data;if(i[0].start)t.applyDeltas(i);else for(var s=0;s<i.length;s+=2){if(Array.isArray(i[s+1]))var o={action:\"insert\",start:i[s],lines:i[s+1]};else var o={action:\"remove\",start:i[s],end:i[s+1]};t.applyDelta(o,!0)}if(r.$timeout)return n.schedule(r.$timeout);r.onUpdate()})};(function(){this.$timeout=500,this.setTimeout=function(e){this.$timeout=e},this.setValue=function(e){this.doc.setValue(e),this.deferredUpdate.schedule(this.$timeout)},this.getValue=function(e){this.sender.callback(this.doc.getValue(),e)},this.onUpdate=function(){},this.isPending=function(){return this.deferredUpdate.isPending()}}).call(o.prototype)}),define(\"ace/mode/php/php\",[\"require\",\"exports\",\"module\"],function(e,t,n){var r={Constants:{}};r.Constants.T_INCLUDE=257,r.Constants.T_INCLUDE_ONCE=258,r.Constants.T_EVAL=259,r.Constants.T_REQUIRE=260,r.Constants.T_REQUIRE_ONCE=261,r.Constants.T_LOGICAL_OR=262,r.Constants.T_LOGICAL_XOR=263,r.Constants.T_LOGICAL_AND=264,r.Constants.T_PRINT=265,r.Constants.T_YIELD=266,r.Constants.T_DOUBLE_ARROW=267,r.Constants.T_YIELD_FROM=268,r.Constants.T_PLUS_EQUAL=269,r.Constants.T_MINUS_EQUAL=270,r.Constants.T_MUL_EQUAL=271,r.Constants.T_DIV_EQUAL=272,r.Constants.T_CONCAT_EQUAL=273,r.Constants.T_MOD_EQUAL=274,r.Constants.T_AND_EQUAL=275,r.Constants.T_OR_EQUAL=276,r.Constants.T_XOR_EQUAL=277,r.Constants.T_SL_EQUAL=278,r.Constants.T_SR_EQUAL=279,r.Constants.T_POW_EQUAL=280,r.Constants.T_COALESCE=281,r.Constants.T_BOOLEAN_OR=282,r.Constants.T_BOOLEAN_AND=283,r.Constants.T_IS_EQUAL=284,r.Constants.T_IS_NOT_EQUAL=285,r.Constants.T_IS_IDENTICAL=286,r.Constants.T_IS_NOT_IDENTICAL=287,r.Constants.T_SPACESHIP=288,r.Constants.T_IS_SMALLER_OR_EQUAL=289,r.Constants.T_IS_GREATER_OR_EQUAL=290,r.Constants.T_SL=291,r.Constants.T_SR=292,r.Constants.T_INSTANCEOF=293,r.Constants.T_INC=294,r.Constants.T_DEC=295,r.Constants.T_INT_CAST=296,r.Constants.T_DOUBLE_CAST=297,r.Constants.T_STRING_CAST=298,r.Constants.T_ARRAY_CAST=299,r.Constants.T_OBJECT_CAST=300,r.Constants.T_BOOL_CAST=301,r.Constants.T_UNSET_CAST=302,r.Constants.T_POW=303,r.Constants.T_NEW=304,r.Constants.T_CLONE=305,r.Constants.T_EXIT=306,r.Constants.T_IF=307,r.Constants.T_ELSEIF=308,r.Constants.T_ELSE=309,r.Constants.T_ENDIF=310,r.Constants.T_LNUMBER=311,r.Constants.T_DNUMBER=312,r.Constants.T_STRING=313,r.Constants.T_STRING_VARNAME=314,r.Constants.T_VARIABLE=315,r.Constants.T_NUM_STRING=316,r.Constants.T_INLINE_HTML=317,r.Constants.T_CHARACTER=318,r.Constants.T_BAD_CHARACTER=319,r.Constants.T_ENCAPSED_AND_WHITESPACE=320,r.Constants.T_CONSTANT_ENCAPSED_STRING=321,r.Constants.T_ECHO=322,r.Constants.T_DO=323,r.Constants.T_WHILE=324,r.Constants.T_ENDWHILE=325,r.Constants.T_FOR=326,r.Constants.T_ENDFOR=327,r.Constants.T_FOREACH=328,r.Constants.T_ENDFOREACH=329,r.Constants.T_DECLARE=330,r.Constants.T_ENDDECLARE=331,r.Constants.T_AS=332,r.Constants.T_SWITCH=333,r.Constants.T_ENDSWITCH=334,r.Constants.T_CASE=335,r.Constants.T_DEFAULT=336,r.Constants.T_BREAK=337,r.Constants.T_CONTINUE=338,r.Constants.T_GOTO=339,r.Constants.T_FUNCTION=340,r.Constants.T_CONST=341,r.Constants.T_RETURN=342,r.Constants.T_TRY=343,r.Constants.T_CATCH=344,r.Constants.T_FINALLY=345,r.Constants.T_THROW=346,r.Constants.T_USE=347,r.Constants.T_INSTEADOF=348,r.Constants.T_GLOBAL=349,r.Constants.T_STATIC=350,r.Constants.T_ABSTRACT=351,r.Constants.T_FINAL=352,r.Constants.T_PRIVATE=353,r.Constants.T_PROTECTED=354,r.Constants.T_PUBLIC=355,r.Constants.T_VAR=356,r.Constants.T_UNSET=357,r.Constants.T_ISSET=358,r.Constants.T_EMPTY=359,r.Constants.T_HALT_COMPILER=360,r.Constants.T_CLASS=361,r.Constants.T_TRAIT=362,r.Constants.T_INTERFACE=363,r.Constants.T_EXTENDS=364,r.Constants.T_IMPLEMENTS=365,r.Constants.T_OBJECT_OPERATOR=366,r.Constants.T_LIST=367,r.Constants.T_ARRAY=368,r.Constants.T_CALLABLE=369,r.Constants.T_CLASS_C=370,r.Constants.T_TRAIT_C=371,r.Constants.T_METHOD_C=372,r.Constants.T_FUNC_C=373,r.Constants.T_LINE=374,r.Constants.T_FILE=375,r.Constants.T_COMMENT=376,r.Constants.T_DOC_COMMENT=377,r.Constants.T_OPEN_TAG=378,r.Constants.T_OPEN_TAG_WITH_ECHO=379,r.Constants.T_CLOSE_TAG=380,r.Constants.T_WHITESPACE=381,r.Constants.T_START_HEREDOC=382,r.Constants.T_END_HEREDOC=383,r.Constants.T_DOLLAR_OPEN_CURLY_BRACES=384,r.Constants.T_CURLY_OPEN=385,r.Constants.T_PAAMAYIM_NEKUDOTAYIM=386,r.Constants.T_NAMESPACE=387,r.Constants.T_NS_C=388,r.Constants.T_DIR=389,r.Constants.T_NS_SEPARATOR=390,r.Constants.T_ELLIPSIS=391,r.Lexer=function(e,t){var n,i,s=[\"INITIAL\"],o=0,u=function(e){s[o]=e},a=function(e){s[++o]=e},f=function(){--o},l=t===undefined||/^(on|true|1)$/i.test(t.short_open_tag),c=l?/^(\\<\\?php(?:\\r\\n|[ \\t\\r\\n])|<\\?|\\<script language\\=('|\")?php('|\")?\\>)/i:/^(\\<\\?php(?:\\r\\n|[ \\t\\r\\n])|\\<script language\\=('|\")?php('|\")?\\>)/i,h=l?/[^<]*(?:<(?!\\?|script language\\=('|\")?php('|\")?\\>)[^<]*)*/i:/[^<]*(?:<(?!\\?=|\\?php[ \\t\\r\\n]|script language\\=('|\")?php('|\")?\\>)[^<]*)*/i;labelRegexPart=\"[a-zA-Z_\\\\x7f-\\\\uffff][a-zA-Z0-9_\\\\x7f-\\\\uffff]*\",stringRegexPart=function(e){return\"[^\"+e+\"\\\\\\\\${]*(?:(?:\\\\\\\\[\\\\s\\\\S]|\\\\$(?!\\\\{|[a-zA-Z_\\\\x7f-\\\\uffff])|\\\\{(?!\\\\$))[^\"+e+\"\\\\\\\\${]*)*\"},sharedStringTokens=[{value:r.Constants.T_VARIABLE,re:new RegExp(\"^\\\\$\"+labelRegexPart+\"(?=\\\\[)\"),func:function(){a(\"VAR_OFFSET\")}},{value:r.Constants.T_VARIABLE,re:new RegExp(\"^\\\\$\"+labelRegexPart+\"(?=->\"+labelRegexPart+\")\"),func:function(){a(\"LOOKING_FOR_PROPERTY\")}},{value:r.Constants.T_DOLLAR_OPEN_CURLY_BRACES,re:new RegExp(\"^\\\\$\\\\{(?=\"+labelRegexPart+\"[\\\\[}])\"),func:function(){a(\"LOOKING_FOR_VARNAME\")}},{value:r.Constants.T_VARIABLE,re:new RegExp(\"^\\\\$\"+labelRegexPart)},{value:r.Constants.T_DOLLAR_OPEN_CURLY_BRACES,re:/^\\$\\{/,func:function(){a(\"IN_SCRIPTING\")}},{value:r.Constants.T_CURLY_OPEN,re:/^\\{(?=\\$)/,func:function(){a(\"IN_SCRIPTING\")}}],data={INITIAL:[{value:r.Constants.T_OPEN_TAG_WITH_ECHO,re:/^<\\?=/i,func:function(){u(\"IN_SCRIPTING\")}},{value:r.Constants.T_OPEN_TAG,re:c,func:function(){u(\"IN_SCRIPTING\")}},{value:r.Constants.T_INLINE_HTML,re:h}],IN_SCRIPTING:[{value:r.Constants.T_WHITESPACE,re:/^[ \\n\\r\\t]+/},{value:r.Constants.T_ABSTRACT,re:/^abstract\\b/i},{value:r.Constants.T_LOGICAL_AND,re:/^and\\b/i},{value:r.Constants.T_ARRAY,re:/^array\\b/i},{value:r.Constants.T_AS,re:/^as\\b/i},{value:r.Constants.T_BREAK,re:/^break\\b/i},{value:r.Constants.T_CALLABLE,re:/^callable\\b/i},{value:r.Constants.T_CASE,re:/^case\\b/i},{value:r.Constants.T_CATCH,re:/^catch\\b/i},{value:r.Constants.T_CLASS,re:/^class\\b/i},{value:r.Constants.T_CLONE,re:/^clone\\b/i},{value:r.Constants.T_CONST,re:/^const\\b/i},{value:r.Constants.T_CONTINUE,re:/^continue\\b/i},{value:r.Constants.T_DECLARE,re:/^declare\\b/i},{value:r.Constants.T_DEFAULT,re:/^default\\b/i},{value:r.Constants.T_DO,re:/^do\\b/i},{value:r.Constants.T_ECHO,re:/^echo\\b/i},{value:r.Constants.T_ELSE,re:/^else\\b/i},{value:r.Constants.T_ELSEIF,re:/^elseif\\b/i},{value:r.Constants.T_ENDDECLARE,re:/^enddeclare\\b/i},{value:r.Constants.T_ENDFOR,re:/^endfor\\b/i},{value:r.Constants.T_ENDFOREACH,re:/^endforeach\\b/i},{value:r.Constants.T_ENDIF,re:/^endif\\b/i},{value:r.Constants.T_ENDSWITCH,re:/^endswitch\\b/i},{value:r.Constants.T_ENDWHILE,re:/^endwhile\\b/i},{value:r.Constants.T_EMPTY,re:/^empty\\b/i},{value:r.Constants.T_EVAL,re:/^eval\\b/i},{value:r.Constants.T_EXIT,re:/^(?:exit|die)\\b/i},{value:r.Constants.T_EXTENDS,re:/^extends\\b/i},{value:r.Constants.T_FINAL,re:/^final\\b/i},{value:r.Constants.T_FINALLY,re:/^finally\\b/i},{value:r.Constants.T_FOR,re:/^for\\b/i},{value:r.Constants.T_FOREACH,re:/^foreach\\b/i},{value:r.Constants.T_FUNCTION,re:/^function\\b/i},{value:r.Constants.T_GLOBAL,re:/^global\\b/i},{value:r.Constants.T_GOTO,re:/^goto\\b/i},{value:r.Constants.T_IF,re:/^if\\b/i},{value:r.Constants.T_IMPLEMENTS,re:/^implements\\b/i},{value:r.Constants.T_INCLUDE,re:/^include\\b/i},{value:r.Constants.T_INCLUDE_ONCE,re:/^include_once\\b/i},{value:r.Constants.T_INSTANCEOF,re:/^instanceof\\b/i},{value:r.Constants.T_INSTEADOF,re:/^insteadof\\b/i},{value:r.Constants.T_INTERFACE,re:/^interface\\b/i},{value:r.Constants.T_ISSET,re:/^isset\\b/i},{value:r.Constants.T_LIST,re:/^list\\b/i},{value:r.Constants.T_NAMESPACE,re:/^namespace\\b/i},{value:r.Constants.T_NEW,re:/^new\\b/i},{value:r.Constants.T_LOGICAL_OR,re:/^or\\b/i},{value:r.Constants.T_PRINT,re:/^print\\b/i},{value:r.Constants.T_PRIVATE,re:/^private\\b/i},{value:r.Constants.T_PROTECTED,re:/^protected\\b/i},{value:r.Constants.T_PUBLIC,re:/^public\\b/i},{value:r.Constants.T_REQUIRE,re:/^require\\b/i},{value:r.Constants.T_REQUIRE_ONCE,re:/^require_once\\b/i},{value:r.Constants.T_STATIC,re:/^static\\b/i},{value:r.Constants.T_SWITCH,re:/^switch\\b/i},{value:r.Constants.T_THROW,re:/^throw\\b/i},{value:r.Constants.T_TRAIT,re:/^trait\\b/i},{value:r.Constants.T_TRY,re:/^try\\b/i},{value:r.Constants.T_UNSET,re:/^unset\\b/i},{value:r.Constants.T_USE,re:/^use\\b/i},{value:r.Constants.T_VAR,re:/^var\\b/i},{value:r.Constants.T_WHILE,re:/^while\\b/i},{value:r.Constants.T_LOGICAL_XOR,re:/^xor\\b/i},{value:r.Constants.T_YIELD_FROM,re:/^yield\\s+from\\b/i},{value:r.Constants.T_YIELD,re:/^yield\\b/i},{value:r.Constants.T_RETURN,re:/^return\\b/i},{value:r.Constants.T_METHOD_C,re:/^__METHOD__\\b/i},{value:r.Constants.T_LINE,re:/^__LINE__\\b/i},{value:r.Constants.T_FILE,re:/^__FILE__\\b/i},{value:r.Constants.T_FUNC_C,re:/^__FUNCTION__\\b/i},{value:r.Constants.T_NS_C,re:/^__NAMESPACE__\\b/i},{value:r.Constants.T_TRAIT_C,re:/^__TRAIT__\\b/i},{value:r.Constants.T_DIR,re:/^__DIR__\\b/i},{value:r.Constants.T_CLASS_C,re:/^__CLASS__\\b/i},{value:r.Constants.T_AND_EQUAL,re:/^&=/},{value:r.Constants.T_ARRAY_CAST,re:/^\\([ \\t]*array[ \\t]*\\)/i},{value:r.Constants.T_BOOL_CAST,re:/^\\([ \\t]*(?:bool|boolean)[ \\t]*\\)/i},{value:r.Constants.T_DOUBLE_CAST,re:/^\\([ \\t]*(?:real|float|double)[ \\t]*\\)/i},{value:r.Constants.T_INT_CAST,re:/^\\([ \\t]*(?:int|integer)[ \\t]*\\)/i},{value:r.Constants.T_OBJECT_CAST,re:/^\\([ \\t]*object[ \\t]*\\)/i},{value:r.Constants.T_STRING_CAST,re:/^\\([ \\t]*(?:binary|string)[ \\t]*\\)/i},{value:r.Constants.T_UNSET_CAST,re:/^\\([ \\t]*unset[ \\t]*\\)/i},{value:r.Constants.T_BOOLEAN_AND,re:/^&&/},{value:r.Constants.T_BOOLEAN_OR,re:/^\\|\\|/},{value:r.Constants.T_CLOSE_TAG,re:/^(?:\\?>|<\\/script>)(\\r\\n|\\r|\\n)?/i,func:function(){u(\"INITIAL\")}},{value:r.Constants.T_DOUBLE_ARROW,re:/^=>/},{value:r.Constants.T_PAAMAYIM_NEKUDOTAYIM,re:/^::/},{value:r.Constants.T_INC,re:/^\\+\\+/},{value:r.Constants.T_DEC,re:/^--/},{value:r.Constants.T_CONCAT_EQUAL,re:/^\\.=/},{value:r.Constants.T_DIV_EQUAL,re:/^\\/=/},{value:r.Constants.T_XOR_EQUAL,re:/^\\^=/},{value:r.Constants.T_MUL_EQUAL,re:/^\\*=/},{value:r.Constants.T_MOD_EQUAL,re:/^%=/},{value:r.Constants.T_SL_EQUAL,re:/^<<=/},{value:r.Constants.T_START_HEREDOC,re:new RegExp(\"^[bB]?<<<[ \\\\t]*'(\"+labelRegexPart+\")'(?:\\\\r\\\\n|\\\\r|\\\\n)\"),func:function(e){n=e[1],u(\"NOWDOC\")}},{value:r.Constants.T_START_HEREDOC,re:new RegExp('^[bB]?<<<[ \\\\t]*(\"?)('+labelRegexPart+\")\\\\1(?:\\\\r\\\\n|\\\\r|\\\\n)\"),func:function(e){n=e[2],i=!0,u(\"HEREDOC\")}},{value:r.Constants.T_SL,re:/^<</},{value:r.Constants.T_SPACESHIP,re:/^<=>/},{value:r.Constants.T_IS_SMALLER_OR_EQUAL,re:/^<=/},{value:r.Constants.T_SR_EQUAL,re:/^>>=/},{value:r.Constants.T_SR,re:/^>>/},{value:r.Constants.T_IS_GREATER_OR_EQUAL,re:/^>=/},{value:r.Constants.T_OR_EQUAL,re:/^\\|=/},{value:r.Constants.T_PLUS_EQUAL,re:/^\\+=/},{value:r.Constants.T_MINUS_EQUAL,re:/^-=/},{value:r.Constants.T_OBJECT_OPERATOR,re:new RegExp(\"^->(?=[ \\n\\r\t]*\"+labelRegexPart+\")\"),func:function(){a(\"LOOKING_FOR_PROPERTY\")}},{value:r.Constants.T_OBJECT_OPERATOR,re:/^->/i},{value:r.Constants.T_ELLIPSIS,re:/^\\.\\.\\./},{value:r.Constants.T_POW_EQUAL,re:/^\\*\\*=/},{value:r.Constants.T_POW,re:/^\\*\\*/},{value:r.Constants.T_COALESCE,re:/^\\?\\?/},{value:r.Constants.T_COMMENT,re:/^\\/\\*([\\S\\s]*?)(?:\\*\\/|$)/},{value:r.Constants.T_COMMENT,re:/^(?:\\/\\/|#)[^\\r\\n?]*(?:\\?(?!>)[^\\r\\n?]*)*(?:\\r\\n|\\r|\\n)?/},{value:r.Constants.T_IS_IDENTICAL,re:/^===/},{value:r.Constants.T_IS_EQUAL,re:/^==/},{value:r.Constants.T_IS_NOT_IDENTICAL,re:/^!==/},{value:r.Constants.T_IS_NOT_EQUAL,re:/^(!=|<>)/},{value:r.Constants.T_DNUMBER,re:/^(?:[0-9]+\\.[0-9]*|\\.[0-9]+)(?:[eE][+-]?[0-9]+)?/},{value:r.Constants.T_DNUMBER,re:/^[0-9]+[eE][+-]?[0-9]+/},{value:r.Constants.T_LNUMBER,re:/^(?:0x[0-9A-F]+|0b[01]+|[0-9]+)/i},{value:r.Constants.T_VARIABLE,re:new RegExp(\"^\\\\$\"+labelRegexPart)},{value:r.Constants.T_CONSTANT_ENCAPSED_STRING,re:/^[bB]?'[^'\\\\]*(?:\\\\[\\s\\S][^'\\\\]*)*'/},{value:r.Constants.T_CONSTANT_ENCAPSED_STRING,re:new RegExp('^[bB]?\"'+stringRegexPart('\"')+'\"')},{value:-1,re:/^[bB]?\"/,func:function(){u(\"DOUBLE_QUOTES\")}},{value:-1,re:/^`/,func:function(){u(\"BACKTICKS\")}},{value:r.Constants.T_NS_SEPARATOR,re:/^\\\\/},{value:r.Constants.T_STRING,re:/^[a-zA-Z_\\x7f-\\uffff][a-zA-Z0-9_\\x7f-\\uffff]*/},{value:-1,re:/^\\{/,func:function(){a(\"IN_SCRIPTING\")}},{value:-1,re:/^\\}/,func:function(){o>0&&f()}},{value:-1,re:/^[\\[\\];:?()!.,><=+-/*|&@^%\"'$~]/}],DOUBLE_QUOTES:sharedStringTokens.concat([{value:-1,re:/^\"/,func:function(){u(\"IN_SCRIPTING\")}},{value:r.Constants.T_ENCAPSED_AND_WHITESPACE,re:new RegExp(\"^\"+stringRegexPart('\"'))}]),BACKTICKS:sharedStringTokens.concat([{value:-1,re:/^`/,func:function(){u(\"IN_SCRIPTING\")}},{value:r.Constants.T_ENCAPSED_AND_WHITESPACE,re:new RegExp(\"^\"+stringRegexPart(\"`\"))}]),VAR_OFFSET:[{value:-1,re:/^\\]/,func:function(){f()}},{value:r.Constants.T_NUM_STRING,re:/^(?:0x[0-9A-F]+|0b[01]+|[0-9]+)/i},{value:r.Constants.T_VARIABLE,re:new RegExp(\"^\\\\$\"+labelRegexPart)},{value:r.Constants.T_STRING,re:new RegExp(\"^\"+labelRegexPart)},{value:-1,re:/^[;:,.\\[()|^&+-/*=%!~$<>?@{}\"`]/}],LOOKING_FOR_PROPERTY:[{value:r.Constants.T_OBJECT_OPERATOR,re:/^->/},{value:r.Constants.T_STRING,re:new RegExp(\"^\"+labelRegexPart),func:function(){f()}},{value:r.Constants.T_WHITESPACE,re:/^[ \\n\\r\\t]+/}],LOOKING_FOR_VARNAME:[{value:r.Constants.T_STRING_VARNAME,re:new RegExp(\"^\"+labelRegexPart+\"(?=[\\\\[}])\"),func:function(){u(\"IN_SCRIPTING\")}}],NOWDOC:[{value:r.Constants.T_END_HEREDOC,matchFunc:function(e){var t=new RegExp(\"^\"+n+\"(?=;?[\\\\r\\\\n])\");return e.match(t)?[e.substr(0,n.length)]:null},func:function(){u(\"IN_SCRIPTING\")}},{value:r.Constants.T_ENCAPSED_AND_WHITESPACE,matchFunc:function(e){var t=new RegExp(\"[\\\\r\\\\n]\"+n+\"(?=;?[\\\\r\\\\n])\"),r=t.exec(e),i=r?r.index+1:e.length;return[e.substring(0,i)]}}],HEREDOC:sharedStringTokens.concat([{value:r.Constants.T_END_HEREDOC,matchFunc:function(e){if(!i)return null;var t=new RegExp(\"^\"+n+\"(?=;?[\\\\r\\\\n])\");return e.match(t)?[e.substr(0,n.length)]:null},func:function(){u(\"IN_SCRIPTING\")}},{value:r.Constants.T_ENCAPSED_AND_WHITESPACE,matchFunc:function(e){var t=e.length,r=new RegExp(\"^\"+stringRegexPart(\"\")),s=r.exec(e);return s&&(t=s[0].length),r=new RegExp(\"([\\\\r\\\\n])\"+n+\"(?=;?[\\\\r\\\\n])\"),s=r.exec(e.substring(0,t)),s?(t=s.index+1,i=!0):i=!1,t==0?null:[e.substring(0,t)]}}])};var p=[],d=1,v=!0;if(e===null)return p;typeof e!=\"string\"&&(e=e.toString());while(e.length>0&&v===!0){var m=s[o],g=data[m];v=g.some(function(t){var n=t.matchFunc!==undefined?t.matchFunc(e):e.match(t.re);if(n!==null){if(n[0].length==0)throw new Error(\"empty match\");t.func!==undefined&&t.func(n);if(t.value===-1)p.push(n[0]);else{var r=n[0];p.push([parseInt(t.value,10),r,d]),d+=r.split(\"\\n\").length-1}return e=e.substring(n[0].length),!0}return!1})}return p},r.Parser=function(e,t){var n=this.yybase,i=this.yydefault,s=this.yycheck,o=this.yyaction,u=this.yylen,a=this.yygbase,f=this.yygcheck,l=this.yyp,c=this.yygoto,h=this.yylhs,p=this.terminals,d=this.translate,v=this.yygdefault;this.pos=-1,this.line=1,this.tokenMap=this.createTokenMap(),this.dropTokens={},this.dropTokens[r.Constants.T_WHITESPACE]=1,this.dropTokens[r.Constants.T_OPEN_TAG]=1;var m=[];e.forEach(function(e,t){typeof e==\"object\"&&e[0]===r.Constants.T_OPEN_TAG_WITH_ECHO?(m.push([r.Constants.T_OPEN_TAG,e[1],e[2]]),m.push([r.Constants.T_ECHO,e[1],e[2]])):m.push(e)}),this.tokens=m;var g=this.TOKEN_NONE;this.startAttributes={startLine:1},this.endAttributes={};var y=[this.startAttributes],b=0,w=[b];this.yyastk=[],this.stackPos=0;var E,S;for(;;){if(n[b]===0)E=i[b];else{g===this.TOKEN_NONE&&(S=this.getNextToken(),g=S>=0&&S<this.TOKEN_MAP_SIZE?d[S]:this.TOKEN_INVALID,y[this.stackPos]=this.startAttributes);if(((E=n[b]+g)>=0&&E<this.YYLAST&&s[E]===g||b<this.YY2TBLSTATE&&(E=n[b+this.YYNLSTATES]+g)>=0&&E<this.YYLAST&&s[E]===g)&&(E=o[E])!==this.YYDEFAULT)if(E>0){++this.stackPos,w[this.stackPos]=b=E,this.yyastk[this.stackPos]=this.tokenValue,y[this.stackPos]=this.startAttributes,g=this.TOKEN_NONE;if(E<this.YYNLSTATES)continue;E-=this.YYNLSTATES}else E=-E;else E=i[b]}for(;;){if(E===0)return this.yyval;if(E===this.YYUNEXPECTED){if(t!==!0){var T=[];for(var N=0;N<this.TOKEN_MAP_SIZE;++N)if((E=n[b]+N)>=0&&E<this.YYLAST&&s[E]==N||b<this.YY2TBLSTATE&&(E=n[b+this.YYNLSTATES]+N)&&E<this.YYLAST&&s[E]==N)if(o[E]!=this.YYUNEXPECTED){if(T.length==4){T=[];break}T.push(this.terminals[N])}var C=\"\";throw T.length&&(C=\", expecting \"+T.join(\" or \")),new r.ParseError(\"syntax error, unexpected \"+p[g]+C,this.startAttributes.startLine)}return this.startAttributes.startLine}for(var x in this.endAttributes)y[this.stackPos-u[E]][x]=this.endAttributes[x];this.stackPos-=u[E],E=h[E],(l=a[E]+w[this.stackPos])>=0&&l<this.YYGLAST&&f[l]===E?b=c[l]:b=v[E],++this.stackPos,w[this.stackPos]=b,this.yyastk[this.stackPos]=this.yyval,y[this.stackPos]=this.startAttributes;if(b<this.YYNLSTATES)break;E=b-this.YYNLSTATES}}},r.ParseError=function(e,t){this.message=e,this.line=t},r.Parser.prototype.getNextToken=function(){this.startAttributes={},this.endAttributes={};var e,t;while(this.tokens[++this.pos]!==undefined){e=this.tokens[this.pos];if(typeof e==\"string\")return this.startAttributes.startLine=this.line,this.endAttributes.endLine=this.line,'b\"'===e?(this.tokenValue='b\"','\"'.charCodeAt(0)):(this.tokenValue=e,e.charCodeAt(0));this.line+=(t=e[1].match(/\\n/g))===null?0:t.length;if(r.Constants.T_COMMENT===e[0])Array.isArray(this.startAttributes.comments)||(this.startAttributes.comments=[]),this.startAttributes.comments.push({type:\"comment\",comment:e[1],line:e[2]});else if(r.Constants.T_DOC_COMMENT===e[0])this.startAttributes.comments.push(new PHPParser_Comment_Doc(e[1],e[2]));else if(this.dropTokens[e[0]]===undefined)return this.tokenValue=e[1],this.startAttributes.startLine=e[2],this.endAttributes.endLine=this.line,this.tokenMap[e[0]]}return this.startAttributes.startLine=this.line,0},r.Parser.prototype.tokenName=function(e){var t=[\"T_INCLUDE\",\"T_INCLUDE_ONCE\",\"T_EVAL\",\"T_REQUIRE\",\"T_REQUIRE_ONCE\",\"T_LOGICAL_OR\",\"T_LOGICAL_XOR\",\"T_LOGICAL_AND\",\"T_PRINT\",\"T_YIELD\",\"T_DOUBLE_ARROW\",\"T_YIELD_FROM\",\"T_PLUS_EQUAL\",\"T_MINUS_EQUAL\",\"T_MUL_EQUAL\",\"T_DIV_EQUAL\",\"T_CONCAT_EQUAL\",\"T_MOD_EQUAL\",\"T_AND_EQUAL\",\"T_OR_EQUAL\",\"T_XOR_EQUAL\",\"T_SL_EQUAL\",\"T_SR_EQUAL\",\"T_POW_EQUAL\",\"T_COALESCE\",\"T_BOOLEAN_OR\",\"T_BOOLEAN_AND\",\"T_IS_EQUAL\",\"T_IS_NOT_EQUAL\",\"T_IS_IDENTICAL\",\"T_IS_NOT_IDENTICAL\",\"T_SPACESHIP\",\"T_IS_SMALLER_OR_EQUAL\",\"T_IS_GREATER_OR_EQUAL\",\"T_SL\",\"T_SR\",\"T_INSTANCEOF\",\"T_INC\",\"T_DEC\",\"T_INT_CAST\",\"T_DOUBLE_CAST\",\"T_STRING_CAST\",\"T_ARRAY_CAST\",\"T_OBJECT_CAST\",\"T_BOOL_CAST\",\"T_UNSET_CAST\",\"T_POW\",\"T_NEW\",\"T_CLONE\",\"T_EXIT\",\"T_IF\",\"T_ELSEIF\",\"T_ELSE\",\"T_ENDIF\",\"T_LNUMBER\",\"T_DNUMBER\",\"T_STRING\",\"T_STRING_VARNAME\",\"T_VARIABLE\",\"T_NUM_STRING\",\"T_INLINE_HTML\",\"T_CHARACTER\",\"T_BAD_CHARACTER\",\"T_ENCAPSED_AND_WHITESPACE\",\"T_CONSTANT_ENCAPSED_STRING\",\"T_ECHO\",\"T_DO\",\"T_WHILE\",\"T_ENDWHILE\",\"T_FOR\",\"T_ENDFOR\",\"T_FOREACH\",\"T_ENDFOREACH\",\"T_DECLARE\",\"T_ENDDECLARE\",\"T_AS\",\"T_SWITCH\",\"T_ENDSWITCH\",\"T_CASE\",\"T_DEFAULT\",\"T_BREAK\",\"T_CONTINUE\",\"T_GOTO\",\"T_FUNCTION\",\"T_CONST\",\"T_RETURN\",\"T_TRY\",\"T_CATCH\",\"T_FINALLY\",\"T_THROW\",\"T_USE\",\"T_INSTEADOF\",\"T_GLOBAL\",\"T_STATIC\",\"T_ABSTRACT\",\"T_FINAL\",\"T_PRIVATE\",\"T_PROTECTED\",\"T_PUBLIC\",\"T_VAR\",\"T_UNSET\",\"T_ISSET\",\"T_EMPTY\",\"T_HALT_COMPILER\",\"T_CLASS\",\"T_TRAIT\",\"T_INTERFACE\",\"T_EXTENDS\",\"T_IMPLEMENTS\",\"T_OBJECT_OPERATOR\",\"T_DOUBLE_ARROW\",\"T_LIST\",\"T_ARRAY\",\"T_CALLABLE\",\"T_CLASS_C\",\"T_TRAIT_C\",\"T_METHOD_C\",\"T_FUNC_C\",\"T_LINE\",\"T_FILE\",\"T_COMMENT\",\"T_DOC_COMMENT\",\"T_OPEN_TAG\",\"T_OPEN_TAG_WITH_ECHO\",\"T_CLOSE_TAG\",\"T_WHITESPACE\",\"T_START_HEREDOC\",\"T_END_HEREDOC\",\"T_DOLLAR_OPEN_CURLY_BRACES\",\"T_CURLY_OPEN\",\"T_PAAMAYIM_NEKUDOTAYIM\",\"T_NAMESPACE\",\"T_NS_C\",\"T_DIR\",\"T_NS_SEPARATOR\",\"T_ELLIPSIS\"],n=\"UNKNOWN\";return t.some(function(t){return r.Constants[t]===e?(n=t,!0):!1}),n},r.Parser.prototype.createTokenMap=function(){var e={},t,n;for(n=256;n<1e3;++n)r.Constants.T_OPEN_TAG_WITH_ECHO===n?e[n]=r.Constants.T_ECHO:r.Constants.T_CLOSE_TAG===n?e[n]=59:\"UNKNOWN\"!==(t=this.tokenName(n))&&(e[n]=this[t]);return e},r.Parser.prototype.TOKEN_NONE=-1,r.Parser.prototype.TOKEN_INVALID=157,r.Parser.prototype.TOKEN_MAP_SIZE=392,r.Parser.prototype.YYLAST=889,r.Parser.prototype.YY2TBLSTATE=337,r.Parser.prototype.YYGLAST=410,r.Parser.prototype.YYNLSTATES=564,r.Parser.prototype.YYUNEXPECTED=32767,r.Parser.prototype.YYDEFAULT=-32766,r.Parser.prototype.YYERRTOK=256,r.Parser.prototype.T_INCLUDE=257,r.Parser.prototype.T_INCLUDE_ONCE=258,r.Parser.prototype.T_EVAL=259,r.Parser.prototype.T_REQUIRE=260,r.Parser.prototype.T_REQUIRE_ONCE=261,r.Parser.prototype.T_LOGICAL_OR=262,r.Parser.prototype.T_LOGICAL_XOR=263,r.Parser.prototype.T_LOGICAL_AND=264,r.Parser.prototype.T_PRINT=265,r.Parser.prototype.T_YIELD=266,r.Parser.prototype.T_DOUBLE_ARROW=267,r.Parser.prototype.T_YIELD_FROM=268,r.Parser.prototype.T_PLUS_EQUAL=269,r.Parser.prototype.T_MINUS_EQUAL=270,r.Parser.prototype.T_MUL_EQUAL=271,r.Parser.prototype.T_DIV_EQUAL=272,r.Parser.prototype.T_CONCAT_EQUAL=273,r.Parser.prototype.T_MOD_EQUAL=274,r.Parser.prototype.T_AND_EQUAL=275,r.Parser.prototype.T_OR_EQUAL=276,r.Parser.prototype.T_XOR_EQUAL=277,r.Parser.prototype.T_SL_EQUAL=278,r.Parser.prototype.T_SR_EQUAL=279,r.Parser.prototype.T_POW_EQUAL=280,r.Parser.prototype.T_COALESCE=281,r.Parser.prototype.T_BOOLEAN_OR=282,r.Parser.prototype.T_BOOLEAN_AND=283,r.Parser.prototype.T_IS_EQUAL=284,r.Parser.prototype.T_IS_NOT_EQUAL=285,r.Parser.prototype.T_IS_IDENTICAL=286,r.Parser.prototype.T_IS_NOT_IDENTICAL=287,r.Parser.prototype.T_SPACESHIP=288,r.Parser.prototype.T_IS_SMALLER_OR_EQUAL=289,r.Parser.prototype.T_IS_GREATER_OR_EQUAL=290,r.Parser.prototype.T_SL=291,r.Parser.prototype.T_SR=292,r.Parser.prototype.T_INSTANCEOF=293,r.Parser.prototype.T_INC=294,r.Parser.prototype.T_DEC=295,r.Parser.prototype.T_INT_CAST=296,r.Parser.prototype.T_DOUBLE_CAST=297,r.Parser.prototype.T_STRING_CAST=298,r.Parser.prototype.T_ARRAY_CAST=299,r.Parser.prototype.T_OBJECT_CAST=300,r.Parser.prototype.T_BOOL_CAST=301,r.Parser.prototype.T_UNSET_CAST=302,r.Parser.prototype.T_POW=303,r.Parser.prototype.T_NEW=304,r.Parser.prototype.T_CLONE=305,r.Parser.prototype.T_EXIT=306,r.Parser.prototype.T_IF=307,r.Parser.prototype.T_ELSEIF=308,r.Parser.prototype.T_ELSE=309,r.Parser.prototype.T_ENDIF=310,r.Parser.prototype.T_LNUMBER=311,r.Parser.prototype.T_DNUMBER=312,r.Parser.prototype.T_STRING=313,r.Parser.prototype.T_STRING_VARNAME=314,r.Parser.prototype.T_VARIABLE=315,r.Parser.prototype.T_NUM_STRING=316,r.Parser.prototype.T_INLINE_HTML=317,r.Parser.prototype.T_CHARACTER=318,r.Parser.prototype.T_BAD_CHARACTER=319,r.Parser.prototype.T_ENCAPSED_AND_WHITESPACE=320,r.Parser.prototype.T_CONSTANT_ENCAPSED_STRING=321,r.Parser.prototype.T_ECHO=322,r.Parser.prototype.T_DO=323,r.Parser.prototype.T_WHILE=324,r.Parser.prototype.T_ENDWHILE=325,r.Parser.prototype.T_FOR=326,r.Parser.prototype.T_ENDFOR=327,r.Parser.prototype.T_FOREACH=328,r.Parser.prototype.T_ENDFOREACH=329,r.Parser.prototype.T_DECLARE=330,r.Parser.prototype.T_ENDDECLARE=331,r.Parser.prototype.T_AS=332,r.Parser.prototype.T_SWITCH=333,r.Parser.prototype.T_ENDSWITCH=334,r.Parser.prototype.T_CASE=335,r.Parser.prototype.T_DEFAULT=336,r.Parser.prototype.T_BREAK=337,r.Parser.prototype.T_CONTINUE=338,r.Parser.prototype.T_GOTO=339,r.Parser.prototype.T_FUNCTION=340,r.Parser.prototype.T_CONST=341,r.Parser.prototype.T_RETURN=342,r.Parser.prototype.T_TRY=343,r.Parser.prototype.T_CATCH=344,r.Parser.prototype.T_FINALLY=345,r.Parser.prototype.T_THROW=346,r.Parser.prototype.T_USE=347,r.Parser.prototype.T_INSTEADOF=348,r.Parser.prototype.T_GLOBAL=349,r.Parser.prototype.T_STATIC=350,r.Parser.prototype.T_ABSTRACT=351,r.Parser.prototype.T_FINAL=352,r.Parser.prototype.T_PRIVATE=353,r.Parser.prototype.T_PROTECTED=354,r.Parser.prototype.T_PUBLIC=355,r.Parser.prototype.T_VAR=356,r.Parser.prototype.T_UNSET=357,r.Parser.prototype.T_ISSET=358,r.Parser.prototype.T_EMPTY=359,r.Parser.prototype.T_HALT_COMPILER=360,r.Parser.prototype.T_CLASS=361,r.Parser.prototype.T_TRAIT=362,r.Parser.prototype.T_INTERFACE=363,r.Parser.prototype.T_EXTENDS=364,r.Parser.prototype.T_IMPLEMENTS=365,r.Parser.prototype.T_OBJECT_OPERATOR=366,r.Parser.prototype.T_LIST=367,r.Parser.prototype.T_ARRAY=368,r.Parser.prototype.T_CALLABLE=369,r.Parser.prototype.T_CLASS_C=370,r.Parser.prototype.T_TRAIT_C=371,r.Parser.prototype.T_METHOD_C=372,r.Parser.prototype.T_FUNC_C=373,r.Parser.prototype.T_LINE=374,r.Parser.prototype.T_FILE=375,r.Parser.prototype.T_COMMENT=376,r.Parser.prototype.T_DOC_COMMENT=377,r.Parser.prototype.T_OPEN_TAG=378,r.Parser.prototype.T_OPEN_TAG_WITH_ECHO=379,r.Parser.prototype.T_CLOSE_TAG=380,r.Parser.prototype.T_WHITESPACE=381,r.Parser.prototype.T_START_HEREDOC=382,r.Parser.prototype.T_END_HEREDOC=383,r.Parser.prototype.T_DOLLAR_OPEN_CURLY_BRACES=384,r.Parser.prototype.T_CURLY_OPEN=385,r.Parser.prototype.T_PAAMAYIM_NEKUDOTAYIM=386,r.Parser.prototype.T_NAMESPACE=387,r.Parser.prototype.T_NS_C=388,r.Parser.prototype.T_DIR=389,r.Parser.prototype.T_NS_SEPARATOR=390,r.Parser.prototype.T_ELLIPSIS=391,r.Parser.prototype.terminals=[\"$EOF\",\"error\",\"T_INCLUDE\",\"T_INCLUDE_ONCE\",\"T_EVAL\",\"T_REQUIRE\",\"T_REQUIRE_ONCE\",\"','\",\"T_LOGICAL_OR\",\"T_LOGICAL_XOR\",\"T_LOGICAL_AND\",\"T_PRINT\",\"T_YIELD\",\"T_DOUBLE_ARROW\",\"T_YIELD_FROM\",\"'='\",\"T_PLUS_EQUAL\",\"T_MINUS_EQUAL\",\"T_MUL_EQUAL\",\"T_DIV_EQUAL\",\"T_CONCAT_EQUAL\",\"T_MOD_EQUAL\",\"T_AND_EQUAL\",\"T_OR_EQUAL\",\"T_XOR_EQUAL\",\"T_SL_EQUAL\",\"T_SR_EQUAL\",\"T_POW_EQUAL\",\"'?'\",\"':'\",\"T_COALESCE\",\"T_BOOLEAN_OR\",\"T_BOOLEAN_AND\",\"'|'\",\"'^'\",\"'&'\",\"T_IS_EQUAL\",\"T_IS_NOT_EQUAL\",\"T_IS_IDENTICAL\",\"T_IS_NOT_IDENTICAL\",\"T_SPACESHIP\",\"'<'\",\"T_IS_SMALLER_OR_EQUAL\",\"'>'\",\"T_IS_GREATER_OR_EQUAL\",\"T_SL\",\"T_SR\",\"'+'\",\"'-'\",\"'.'\",\"'*'\",\"'/'\",\"'%'\",\"'!'\",\"T_INSTANCEOF\",\"'~'\",\"T_INC\",\"T_DEC\",\"T_INT_CAST\",\"T_DOUBLE_CAST\",\"T_STRING_CAST\",\"T_ARRAY_CAST\",\"T_OBJECT_CAST\",\"T_BOOL_CAST\",\"T_UNSET_CAST\",\"'@'\",\"T_POW\",\"'['\",\"T_NEW\",\"T_CLONE\",\"T_EXIT\",\"T_IF\",\"T_ELSEIF\",\"T_ELSE\",\"T_ENDIF\",\"T_LNUMBER\",\"T_DNUMBER\",\"T_STRING\",\"T_STRING_VARNAME\",\"T_VARIABLE\",\"T_NUM_STRING\",\"T_INLINE_HTML\",\"T_ENCAPSED_AND_WHITESPACE\",\"T_CONSTANT_ENCAPSED_STRING\",\"T_ECHO\",\"T_DO\",\"T_WHILE\",\"T_ENDWHILE\",\"T_FOR\",\"T_ENDFOR\",\"T_FOREACH\",\"T_ENDFOREACH\",\"T_DECLARE\",\"T_ENDDECLARE\",\"T_AS\",\"T_SWITCH\",\"T_ENDSWITCH\",\"T_CASE\",\"T_DEFAULT\",\"T_BREAK\",\"T_CONTINUE\",\"T_GOTO\",\"T_FUNCTION\",\"T_CONST\",\"T_RETURN\",\"T_TRY\",\"T_CATCH\",\"T_FINALLY\",\"T_THROW\",\"T_USE\",\"T_INSTEADOF\",\"T_GLOBAL\",\"T_STATIC\",\"T_ABSTRACT\",\"T_FINAL\",\"T_PRIVATE\",\"T_PROTECTED\",\"T_PUBLIC\",\"T_VAR\",\"T_UNSET\",\"T_ISSET\",\"T_EMPTY\",\"T_HALT_COMPILER\",\"T_CLASS\",\"T_TRAIT\",\"T_INTERFACE\",\"T_EXTENDS\",\"T_IMPLEMENTS\",\"T_OBJECT_OPERATOR\",\"T_LIST\",\"T_ARRAY\",\"T_CALLABLE\",\"T_CLASS_C\",\"T_TRAIT_C\",\"T_METHOD_C\",\"T_FUNC_C\",\"T_LINE\",\"T_FILE\",\"T_START_HEREDOC\",\"T_END_HEREDOC\",\"T_DOLLAR_OPEN_CURLY_BRACES\",\"T_CURLY_OPEN\",\"T_PAAMAYIM_NEKUDOTAYIM\",\"T_NAMESPACE\",\"T_NS_C\",\"T_DIR\",\"T_NS_SEPARATOR\",\"T_ELLIPSIS\",\"';'\",\"'{'\",\"'}'\",\"'('\",\"')'\",\"'`'\",\"']'\",\"'\\\"'\",\"'$'\",\"???\"],r.Parser.prototype.translate=[0,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,53,155,157,156,52,35,157,151,152,50,47,7,48,49,51,157,157,157,157,157,157,157,157,157,157,29,148,41,15,43,28,65,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,67,157,154,34,157,153,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,149,33,150,55,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,1,2,3,4,5,6,8,9,10,11,12,13,14,16,17,18,19,20,21,22,23,24,25,26,27,30,31,32,36,37,38,39,40,42,44,45,46,54,56,57,58,59,60,61,62,63,64,66,68,69,70,71,72,73,74,75,76,77,78,79,80,81,157,157,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,157,157,157,157,157,157,138,139,140,141,142,143,144,145,146,147],r.Parser.prototype.yyaction=[569,570,571,572,573,215,574,575,576,612,613,0,27,99,100,101,102,103,104,105,106,107,108,109,110,-32766,-32766,-32766,95,96,97,24,240,226,-267,-32766,-32766,-32766,-32766,-32766,-32766,530,344,114,98,-32766,286,-32766,-32766,-32766,-32766,-32766,577,870,872,-32766,-32766,-32766,-32766,-32766,-32766,-32766,-32766,224,-32766,714,578,579,580,581,582,583,584,-32766,264,644,840,841,842,839,838,837,585,586,587,588,589,590,591,592,593,594,595,615,616,617,618,619,607,608,609,610,611,596,597,598,599,600,601,602,638,639,640,641,642,643,603,604,605,606,636,627,625,626,622,623,116,614,620,621,628,629,631,630,632,633,42,43,381,44,45,624,635,634,-214,46,47,289,48,-32767,-32767,-32767,-32767,90,91,92,93,94,267,241,22,840,841,842,839,838,837,832,-32766,-32766,-32766,306,1e3,1e3,1037,120,966,436,-423,244,797,49,50,660,661,272,362,51,-32766,52,219,220,53,54,55,56,57,58,59,60,1016,22,238,61,351,945,-32766,-32766,-32766,967,968,646,705,1e3,28,-456,125,966,-32766,-32766,-32766,715,398,399,216,1e3,-32766,339,-32766,-32766,-32766,-32766,25,222,980,552,355,378,-32766,-423,-32766,-32766,-32766,121,65,1045,408,1047,1046,274,274,131,244,-423,394,395,358,519,945,537,-423,111,-426,398,399,130,972,973,974,975,969,970,243,128,-422,-421,1013,409,976,971,353,791,792,7,-162,63,124,255,701,256,274,382,-122,-122,-122,-4,715,383,646,1042,-421,704,274,-219,33,17,384,-122,385,-122,386,-122,387,-122,369,388,-122,-122,-122,34,35,389,352,520,36,390,353,702,62,112,818,287,288,391,392,-422,-421,-161,350,393,40,38,690,735,396,397,361,22,122,-422,-421,-32766,-32766,-32766,791,792,-422,-421,-425,1e3,-456,-421,-238,966,409,41,382,353,717,535,-122,-32766,383,-32766,-32766,-421,704,21,813,33,17,384,-421,385,-466,386,224,387,-467,273,388,367,945,-458,34,35,389,352,345,36,390,248,247,62,254,715,287,288,391,392,399,-32766,-32766,-32766,393,295,1e3,652,735,396,397,117,115,113,814,119,72,73,74,-162,764,65,240,541,370,518,274,118,270,92,93,94,242,717,535,-4,26,1e3,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,547,240,713,715,382,276,-32766,-32766,126,945,383,-161,938,98,704,225,659,33,17,384,346,385,274,386,728,387,221,120,388,505,506,540,34,35,389,715,-238,36,390,1017,223,62,494,18,287,288,127,297,376,6,98,798,393,274,660,661,490,491,-466,39,-466,514,-467,539,-467,16,458,-458,315,791,792,829,553,382,817,563,653,538,765,383,449,751,535,704,448,435,33,17,384,430,385,646,386,359,387,357,647,388,673,429,1040,34,35,389,715,382,36,390,941,492,62,383,503,287,288,704,434,440,33,17,384,393,385,-32766,386,445,387,495,509,388,10,529,542,34,35,389,715,515,36,390,499,500,62,214,-80,287,288,452,269,736,717,535,488,393,356,266,979,265,730,982,722,358,338,493,548,0,294,737,0,3,0,309,0,0,382,0,0,271,0,0,383,0,717,535,704,227,0,33,17,384,9,385,0,386,0,387,-382,0,388,0,0,325,34,35,389,715,382,36,390,321,341,62,383,340,287,288,704,22,320,33,17,384,393,385,442,386,337,387,562,1e3,388,32,31,966,34,35,389,823,657,36,390,656,821,62,703,711,287,288,561,822,825,717,535,695,393,747,749,693,759,758,752,767,945,824,706,700,712,699,698,658,0,263,262,559,558,382,556,554,551,398,399,383,550,717,535,704,546,545,33,17,384,543,385,536,386,71,387,933,932,388,30,65,731,34,35,389,274,724,36,390,830,734,62,663,662,287,288,-32766,-32766,-32766,733,732,934,393,665,664,756,555,691,1041,1001,994,1006,1011,1014,757,1043,-32766,654,-32766,-32766,-32766,-32766,-32766,-32766,-32767,-32767,-32767,-32767,-32767,655,1044,717,535,-446,926,348,343,268,237,236,235,234,218,217,132,129,-426,-425,-424,123,20,23,70,69,29,37,64,68,66,67,-448,0,15,19,250,910,296,-217,467,484,909,472,528,913,11,964,955,-215,525,379,375,373,371,14,13,12,-214,0,-393,0,1005,1039,992,993,963,0,981],r.Parser.prototype.yycheck=[2,3,4,5,6,13,8,9,10,11,12,0,15,16,17,18,19,20,21,22,23,24,25,26,27,8,9,10,50,51,52,7,54,7,79,8,9,10,8,9,10,77,7,13,66,28,7,30,31,32,33,34,54,56,57,28,8,30,31,32,33,34,35,35,109,1,68,69,70,71,72,73,74,118,7,77,112,113,114,115,116,117,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,7,129,130,131,132,133,134,135,136,137,2,3,4,5,6,143,144,145,152,11,12,7,14,41,42,43,44,45,46,47,48,49,109,7,67,112,113,114,115,116,117,118,8,9,10,79,79,79,82,147,83,82,67,28,152,47,48,102,103,7,7,53,28,55,56,57,58,59,60,61,62,63,64,65,1,67,68,69,70,112,8,9,10,75,76,77,148,79,13,7,67,83,8,9,10,1,129,130,13,79,28,146,30,31,32,33,140,141,139,29,102,7,28,128,30,31,32,149,151,77,112,79,80,156,156,15,28,142,120,121,146,77,112,149,149,15,151,129,130,15,132,133,134,135,136,137,138,15,67,67,77,143,144,145,146,130,131,7,7,151,15,153,148,155,156,71,72,73,74,0,1,77,77,150,67,81,156,152,84,85,86,87,88,89,90,91,92,93,29,95,96,97,98,99,100,101,102,143,104,105,146,148,108,15,150,111,112,113,114,128,128,7,7,119,67,67,122,123,124,125,7,67,149,142,142,8,9,10,130,131,149,149,151,79,152,128,7,83,143,7,71,146,148,149,150,28,77,30,31,142,81,7,148,84,85,86,149,88,7,90,35,92,7,33,95,7,112,7,99,100,101,102,103,104,105,128,128,108,109,1,111,112,113,114,130,8,9,10,119,142,79,122,123,124,125,15,149,149,148,29,8,9,10,152,29,151,54,29,149,79,156,15,143,47,48,49,29,148,149,150,28,79,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,29,54,29,1,71,67,8,9,29,112,77,152,152,66,81,35,148,84,85,86,123,88,156,90,35,92,35,147,95,72,73,29,99,100,101,1,152,104,105,152,35,108,72,73,111,112,97,98,102,103,66,152,119,156,102,103,106,107,152,67,154,74,152,29,154,152,128,152,78,130,131,148,149,71,148,149,148,149,148,77,77,148,149,81,77,77,84,85,86,77,88,77,90,77,92,77,77,95,77,77,77,99,100,101,1,71,104,105,79,79,108,77,79,111,112,81,79,82,84,85,86,119,88,82,90,86,92,87,96,95,94,89,29,99,100,101,1,91,104,105,93,96,108,94,94,111,112,94,110,123,148,149,109,119,102,127,139,126,147,139,150,146,149,154,29,-1,142,123,-1,142,-1,146,-1,-1,71,-1,-1,126,-1,-1,77,-1,148,149,81,35,-1,84,85,86,142,88,-1,90,-1,92,142,-1,95,-1,-1,146,99,100,101,1,71,104,105,146,146,108,77,146,111,112,81,67,146,84,85,86,119,88,146,90,149,92,148,79,95,148,148,83,99,100,101,148,148,104,105,148,148,108,148,148,111,112,148,148,148,148,149,148,119,148,148,148,148,148,148,148,112,148,148,148,148,148,148,148,-1,149,149,149,149,71,149,149,149,129,130,77,149,148,149,81,149,149,84,85,86,149,88,149,90,149,92,150,150,95,151,151,150,99,100,101,156,150,104,105,150,150,108,150,150,111,112,8,9,10,150,150,150,119,150,150,150,150,150,150,150,150,150,150,150,150,150,28,150,30,31,32,33,34,35,36,37,38,39,40,150,150,148,149,151,153,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,-1,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,152,-1,153,-1,154,154,154,154,154,-1,155],r.Parser.prototype.yybase=[0,220,295,94,180,560,-2,-2,-2,-2,-36,473,574,606,574,505,404,675,675,675,28,351,462,462,462,461,396,476,451,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,401,64,201,568,704,713,708,702,714,520,706,705,211,650,651,450,652,653,654,655,709,480,703,712,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,48,30,469,403,403,403,403,403,403,403,403,403,403,403,403,403,403,403,403,403,403,403,160,160,160,343,210,208,198,17,233,27,780,780,780,780,780,108,108,108,108,621,621,93,280,280,280,280,280,280,280,280,280,280,280,632,641,642,643,392,392,151,151,151,151,368,-45,146,224,224,95,410,491,733,199,199,111,207,-22,-22,-22,81,506,92,92,233,233,273,233,423,423,423,221,221,221,221,221,110,221,221,221,617,512,168,516,647,397,503,656,274,381,377,538,535,337,523,337,421,441,428,525,337,337,285,401,394,378,567,474,339,564,140,179,409,399,384,594,561,711,330,710,358,149,378,378,378,370,593,548,355,-8,646,484,277,417,386,645,635,230,634,276,331,356,565,485,485,485,485,485,485,460,485,483,691,691,478,501,460,696,460,485,691,460,460,502,485,522,522,483,508,499,691,691,499,478,460,571,551,514,482,413,413,514,460,413,501,413,11,697,699,444,700,695,698,676,694,493,615,497,515,684,683,693,479,489,620,692,549,592,487,246,314,498,463,689,523,486,455,455,455,463,687,455,455,455,455,455,455,455,455,732,24,495,510,591,590,589,406,588,496,524,422,599,488,549,549,649,727,673,490,682,716,690,555,119,271,681,648,543,492,534,680,598,246,715,494,672,549,671,455,674,701,730,731,688,728,722,152,526,587,178,729,659,596,595,554,725,707,721,720,178,576,511,717,518,677,504,678,613,258,657,686,584,724,723,726,583,582,609,608,250,236,685,442,458,517,581,500,628,604,679,580,579,623,619,718,521,486,519,509,507,513,600,618,719,206,578,586,573,481,572,631,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,134,134,-2,-2,-2,0,0,0,0,-2,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,134,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,418,-3,418,418,-3,418,418,418,418,418,418,-22,-22,-22,-22,221,221,221,221,221,221,221,221,221,221,221,221,221,221,49,49,49,49,-22,-22,221,221,221,221,221,49,221,221,221,92,221,92,92,337,337,0,0,0,0,0,485,92,0,0,0,0,0,0,485,485,485,0,0,0,0,0,485,0,0,0,337,92,0,420,420,178,420,420,0,0,0,485,485,0,508,0,0,0,0,691,0,0,0,0,0,455,119,682,0,39,0,0,0,0,0,490,39,26,0,26,0,0,455,455,455,0,490,490,0,0,67,490,0,0,0,67,35,0,35,0,0,0,178],r.Parser.prototype.yydefault=[3,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,468,468,468,32767,32767,32767,32767,285,460,285,285,32767,419,419,419,419,419,419,419,460,32767,32767,32767,32767,32767,364,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,465,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,347,348,350,351,284,420,237,464,283,116,246,239,191,282,223,119,312,365,314,363,367,313,290,294,295,296,297,298,299,300,301,302,303,304,305,288,289,366,344,343,342,310,311,287,315,317,287,316,333,334,331,332,335,336,337,338,339,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,269,269,269,269,324,325,229,229,229,229,32767,270,32767,229,32767,32767,32767,32767,32767,32767,32767,413,341,319,320,318,32767,392,32767,394,307,309,387,291,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,389,421,421,32767,32767,32767,381,32767,159,210,212,397,32767,32767,32767,32767,32767,329,32767,32767,32767,32767,32767,32767,474,32767,32767,32767,32767,32767,421,32767,32767,32767,321,322,323,32767,32767,32767,421,421,32767,32767,421,32767,421,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,163,32767,32767,395,395,32767,32767,163,390,163,32767,32767,163,163,176,32767,174,174,32767,32767,178,32767,435,178,32767,163,196,196,373,165,231,231,373,163,231,32767,231,32767,32767,32767,82,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,383,32767,32767,32767,401,32767,414,433,381,32767,327,328,330,32767,423,352,353,354,355,356,357,358,360,32767,461,386,32767,32767,32767,32767,32767,32767,84,108,245,32767,473,84,384,32767,473,32767,32767,32767,32767,32767,32767,286,32767,32767,32767,84,32767,84,32767,32767,457,32767,32767,421,385,32767,326,398,439,32767,32767,422,32767,32767,218,84,32767,177,32767,32767,32767,32767,32767,32767,401,32767,32767,179,32767,32767,421,32767,32767,32767,32767,32767,281,32767,32767,32767,32767,32767,421,32767,32767,32767,32767,222,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,82,60,32767,263,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,32767,121,121,3,3,121,121,121,121,121,121,121,121,121,121,121,121,121,121,121,248,154,248,204,248,248,207,196,196,255],r.Parser.prototype.yygoto=[163,163,135,135,135,146,148,179,164,161,145,161,161,161,162,162,162,162,162,162,162,145,157,158,159,160,176,174,177,410,411,299,412,415,416,417,418,419,420,421,422,857,136,137,138,139,140,141,142,143,144,147,173,175,178,195,198,199,201,202,204,205,206,207,208,209,210,211,212,213,232,233,251,252,253,316,317,318,462,180,181,182,183,184,185,186,187,188,189,190,191,192,193,149,194,150,165,166,167,196,168,151,152,153,169,154,197,133,170,155,171,172,156,521,200,257,246,464,432,687,649,278,481,482,527,200,437,437,437,766,5,746,650,557,437,426,775,770,428,431,444,465,466,468,483,279,651,336,450,453,437,560,485,487,508,511,763,516,517,777,524,762,526,532,773,534,480,480,965,965,965,965,965,965,965,965,965,965,965,965,413,413,413,413,413,413,413,413,413,413,413,413,413,413,942,502,478,496,512,456,298,437,437,451,471,437,437,674,437,229,456,230,231,463,828,533,681,438,513,826,461,475,460,414,414,414,414,414,414,414,414,414,414,414,414,414,414,301,674,674,443,454,1033,1033,1034,1034,425,531,425,708,750,800,457,372,1033,943,1034,1026,300,1018,497,8,313,904,796,944,996,785,789,1007,285,670,1036,329,307,310,804,668,544,332,935,940,366,807,678,477,377,754,844,0,667,667,675,675,675,677,0,666,323,498,328,312,312,258,259,283,459,261,322,284,326,486,280,281,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,790,790,790,790,946,0,946,790,790,1004,790,1004,0,0,0,0,836,0,1015,1015,0,0,0,0,0,0,0,0,0,0,0,744,744,744,720,744,0,739,745,721,780,780,1023,0,0,1002,0,0,0,0,0,0,0,0,0,0,0,0,806,0,806,0,0,0,0,1008,1009],r.Parser.prototype.yygcheck=[23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,52,45,112,112,80,8,10,10,64,55,55,55,45,8,8,8,10,92,10,11,10,8,10,10,10,38,38,38,38,38,38,62,62,12,62,28,8,8,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28,70,70,70,70,70,70,70,70,70,70,70,70,70,70,113,113,113,113,113,113,113,113,113,113,113,113,113,113,76,56,35,35,56,69,56,8,8,8,8,8,8,19,8,60,69,60,60,7,7,7,25,8,7,7,2,2,8,115,115,115,115,115,115,115,115,115,115,115,115,115,115,53,19,19,53,53,123,123,124,124,109,5,109,44,29,78,114,53,123,76,124,122,41,120,43,53,42,96,74,76,76,72,75,117,14,21,123,18,9,13,79,20,66,17,102,104,58,81,22,59,100,63,94,-1,19,19,19,19,19,19,-1,19,45,45,45,45,45,45,45,45,45,45,45,45,45,45,64,64,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,52,52,52,52,52,-1,52,52,52,80,52,80,-1,-1,-1,-1,92,-1,80,80,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,52,52,52,52,52,-1,52,52,52,69,69,69,-1,-1,80,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,80,-1,80,-1,-1,-1,-1,80,80],r.Parser.prototype.yygbase=[0,0,-317,0,0,237,0,210,-136,4,118,130,144,-10,16,0,0,-59,10,-47,-9,7,-77,-20,0,209,0,0,-388,234,0,0,0,0,0,165,0,0,103,0,0,225,44,45,235,84,0,0,0,0,0,0,109,-115,0,-113,-179,0,-78,-81,-347,0,-122,-80,-249,0,-19,0,0,169,-48,0,26,0,22,24,-99,0,230,-13,114,-79,0,0,0,0,0,0,0,0,0,0,120,0,-90,0,23,0,0,0,-89,0,-67,0,-69,0,0,0,0,8,0,0,-140,-34,229,9,0,21,0,0,218,0,233,-3,-1,0],r.Parser.prototype.yygdefault=[-32768,380,565,2,566,637,645,504,400,433,748,688,689,303,342,401,302,330,324,676,669,671,679,134,333,682,1,684,439,716,291,692,292,507,694,446,696,697,427,304,305,447,311,479,707,203,308,709,290,710,719,335,293,510,489,469,501,402,363,476,228,455,473,753,277,761,549,769,772,403,404,470,784,368,794,788,960,319,799,805,991,808,811,349,331,327,815,816,4,820,522,523,835,239,843,856,347,923,925,441,374,936,360,334,939,995,354,405,364,952,260,282,245,406,423,249,407,365,998,314,1019,424,1027,1035,275,474],r.Parser.prototype.yylhs=[0,1,3,3,2,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,7,7,8,8,9,4,4,4,4,4,4,4,4,4,4,4,14,14,15,15,15,15,17,17,13,13,18,18,19,19,20,20,21,21,16,16,22,24,24,25,26,26,28,27,27,27,27,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,10,10,48,48,51,51,50,49,49,42,42,53,53,54,54,11,12,12,12,57,57,57,58,58,61,61,59,59,62,62,36,36,44,44,47,47,47,46,46,63,37,37,37,37,64,64,65,65,66,66,34,34,30,30,67,32,32,68,31,31,33,33,43,43,43,43,55,55,71,71,72,72,74,74,75,75,75,73,73,56,56,76,76,77,77,78,78,78,39,39,79,40,40,81,81,60,60,82,82,82,82,87,87,88,88,89,89,89,89,89,90,91,91,86,86,83,83,85,85,93,93,92,92,92,92,92,92,84,84,94,94,41,41,35,35,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,101,95,95,100,100,103,103,104,105,105,105,109,109,52,52,52,96,96,107,107,97,97,99,99,99,102,102,113,113,70,115,115,115,98,98,98,98,98,98,98,98,98,98,98,98,98,98,98,98,38,38,111,111,111,106,106,106,116,116,116,116,116,116,45,45,45,80,80,80,118,110,110,110,110,110,110,108,108,108,117,117,117,117,69,119,119,120,120,120,120,120,114,121,121,122,122,122,122,122,112,112,112,112,124,123,123,123,123,123,123,123,125,125,125],r.Parser.prototype.yylen=[1,1,2,0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,3,1,1,1,1,1,3,5,4,3,4,2,3,1,1,7,8,6,7,3,1,3,1,3,1,1,3,1,2,1,2,3,1,3,3,1,3,2,0,1,1,1,1,1,3,7,10,5,7,9,5,3,3,3,3,3,3,1,2,5,7,9,5,6,3,3,2,2,1,1,1,0,2,1,3,8,0,4,1,3,0,1,0,1,10,7,6,5,1,2,2,0,2,0,2,0,2,1,3,1,4,1,4,1,1,4,1,3,3,3,4,4,5,0,2,4,3,1,1,1,4,0,2,5,0,2,6,0,2,0,3,1,2,1,1,1,0,1,3,4,6,1,2,1,1,1,0,1,0,2,2,3,1,3,1,2,2,3,1,1,3,1,1,3,2,0,3,4,9,3,1,3,0,2,4,5,4,4,4,3,1,1,1,3,1,1,0,1,1,2,1,1,1,1,1,1,1,3,1,3,3,1,0,1,1,3,3,3,4,1,2,3,3,3,3,3,3,3,3,3,3,3,3,2,2,2,2,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,2,2,2,3,3,3,3,3,3,3,3,3,3,3,5,4,3,4,4,2,2,4,2,2,2,2,2,2,2,2,2,2,2,1,3,2,1,2,4,2,10,11,7,3,2,0,4,1,3,2,2,2,4,1,1,1,2,3,1,1,1,1,0,3,0,1,1,0,1,1,3,3,4,1,1,1,1,1,1,1,1,1,1,1,1,1,1,3,2,3,3,0,1,1,3,1,1,3,1,1,4,4,4,1,4,1,1,3,1,4,2,3,1,4,4,3,3,3,1,3,1,1,3,1,1,4,3,1,1,1,3,3,0,1,3,1,3,1,4,2,0,2,2,1,2,1,1,4,3,3,3,6,3,1,1,1],t.PHP=r}),define(\"ace/mode/php_worker\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/worker/mirror\",\"ace/mode/php/php\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../worker/mirror\").Mirror,s=e(\"./php/php\").PHP,o=t.PhpWorker=function(e){i.call(this,e),this.setTimeout(500)};r.inherits(o,i),function(){this.setOptions=function(e){this.inlinePhp=e&&e.inline},this.onUpdate=function(){var e=this.doc.getValue(),t=[];this.inlinePhp&&(e=\"<?\"+e+\"?>\");var n=s.Lexer(e,{short_open_tag:1});try{new s.Parser(n)}catch(r){t.push({row:r.line-1,column:null,text:r.message.charAt(0).toUpperCase()+r.message.substring(1),type:\"error\"})}this.sender.emit(\"annotate\",t)}}.call(o.prototype)}),define(\"ace/lib/es5-shim\",[\"require\",\"exports\",\"module\"],function(e,t,n){function r(){}function w(e){try{return Object.defineProperty(e,\"sentinel\",{}),\"sentinel\"in e}catch(t){}}function H(e){return e=+e,e!==e?e=0:e!==0&&e!==1/0&&e!==-1/0&&(e=(e>0||-1)*Math.floor(Math.abs(e))),e}function B(e){var t=typeof e;return e===null||t===\"undefined\"||t===\"boolean\"||t===\"number\"||t===\"string\"}function j(e){var t,n,r;if(B(e))return e;n=e.valueOf;if(typeof n==\"function\"){t=n.call(e);if(B(t))return t}r=e.toString;if(typeof r==\"function\"){t=r.call(e);if(B(t))return t}throw new TypeError}Function.prototype.bind||(Function.prototype.bind=function(t){var n=this;if(typeof n!=\"function\")throw new TypeError(\"Function.prototype.bind called on incompatible \"+n);var i=u.call(arguments,1),s=function(){if(this instanceof s){var e=n.apply(this,i.concat(u.call(arguments)));return Object(e)===e?e:this}return n.apply(t,i.concat(u.call(arguments)))};return n.prototype&&(r.prototype=n.prototype,s.prototype=new r,r.prototype=null),s});var i=Function.prototype.call,s=Array.prototype,o=Object.prototype,u=s.slice,a=i.bind(o.toString),f=i.bind(o.hasOwnProperty),l,c,h,p,d;if(d=f(o,\"__defineGetter__\"))l=i.bind(o.__defineGetter__),c=i.bind(o.__defineSetter__),h=i.bind(o.__lookupGetter__),p=i.bind(o.__lookupSetter__);if([1,2].splice(0).length!=2)if(!function(){function e(e){var t=new Array(e+2);return t[0]=t[1]=0,t}var t=[],n;t.splice.apply(t,e(20)),t.splice.apply(t,e(26)),n=t.length,t.splice(5,0,\"XXX\"),n+1==t.length;if(n+1==t.length)return!0}())Array.prototype.splice=function(e,t){var n=this.length;e>0?e>n&&(e=n):e==void 0?e=0:e<0&&(e=Math.max(n+e,0)),e+t<n||(t=n-e);var r=this.slice(e,e+t),i=u.call(arguments,2),s=i.length;if(e===n)s&&this.push.apply(this,i);else{var o=Math.min(t,n-e),a=e+o,f=a+s-o,l=n-a,c=n-o;if(f<a)for(var h=0;h<l;++h)this[f+h]=this[a+h];else if(f>a)for(h=l;h--;)this[f+h]=this[a+h];if(s&&e===c)this.length=c,this.push.apply(this,i);else{this.length=c+s;for(h=0;h<s;++h)this[e+h]=i[h]}}return r};else{var v=Array.prototype.splice;Array.prototype.splice=function(e,t){return arguments.length?v.apply(this,[e===void 0?0:e,t===void 0?this.length-e:t].concat(u.call(arguments,2))):[]}}Array.isArray||(Array.isArray=function(t){return a(t)==\"[object Array]\"});var m=Object(\"a\"),g=m[0]!=\"a\"||!(0 in m);Array.prototype.forEach||(Array.prototype.forEach=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=arguments[1],s=-1,o=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError;while(++s<o)s in r&&t.call(i,r[s],s,n)}),Array.prototype.map||(Array.prototype.map=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=Array(i),o=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var u=0;u<i;u++)u in r&&(s[u]=t.call(o,r[u],u,n));return s}),Array.prototype.filter||(Array.prototype.filter=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=[],o,u=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var f=0;f<i;f++)f in r&&(o=r[f],t.call(u,o,f,n)&&s.push(o));return s}),Array.prototype.every||(Array.prototype.every=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&!t.call(s,r[o],o,n))return!1;return!0}),Array.prototype.some||(Array.prototype.some=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&t.call(s,r[o],o,n))return!0;return!1}),Array.prototype.reduce||(Array.prototype.reduce=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduce of empty array with no initial value\");var s=0,o;if(arguments.length>=2)o=arguments[1];else do{if(s in r){o=r[s++];break}if(++s>=i)throw new TypeError(\"reduce of empty array with no initial value\")}while(!0);for(;s<i;s++)s in r&&(o=t.call(void 0,o,r[s],s,n));return o}),Array.prototype.reduceRight||(Array.prototype.reduceRight=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduceRight of empty array with no initial value\");var s,o=i-1;if(arguments.length>=2)s=arguments[1];else do{if(o in r){s=r[o--];break}if(--o<0)throw new TypeError(\"reduceRight of empty array with no initial value\")}while(!0);do o in this&&(s=t.call(void 0,s,r[o],o,n));while(o--);return s});if(!Array.prototype.indexOf||[0,1].indexOf(1,2)!=-1)Array.prototype.indexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=0;arguments.length>1&&(i=H(arguments[1])),i=i>=0?i:Math.max(0,r+i);for(;i<r;i++)if(i in n&&n[i]===t)return i;return-1};if(!Array.prototype.lastIndexOf||[0,1].lastIndexOf(0,-3)!=-1)Array.prototype.lastIndexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=r-1;arguments.length>1&&(i=Math.min(i,H(arguments[1]))),i=i>=0?i:r-Math.abs(i);for(;i>=0;i--)if(i in n&&t===n[i])return i;return-1};Object.getPrototypeOf||(Object.getPrototypeOf=function(t){return t.__proto__||(t.constructor?t.constructor.prototype:o)});if(!Object.getOwnPropertyDescriptor){var y=\"Object.getOwnPropertyDescriptor called on a non-object: \";Object.getOwnPropertyDescriptor=function(t,n){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(y+t);if(!f(t,n))return;var r,i,s;r={enumerable:!0,configurable:!0};if(d){var u=t.__proto__;t.__proto__=o;var i=h(t,n),s=p(t,n);t.__proto__=u;if(i||s)return i&&(r.get=i),s&&(r.set=s),r}return r.value=t[n],r}}Object.getOwnPropertyNames||(Object.getOwnPropertyNames=function(t){return Object.keys(t)});if(!Object.create){var b;Object.prototype.__proto__===null?b=function(){return{__proto__:null}}:b=function(){var e={};for(var t in e)e[t]=null;return e.constructor=e.hasOwnProperty=e.propertyIsEnumerable=e.isPrototypeOf=e.toLocaleString=e.toString=e.valueOf=e.__proto__=null,e},Object.create=function(t,n){var r;if(t===null)r=b();else{if(typeof t!=\"object\")throw new TypeError(\"typeof prototype[\"+typeof t+\"] != 'object'\");var i=function(){};i.prototype=t,r=new i,r.__proto__=t}return n!==void 0&&Object.defineProperties(r,n),r}}if(Object.defineProperty){var E=w({}),S=typeof document==\"undefined\"||w(document.createElement(\"div\"));if(!E||!S)var x=Object.defineProperty}if(!Object.defineProperty||x){var T=\"Property description must be an object: \",N=\"Object.defineProperty called on non-object: \",C=\"getters & setters can not be defined on this javascript engine\";Object.defineProperty=function(t,n,r){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(N+t);if(typeof r!=\"object\"&&typeof r!=\"function\"||r===null)throw new TypeError(T+r);if(x)try{return x.call(Object,t,n,r)}catch(i){}if(f(r,\"value\"))if(d&&(h(t,n)||p(t,n))){var s=t.__proto__;t.__proto__=o,delete t[n],t[n]=r.value,t.__proto__=s}else t[n]=r.value;else{if(!d)throw new TypeError(C);f(r,\"get\")&&l(t,n,r.get),f(r,\"set\")&&c(t,n,r.set)}return t}}Object.defineProperties||(Object.defineProperties=function(t,n){for(var r in n)f(n,r)&&Object.defineProperty(t,r,n[r]);return t}),Object.seal||(Object.seal=function(t){return t}),Object.freeze||(Object.freeze=function(t){return t});try{Object.freeze(function(){})}catch(k){Object.freeze=function(t){return function(n){return typeof n==\"function\"?n:t(n)}}(Object.freeze)}Object.preventExtensions||(Object.preventExtensions=function(t){return t}),Object.isSealed||(Object.isSealed=function(t){return!1}),Object.isFrozen||(Object.isFrozen=function(t){return!1}),Object.isExtensible||(Object.isExtensible=function(t){if(Object(t)===t)throw new TypeError;var n=\"\";while(f(t,n))n+=\"?\";t[n]=!0;var r=f(t,n);return delete t[n],r});if(!Object.keys){var L=!0,A=[\"toString\",\"toLocaleString\",\"valueOf\",\"hasOwnProperty\",\"isPrototypeOf\",\"propertyIsEnumerable\",\"constructor\"],O=A.length;for(var M in{toString:null})L=!1;Object.keys=function I(e){if(typeof e!=\"object\"&&typeof e!=\"function\"||e===null)throw new TypeError(\"Object.keys called on a non-object\");var I=[];for(var t in e)f(e,t)&&I.push(t);if(L)for(var n=0,r=O;n<r;n++){var i=A[n];f(e,i)&&I.push(i)}return I}}Date.now||(Date.now=function(){return(new Date).getTime()});var _=\"\t\\n\u000b\\f\\r \\u00a0\\u1680\\u180e\\u2000\\u2001\\u2002\\u2003\\u2004\\u2005\\u2006\\u2007\\u2008\\u2009\\u200a\\u202f\\u205f\\u3000\\u2028\\u2029\\ufeff\";if(!String.prototype.trim||_.trim()){_=\"[\"+_+\"]\";var D=new RegExp(\"^\"+_+_+\"*\"),P=new RegExp(_+_+\"*$\");String.prototype.trim=function(){return String(this).replace(D,\"\").replace(P,\"\")}}var F=function(e){if(e==null)throw new TypeError(\"can't convert \"+e+\" to object\");return Object(e)}})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ace/worker-xml.js",
    "content": "\"no use strict\";(function(e){function t(e,t){var n=e,r=\"\";while(n){var i=t[n];if(typeof i==\"string\")return i+r;if(i)return i.location.replace(/\\/*$/,\"/\")+(r||i.main||i.name);if(i===!1)return\"\";var s=n.lastIndexOf(\"/\");if(s===-1)break;r=n.substr(s)+r,n=n.slice(0,s)}return e}if(typeof e.window!=\"undefined\"&&e.document)return;if(e.require&&e.define)return;e.console||(e.console=function(){var e=Array.prototype.slice.call(arguments,0);postMessage({type:\"log\",data:e})},e.console.error=e.console.warn=e.console.log=e.console.trace=e.console),e.window=e,e.ace=e,e.onerror=function(e,t,n,r,i){postMessage({type:\"error\",data:{message:e,data:i.data,file:t,line:n,col:r,stack:i.stack}})},e.normalizeModule=function(t,n){if(n.indexOf(\"!\")!==-1){var r=n.split(\"!\");return e.normalizeModule(t,r[0])+\"!\"+e.normalizeModule(t,r[1])}if(n.charAt(0)==\".\"){var i=t.split(\"/\").slice(0,-1).join(\"/\");n=(i?i+\"/\":\"\")+n;while(n.indexOf(\".\")!==-1&&s!=n){var s=n;n=n.replace(/^\\.\\//,\"\").replace(/\\/\\.\\//,\"/\").replace(/[^\\/]+\\/\\.\\.\\//,\"\")}}return n},e.require=function(r,i){i||(i=r,r=null);if(!i.charAt)throw new Error(\"worker.js require() accepts only (parentId, id) as arguments\");i=e.normalizeModule(r,i);var s=e.require.modules[i];if(s)return s.initialized||(s.initialized=!0,s.exports=s.factory().exports),s.exports;if(!e.require.tlns)return console.log(\"unable to load \"+i);var o=t(i,e.require.tlns);return o.slice(-3)!=\".js\"&&(o+=\".js\"),e.require.id=i,e.require.modules[i]={},importScripts(o),e.require(r,i)},e.require.modules={},e.require.tlns={},e.define=function(t,n,r){arguments.length==2?(r=n,typeof t!=\"string\"&&(n=t,t=e.require.id)):arguments.length==1&&(r=t,n=[],t=e.require.id);if(typeof r!=\"function\"){e.require.modules[t]={exports:r,initialized:!0};return}n.length||(n=[\"require\",\"exports\",\"module\"]);var i=function(n){return e.require(t,n)};e.require.modules[t]={exports:{},factory:function(){var e=this,t=r.apply(this,n.map(function(t){switch(t){case\"require\":return i;case\"exports\":return e.exports;case\"module\":return e;default:return i(t)}}));return t&&(e.exports=t),e}}},e.define.amd={},require.tlns={},e.initBaseUrls=function(t){for(var n in t)require.tlns[n]=t[n]},e.initSender=function(){var n=e.require(\"ace/lib/event_emitter\").EventEmitter,r=e.require(\"ace/lib/oop\"),i=function(){};return function(){r.implement(this,n),this.callback=function(e,t){postMessage({type:\"call\",id:t,data:e})},this.emit=function(e,t){postMessage({type:\"event\",name:e,data:t})}}.call(i.prototype),new i};var n=e.main=null,r=e.sender=null;e.onmessage=function(t){var i=t.data;if(i.event&&r)r._signal(i.event,i.data);else if(i.command)if(n[i.command])n[i.command].apply(n,i.args);else{if(!e[i.command])throw new Error(\"Unknown command:\"+i.command);e[i.command].apply(e,i.args)}else if(i.init){e.initBaseUrls(i.tlns),require(\"ace/lib/es5-shim\"),r=e.sender=e.initSender();var s=require(i.module)[i.classname];n=e.main=new s(r)}}})(this),define(\"ace/lib/oop\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.inherits=function(e,t){e.super_=t,e.prototype=Object.create(t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}})},t.mixin=function(e,t){for(var n in t)e[n]=t[n];return e},t.implement=function(e,n){t.mixin(e,n)}}),define(\"ace/lib/lang\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";t.last=function(e){return e[e.length-1]},t.stringReverse=function(e){return e.split(\"\").reverse().join(\"\")},t.stringRepeat=function(e,t){var n=\"\";while(t>0){t&1&&(n+=e);if(t>>=1)e+=e}return n};var r=/^\\s\\s*/,i=/\\s\\s*$/;t.stringTrimLeft=function(e){return e.replace(r,\"\")},t.stringTrimRight=function(e){return e.replace(i,\"\")},t.copyObject=function(e){var t={};for(var n in e)t[n]=e[n];return t},t.copyArray=function(e){var t=[];for(var n=0,r=e.length;n<r;n++)e[n]&&typeof e[n]==\"object\"?t[n]=this.copyObject(e[n]):t[n]=e[n];return t},t.deepCopy=function s(e){if(typeof e!=\"object\"||!e)return e;var t;if(Array.isArray(e)){t=[];for(var n=0;n<e.length;n++)t[n]=s(e[n]);return t}if(Object.prototype.toString.call(e)!==\"[object Object]\")return e;t={};for(var n in e)t[n]=s(e[n]);return t},t.arrayToMap=function(e){var t={};for(var n=0;n<e.length;n++)t[e[n]]=1;return t},t.createMap=function(e){var t=Object.create(null);for(var n in e)t[n]=e[n];return t},t.arrayRemove=function(e,t){for(var n=0;n<=e.length;n++)t===e[n]&&e.splice(n,1)},t.escapeRegExp=function(e){return e.replace(/([.*+?^${}()|[\\]\\/\\\\])/g,\"\\\\$1\")},t.escapeHTML=function(e){return e.replace(/&/g,\"&#38;\").replace(/\"/g,\"&#34;\").replace(/'/g,\"&#39;\").replace(/</g,\"&#60;\")},t.getMatchOffsets=function(e,t){var n=[];return e.replace(t,function(e){n.push({offset:arguments[arguments.length-2],length:e.length})}),n},t.deferredCall=function(e){var t=null,n=function(){t=null,e()},r=function(e){return r.cancel(),t=setTimeout(n,e||0),r};return r.schedule=r,r.call=function(){return this.cancel(),e(),r},r.cancel=function(){return clearTimeout(t),t=null,r},r.isPending=function(){return t},r},t.delayedCall=function(e,t){var n=null,r=function(){n=null,e()},i=function(e){n==null&&(n=setTimeout(r,e||t))};return i.delay=function(e){n&&clearTimeout(n),n=setTimeout(r,e||t)},i.schedule=i,i.call=function(){this.cancel(),e()},i.cancel=function(){n&&clearTimeout(n),n=null},i.isPending=function(){return n},i}}),define(\"ace/range\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r=function(e,t){return e.row-t.row||e.column-t.column},i=function(e,t,n,r){this.start={row:e,column:t},this.end={row:n,column:r}};(function(){this.isEqual=function(e){return this.start.row===e.start.row&&this.end.row===e.end.row&&this.start.column===e.start.column&&this.end.column===e.end.column},this.toString=function(){return\"Range: [\"+this.start.row+\"/\"+this.start.column+\"] -> [\"+this.end.row+\"/\"+this.end.column+\"]\"},this.contains=function(e,t){return this.compare(e,t)==0},this.compareRange=function(e){var t,n=e.end,r=e.start;return t=this.compare(n.row,n.column),t==1?(t=this.compare(r.row,r.column),t==1?2:t==0?1:0):t==-1?-2:(t=this.compare(r.row,r.column),t==-1?-1:t==1?42:0)},this.comparePoint=function(e){return this.compare(e.row,e.column)},this.containsRange=function(e){return this.comparePoint(e.start)==0&&this.comparePoint(e.end)==0},this.intersects=function(e){var t=this.compareRange(e);return t==-1||t==0||t==1},this.isEnd=function(e,t){return this.end.row==e&&this.end.column==t},this.isStart=function(e,t){return this.start.row==e&&this.start.column==t},this.setStart=function(e,t){typeof e==\"object\"?(this.start.column=e.column,this.start.row=e.row):(this.start.row=e,this.start.column=t)},this.setEnd=function(e,t){typeof e==\"object\"?(this.end.column=e.column,this.end.row=e.row):(this.end.row=e,this.end.column=t)},this.inside=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)||this.isStart(e,t)?!1:!0:!1},this.insideStart=function(e,t){return this.compare(e,t)==0?this.isEnd(e,t)?!1:!0:!1},this.insideEnd=function(e,t){return this.compare(e,t)==0?this.isStart(e,t)?!1:!0:!1},this.compare=function(e,t){return!this.isMultiLine()&&e===this.start.row?t<this.start.column?-1:t>this.end.column?1:0:e<this.start.row?-1:e>this.end.row?1:this.start.row===e?t>=this.start.column?0:-1:this.end.row===e?t<=this.end.column?0:1:0},this.compareStart=function(e,t){return this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.compareEnd=function(e,t){return this.end.row==e&&this.end.column==t?1:this.compare(e,t)},this.compareInside=function(e,t){return this.end.row==e&&this.end.column==t?1:this.start.row==e&&this.start.column==t?-1:this.compare(e,t)},this.clipRows=function(e,t){if(this.end.row>t)var n={row:t+1,column:0};else if(this.end.row<e)var n={row:e,column:0};if(this.start.row>t)var r={row:t+1,column:0};else if(this.start.row<e)var r={row:e,column:0};return i.fromPoints(r||this.start,n||this.end)},this.extend=function(e,t){var n=this.compare(e,t);if(n==0)return this;if(n==-1)var r={row:e,column:t};else var s={row:e,column:t};return i.fromPoints(r||this.start,s||this.end)},this.isEmpty=function(){return this.start.row===this.end.row&&this.start.column===this.end.column},this.isMultiLine=function(){return this.start.row!==this.end.row},this.clone=function(){return i.fromPoints(this.start,this.end)},this.collapseRows=function(){return this.end.column==0?new i(this.start.row,0,Math.max(this.start.row,this.end.row-1),0):new i(this.start.row,0,this.end.row,0)},this.toScreenRange=function(e){var t=e.documentToScreenPosition(this.start),n=e.documentToScreenPosition(this.end);return new i(t.row,t.column,n.row,n.column)},this.moveBy=function(e,t){this.start.row+=e,this.start.column+=t,this.end.row+=e,this.end.column+=t}}).call(i.prototype),i.fromPoints=function(e,t){return new i(e.row,e.column,t.row,t.column)},i.comparePoints=r,i.comparePoints=function(e,t){return e.row-t.row||e.column-t.column},t.Range=i}),define(\"ace/apply_delta\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";function r(e,t){throw console.log(\"Invalid Delta:\",e),\"Invalid Delta: \"+t}function i(e,t){return t.row>=0&&t.row<e.length&&t.column>=0&&t.column<=e[t.row].length}function s(e,t){t.action!=\"insert\"&&t.action!=\"remove\"&&r(t,\"delta.action must be 'insert' or 'remove'\"),t.lines instanceof Array||r(t,\"delta.lines must be an Array\"),(!t.start||!t.end)&&r(t,\"delta.start/end must be an present\");var n=t.start;i(e,t.start)||r(t,\"delta.start must be contained in document\");var s=t.end;t.action==\"remove\"&&!i(e,s)&&r(t,\"delta.end must contained in document for 'remove' actions\");var o=s.row-n.row,u=s.column-(o==0?n.column:0);(o!=t.lines.length-1||t.lines[o].length!=u)&&r(t,\"delta.range must match delta lines\")}t.applyDelta=function(e,t,n){var r=t.start.row,i=t.start.column,s=e[r]||\"\";switch(t.action){case\"insert\":var o=t.lines;if(o.length===1)e[r]=s.substring(0,i)+t.lines[0]+s.substring(i);else{var u=[r,1].concat(t.lines);e.splice.apply(e,u),e[r]=s.substring(0,i)+e[r],e[r+t.lines.length-1]+=s.substring(i)}break;case\"remove\":var a=t.end.column,f=t.end.row;r===f?e[r]=s.substring(0,i)+s.substring(a):e.splice(r,f-r+1,s.substring(0,i)+e[f].substring(a))}}}),define(\"ace/lib/event_emitter\",[\"require\",\"exports\",\"module\"],function(e,t,n){\"use strict\";var r={},i=function(){this.propagationStopped=!0},s=function(){this.defaultPrevented=!0};r._emit=r._dispatchEvent=function(e,t){this._eventRegistry||(this._eventRegistry={}),this._defaultHandlers||(this._defaultHandlers={});var n=this._eventRegistry[e]||[],r=this._defaultHandlers[e];if(!n.length&&!r)return;if(typeof t!=\"object\"||!t)t={};t.type||(t.type=e),t.stopPropagation||(t.stopPropagation=i),t.preventDefault||(t.preventDefault=s),n=n.slice();for(var o=0;o<n.length;o++){n[o](t,this);if(t.propagationStopped)break}if(r&&!t.defaultPrevented)return r(t,this)},r._signal=function(e,t){var n=(this._eventRegistry||{})[e];if(!n)return;n=n.slice();for(var r=0;r<n.length;r++)n[r](t,this)},r.once=function(e,t){var n=this;t&&this.addEventListener(e,function r(){n.removeEventListener(e,r),t.apply(null,arguments)})},r.setDefaultHandler=function(e,t){var n=this._defaultHandlers;n||(n=this._defaultHandlers={_disabled_:{}});if(n[e]){var r=n[e],i=n._disabled_[e];i||(n._disabled_[e]=i=[]),i.push(r);var s=i.indexOf(t);s!=-1&&i.splice(s,1)}n[e]=t},r.removeDefaultHandler=function(e,t){var n=this._defaultHandlers;if(!n)return;var r=n._disabled_[e];if(n[e]==t){var i=n[e];r&&this.setDefaultHandler(e,r.pop())}else if(r){var s=r.indexOf(t);s!=-1&&r.splice(s,1)}},r.on=r.addEventListener=function(e,t,n){this._eventRegistry=this._eventRegistry||{};var r=this._eventRegistry[e];return r||(r=this._eventRegistry[e]=[]),r.indexOf(t)==-1&&r[n?\"unshift\":\"push\"](t),t},r.off=r.removeListener=r.removeEventListener=function(e,t){this._eventRegistry=this._eventRegistry||{};var n=this._eventRegistry[e];if(!n)return;var r=n.indexOf(t);r!==-1&&n.splice(r,1)},r.removeAllListeners=function(e){this._eventRegistry&&(this._eventRegistry[e]=[])},t.EventEmitter=r}),define(\"ace/anchor\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/event_emitter\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./lib/event_emitter\").EventEmitter,s=t.Anchor=function(e,t,n){this.$onChange=this.onChange.bind(this),this.attach(e),typeof n==\"undefined\"?this.setPosition(t.row,t.column):this.setPosition(t,n)};(function(){function e(e,t,n){var r=n?e.column<=t.column:e.column<t.column;return e.row<t.row||e.row==t.row&&r}function t(t,n,r){var i=t.action==\"insert\",s=(i?1:-1)*(t.end.row-t.start.row),o=(i?1:-1)*(t.end.column-t.start.column),u=t.start,a=i?u:t.end;return e(n,u,r)?{row:n.row,column:n.column}:e(a,n,!r)?{row:n.row+s,column:n.column+(n.row==a.row?o:0)}:{row:u.row,column:u.column}}r.implement(this,i),this.getPosition=function(){return this.$clipPositionToDocument(this.row,this.column)},this.getDocument=function(){return this.document},this.$insertRight=!1,this.onChange=function(e){if(e.start.row==e.end.row&&e.start.row!=this.row)return;if(e.start.row>this.row)return;var n=t(e,{row:this.row,column:this.column},this.$insertRight);this.setPosition(n.row,n.column,!0)},this.setPosition=function(e,t,n){var r;n?r={row:e,column:t}:r=this.$clipPositionToDocument(e,t);if(this.row==r.row&&this.column==r.column)return;var i={row:this.row,column:this.column};this.row=r.row,this.column=r.column,this._signal(\"change\",{old:i,value:r})},this.detach=function(){this.document.removeEventListener(\"change\",this.$onChange)},this.attach=function(e){this.document=e||this.document,this.document.on(\"change\",this.$onChange)},this.$clipPositionToDocument=function(e,t){var n={};return e>=this.document.getLength()?(n.row=Math.max(0,this.document.getLength()-1),n.column=this.document.getLine(n.row).length):e<0?(n.row=0,n.column=0):(n.row=e,n.column=Math.min(this.document.getLine(n.row).length,Math.max(0,t))),t<0&&(n.column=0),n}}).call(s.prototype)}),define(\"ace/document\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/apply_delta\",\"ace/lib/event_emitter\",\"ace/range\",\"ace/anchor\"],function(e,t,n){\"use strict\";var r=e(\"./lib/oop\"),i=e(\"./apply_delta\").applyDelta,s=e(\"./lib/event_emitter\").EventEmitter,o=e(\"./range\").Range,u=e(\"./anchor\").Anchor,a=function(e){this.$lines=[\"\"],e.length===0?this.$lines=[\"\"]:Array.isArray(e)?this.insertMergedLines({row:0,column:0},e):this.insert({row:0,column:0},e)};(function(){r.implement(this,s),this.setValue=function(e){var t=this.getLength()-1;this.remove(new o(0,0,t,this.getLine(t).length)),this.insert({row:0,column:0},e)},this.getValue=function(){return this.getAllLines().join(this.getNewLineCharacter())},this.createAnchor=function(e,t){return new u(this,e,t)},\"aaa\".split(/a/).length===0?this.$split=function(e){return e.replace(/\\r\\n|\\r/g,\"\\n\").split(\"\\n\")}:this.$split=function(e){return e.split(/\\r\\n|\\r|\\n/)},this.$detectNewLine=function(e){var t=e.match(/^.*?(\\r\\n|\\r|\\n)/m);this.$autoNewLine=t?t[1]:\"\\n\",this._signal(\"changeNewLineMode\")},this.getNewLineCharacter=function(){switch(this.$newLineMode){case\"windows\":return\"\\r\\n\";case\"unix\":return\"\\n\";default:return this.$autoNewLine||\"\\n\"}},this.$autoNewLine=\"\",this.$newLineMode=\"auto\",this.setNewLineMode=function(e){if(this.$newLineMode===e)return;this.$newLineMode=e,this._signal(\"changeNewLineMode\")},this.getNewLineMode=function(){return this.$newLineMode},this.isNewLine=function(e){return e==\"\\r\\n\"||e==\"\\r\"||e==\"\\n\"},this.getLine=function(e){return this.$lines[e]||\"\"},this.getLines=function(e,t){return this.$lines.slice(e,t+1)},this.getAllLines=function(){return this.getLines(0,this.getLength())},this.getLength=function(){return this.$lines.length},this.getTextRange=function(e){return this.getLinesForRange(e).join(this.getNewLineCharacter())},this.getLinesForRange=function(e){var t;if(e.start.row===e.end.row)t=[this.getLine(e.start.row).substring(e.start.column,e.end.column)];else{t=this.getLines(e.start.row,e.end.row),t[0]=(t[0]||\"\").substring(e.start.column);var n=t.length-1;e.end.row-e.start.row==n&&(t[n]=t[n].substring(0,e.end.column))}return t},this.insertLines=function(e,t){return console.warn(\"Use of document.insertLines is deprecated. Use the insertFullLines method instead.\"),this.insertFullLines(e,t)},this.removeLines=function(e,t){return console.warn(\"Use of document.removeLines is deprecated. Use the removeFullLines method instead.\"),this.removeFullLines(e,t)},this.insertNewLine=function(e){return console.warn(\"Use of document.insertNewLine is deprecated. Use insertMergedLines(position, ['', '']) instead.\"),this.insertMergedLines(e,[\"\",\"\"])},this.insert=function(e,t){return this.getLength()<=1&&this.$detectNewLine(t),this.insertMergedLines(e,this.$split(t))},this.insertInLine=function(e,t){var n=this.clippedPos(e.row,e.column),r=this.pos(e.row,e.column+t.length);return this.applyDelta({start:n,end:r,action:\"insert\",lines:[t]},!0),this.clonePos(r)},this.clippedPos=function(e,t){var n=this.getLength();e===undefined?e=n:e<0?e=0:e>=n&&(e=n-1,t=undefined);var r=this.getLine(e);return t==undefined&&(t=r.length),t=Math.min(Math.max(t,0),r.length),{row:e,column:t}},this.clonePos=function(e){return{row:e.row,column:e.column}},this.pos=function(e,t){return{row:e,column:t}},this.$clipPosition=function(e){var t=this.getLength();return e.row>=t?(e.row=Math.max(0,t-1),e.column=this.getLine(t-1).length):(e.row=Math.max(0,e.row),e.column=Math.min(Math.max(e.column,0),this.getLine(e.row).length)),e},this.insertFullLines=function(e,t){e=Math.min(Math.max(e,0),this.getLength());var n=0;e<this.getLength()?(t=t.concat([\"\"]),n=0):(t=[\"\"].concat(t),e--,n=this.$lines[e].length),this.insertMergedLines({row:e,column:n},t)},this.insertMergedLines=function(e,t){var n=this.clippedPos(e.row,e.column),r={row:n.row+t.length-1,column:(t.length==1?n.column:0)+t[t.length-1].length};return this.applyDelta({start:n,end:r,action:\"insert\",lines:t}),this.clonePos(r)},this.remove=function(e){var t=this.clippedPos(e.start.row,e.start.column),n=this.clippedPos(e.end.row,e.end.column);return this.applyDelta({start:t,end:n,action:\"remove\",lines:this.getLinesForRange({start:t,end:n})}),this.clonePos(t)},this.removeInLine=function(e,t,n){var r=this.clippedPos(e,t),i=this.clippedPos(e,n);return this.applyDelta({start:r,end:i,action:\"remove\",lines:this.getLinesForRange({start:r,end:i})},!0),this.clonePos(r)},this.removeFullLines=function(e,t){e=Math.min(Math.max(0,e),this.getLength()-1),t=Math.min(Math.max(0,t),this.getLength()-1);var n=t==this.getLength()-1&&e>0,r=t<this.getLength()-1,i=n?e-1:e,s=n?this.getLine(i).length:0,u=r?t+1:t,a=r?0:this.getLine(u).length,f=new o(i,s,u,a),l=this.$lines.slice(e,t+1);return this.applyDelta({start:f.start,end:f.end,action:\"remove\",lines:this.getLinesForRange(f)}),l},this.removeNewLine=function(e){e<this.getLength()-1&&e>=0&&this.applyDelta({start:this.pos(e,this.getLine(e).length),end:this.pos(e+1,0),action:\"remove\",lines:[\"\",\"\"]})},this.replace=function(e,t){e instanceof o||(e=o.fromPoints(e.start,e.end));if(t.length===0&&e.isEmpty())return e.start;if(t==this.getTextRange(e))return e.end;this.remove(e);var n;return t?n=this.insert(e.start,t):n=e.start,n},this.applyDeltas=function(e){for(var t=0;t<e.length;t++)this.applyDelta(e[t])},this.revertDeltas=function(e){for(var t=e.length-1;t>=0;t--)this.revertDelta(e[t])},this.applyDelta=function(e,t){var n=e.action==\"insert\";if(n?e.lines.length<=1&&!e.lines[0]:!o.comparePoints(e.start,e.end))return;n&&e.lines.length>2e4&&this.$splitAndapplyLargeDelta(e,2e4),i(this.$lines,e,t),this._signal(\"change\",e)},this.$splitAndapplyLargeDelta=function(e,t){var n=e.lines,r=n.length,i=e.start.row,s=e.start.column,o=0,u=0;do{o=u,u+=t-1;var a=n.slice(o,u);if(u>r){e.lines=a,e.start.row=i+o,e.start.column=s;break}a.push(\"\"),this.applyDelta({start:this.pos(i+o,s),end:this.pos(i+u,s=0),action:e.action,lines:a},!0)}while(!0)},this.revertDelta=function(e){this.applyDelta({start:this.clonePos(e.start),end:this.clonePos(e.end),action:e.action==\"insert\"?\"remove\":\"insert\",lines:e.lines.slice()})},this.indexToPosition=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length;for(var i=t||0,s=n.length;i<s;i++){e-=n[i].length+r;if(e<0)return{row:i,column:e+n[i].length+r}}return{row:s-1,column:n[s-1].length}},this.positionToIndex=function(e,t){var n=this.$lines||this.getAllLines(),r=this.getNewLineCharacter().length,i=0,s=Math.min(e.row,n.length);for(var o=t||0;o<s;++o)i+=n[o].length+r;return i+e.column}}).call(a.prototype),t.Document=a}),define(\"ace/worker/mirror\",[\"require\",\"exports\",\"module\",\"ace/range\",\"ace/document\",\"ace/lib/lang\"],function(e,t,n){\"use strict\";var r=e(\"../range\").Range,i=e(\"../document\").Document,s=e(\"../lib/lang\"),o=t.Mirror=function(e){this.sender=e;var t=this.doc=new i(\"\"),n=this.deferredUpdate=s.delayedCall(this.onUpdate.bind(this)),r=this;e.on(\"change\",function(e){var i=e.data;if(i[0].start)t.applyDeltas(i);else for(var s=0;s<i.length;s+=2){if(Array.isArray(i[s+1]))var o={action:\"insert\",start:i[s],lines:i[s+1]};else var o={action:\"remove\",start:i[s],end:i[s+1]};t.applyDelta(o,!0)}if(r.$timeout)return n.schedule(r.$timeout);r.onUpdate()})};(function(){this.$timeout=500,this.setTimeout=function(e){this.$timeout=e},this.setValue=function(e){this.doc.setValue(e),this.deferredUpdate.schedule(this.$timeout)},this.getValue=function(e){this.sender.callback(this.doc.getValue(),e)},this.onUpdate=function(){},this.isPending=function(){return this.deferredUpdate.isPending()}}).call(o.prototype)}),define(\"ace/mode/xml/sax\",[\"require\",\"exports\",\"module\"],function(e,t,n){function d(){}function v(e,t,n,r,i){function s(e){if(e>65535){e-=65536;var t=55296+(e>>10),n=56320+(e&1023);return String.fromCharCode(t,n)}return String.fromCharCode(e)}function o(e){var t=e.slice(1,-1);return t in n?n[t]:t.charAt(0)===\"#\"?s(parseInt(t.substr(1).replace(\"x\",\"0x\"))):(i.error(\"entity not found:\"+e),e)}function u(t){var n=e.substring(v,t).replace(/&#?\\w+;/g,o);h&&a(v),r.characters(n,0,t-v),v=t}function a(t,n){while(t>=l&&(n=c.exec(e)))f=n.index,l=f+n[0].length,h.lineNumber++;h.columnNumber=t-f+1}var f=0,l=0,c=/.+(?:\\r\\n?|\\n)|.*$/g,h=r.locator,p=[{currentNSMap:t}],d={},v=0;for(;;){var E=e.indexOf(\"<\",v);if(E<0){if(!e.substr(v).match(/^\\s*$/)){var N=r.document,C=N.createTextNode(e.substr(v));N.appendChild(C),r.currentElement=C}return}E>v&&u(E);switch(e.charAt(E+1)){case\"/\":var k=e.indexOf(\">\",E+3),L=e.substring(E+2,k),A;if(!(p.length>1)){i.fatalError(\"end tag name not found for: \"+L);break}A=p.pop();var O=A.localNSMap;A.tagName!=L&&i.fatalError(\"end tag name: \"+L+\" does not match the current start tagName: \"+A.tagName),r.endElement(A.uri,A.localName,L);if(O)for(var M in O)r.endPrefixMapping(M);k++;break;case\"?\":h&&a(E),k=x(e,E,r);break;case\"!\":h&&a(E),k=S(e,E,r,i);break;default:try{h&&a(E);var _=new T,k=g(e,E,_,o,i),D=_.length;if(D&&h){var P=m(h,{});for(var E=0;E<D;E++){var H=_[E];a(H.offset),H.offset=m(h,{})}m(P,h)}!_.closed&&w(e,k,_.tagName,d)&&(_.closed=!0,n.nbsp||i.warning(\"unclosed xml attribute\")),y(_,r,p),_.uri===\"http://www.w3.org/1999/xhtml\"&&!_.closed?k=b(e,k,_.tagName,o,r):k++}catch(B){i.error(\"element parse error: \"+B),k=-1}}k<0?u(E+1):v=k}}function m(e,t){return t.lineNumber=e.lineNumber,t.columnNumber=e.columnNumber,t}function g(e,t,n,r,i){var s,d,v=++t,m=o;for(;;){var g=e.charAt(v);switch(g){case\"=\":if(m===u)s=e.slice(t,v),m=f;else{if(m!==a)throw new Error(\"attribute equal must after attrName\");m=f}break;case\"'\":case'\"':if(m===f){t=v+1,v=e.indexOf(g,t);if(!(v>0))throw new Error(\"attribute value no end '\"+g+\"' match\");d=e.slice(t,v).replace(/&#?\\w+;/g,r),n.add(s,d,t-1),m=c}else{if(m!=l)throw new Error('attribute value must after \"=\"');d=e.slice(t,v).replace(/&#?\\w+;/g,r),n.add(s,d,t),i.warning('attribute \"'+s+'\" missed start quot('+g+\")!!\"),t=v+1,m=c}break;case\"/\":switch(m){case o:n.setTagName(e.slice(t,v));case c:case h:case p:m=p,n.closed=!0;case l:case u:case a:break;default:throw new Error(\"attribute invalid close char('/')\")}break;case\"\":i.error(\"unexpected end of input\");case\">\":switch(m){case o:n.setTagName(e.slice(t,v));case c:case h:case p:break;case l:case u:d=e.slice(t,v),d.slice(-1)===\"/\"&&(n.closed=!0,d=d.slice(0,-1));case a:m===a&&(d=s),m==l?(i.warning('attribute \"'+d+'\" missed quot(\")!!'),n.add(s,d.replace(/&#?\\w+;/g,r),t)):(i.warning('attribute \"'+d+'\" missed value!! \"'+d+'\" instead!!'),n.add(d,d,t));break;case f:throw new Error(\"attribute value missed!!\")}return v;case\"\\u0080\":g=\" \";default:if(g<=\" \")switch(m){case o:n.setTagName(e.slice(t,v)),m=h;break;case u:s=e.slice(t,v),m=a;break;case l:var d=e.slice(t,v).replace(/&#?\\w+;/g,r);i.warning('attribute \"'+d+'\" missed quot(\")!!'),n.add(s,d,t);case c:m=h}else switch(m){case a:i.warning('attribute \"'+s+'\" missed value!! \"'+s+'\" instead!!'),n.add(s,s,t),t=v,m=u;break;case c:i.warning('attribute space is required\"'+s+'\"!!');case h:m=u,t=v;break;case f:m=l,t=v;break;case p:throw new Error(\"elements closed character '/' and '>' must be connected to\")}}v++}}function y(e,t,n){var r=e.tagName,i=null,s=n[n.length-1].currentNSMap,o=e.length;while(o--){var u=e[o],a=u.qName,f=u.value,l=a.indexOf(\":\");if(l>0)var c=u.prefix=a.slice(0,l),h=a.slice(l+1),p=c===\"xmlns\"&&h;else h=a,c=null,p=a===\"xmlns\"&&\"\";u.localName=h,p!==!1&&(i==null&&(i={},E(s,s={})),s[p]=i[p]=f,u.uri=\"http://www.w3.org/2000/xmlns/\",t.startPrefixMapping(p,f))}var o=e.length;while(o--){u=e[o];var c=u.prefix;c&&(c===\"xml\"&&(u.uri=\"http://www.w3.org/XML/1998/namespace\"),c!==\"xmlns\"&&(u.uri=s[c]))}var l=r.indexOf(\":\");l>0?(c=e.prefix=r.slice(0,l),h=e.localName=r.slice(l+1)):(c=null,h=e.localName=r);var d=e.uri=s[c||\"\"];t.startElement(d,h,r,e);if(e.closed){t.endElement(d,h,r);if(i)for(c in i)t.endPrefixMapping(c)}else e.currentNSMap=s,e.localNSMap=i,n.push(e)}function b(e,t,n,r,i){if(/^(?:script|textarea)$/i.test(n)){var s=e.indexOf(\"</\"+n+\">\",t),o=e.substring(t+1,s);if(/[&<]/.test(o))return/^script$/i.test(n)?(i.characters(o,0,o.length),s):(o=o.replace(/&#?\\w+;/g,r),i.characters(o,0,o.length),s)}return t+1}function w(e,t,n,r){var i=r[n];return i==null&&(i=r[n]=e.lastIndexOf(\"</\"+n+\">\")),i<t}function E(e,t){for(var n in e)t[n]=e[n]}function S(e,t,n,r){var i=e.charAt(t+2);switch(i){case\"-\":if(e.charAt(t+3)===\"-\"){var s=e.indexOf(\"-->\",t+4);return s>t?(n.comment(e,t+4,s-t-4),s+3):(r.error(\"Unclosed comment\"),-1)}return-1;default:if(e.substr(t+3,6)==\"CDATA[\"){var s=e.indexOf(\"]]>\",t+9);return n.startCDATA(),n.characters(e,t+9,s-t-9),n.endCDATA(),s+3}var o=C(e,t),u=o.length;if(u>1&&/!doctype/i.test(o[0][0])){var a=o[1][0],f=u>3&&/^public$/i.test(o[2][0])&&o[3][0],l=u>4&&o[4][0],c=o[u-1];return n.startDTD(a,f&&f.replace(/^(['\"])(.*?)\\1$/,\"$2\"),l&&l.replace(/^(['\"])(.*?)\\1$/,\"$2\")),n.endDTD(),c.index+c[0].length}}return-1}function x(e,t,n){var r=e.indexOf(\"?>\",t);if(r){var i=e.substring(t,r).match(/^<\\?(\\S*)\\s*([\\s\\S]*?)\\s*$/);if(i){var s=i[0].length;return n.processingInstruction(i[1],i[2]),r+2}return-1}return-1}function T(e){}function N(e,t){return e.__proto__=t,e}function C(e,t){var n,r=[],i=/'[^']+'|\"[^\"]+\"|[^\\s<>\\/=]+=?|(\\/?\\s*>|<)/g;i.lastIndex=t,i.exec(e);while(n=i.exec(e)){r.push(n);if(n[1])return r}}var r=/[A-Z_a-z\\xC0-\\xD6\\xD8-\\xF6\\u00F8-\\u02FF\\u0370-\\u037D\\u037F-\\u1FFF\\u200C-\\u200D\\u2070-\\u218F\\u2C00-\\u2FEF\\u3001-\\uD7FF\\uF900-\\uFDCF\\uFDF0-\\uFFFD]/,i=new RegExp(\"[\\\\-\\\\.0-9\"+r.source.slice(1,-1)+\"\\u00b7\\u0300-\\u036f\\\\ux203F-\\u2040]\"),s=new RegExp(\"^\"+r.source+i.source+\"*(?::\"+r.source+i.source+\"*)?$\"),o=0,u=1,a=2,f=3,l=4,c=5,h=6,p=7;return d.prototype={parse:function(e,t,n){var r=this.domBuilder;r.startDocument(),E(t,t={}),v(e,t,n,r,this.errorHandler),r.endDocument()}},T.prototype={setTagName:function(e){if(!s.test(e))throw new Error(\"invalid tagName:\"+e);this.tagName=e},add:function(e,t,n){if(!s.test(e))throw new Error(\"invalid attribute:\"+e);this[this.length++]={qName:e,value:t,offset:n}},length:0,getLocalName:function(e){return this[e].localName},getOffset:function(e){return this[e].offset},getQName:function(e){return this[e].qName},getURI:function(e){return this[e].uri},getValue:function(e){return this[e].value}},N({},N.prototype)instanceof N||(N=function(e,t){function n(){}n.prototype=t,n=new n;for(t in e)n[t]=e[t];return n}),d}),define(\"ace/mode/xml/dom\",[\"require\",\"exports\",\"module\"],function(e,t,n){function r(e,t){for(var n in e)t[n]=e[n]}function i(e,t){var n=e.prototype;if(Object.create){var i=Object.create(t.prototype);n.__proto__=i}if(!(n instanceof t)){function s(){}s.prototype=t.prototype,s=new s,r(n,s),e.prototype=n=s}n.constructor!=e&&(typeof e!=\"function\"&&console.error(\"unknow Class:\"+e),n.constructor=e)}function B(e,t){if(t instanceof Error)var n=t;else n=this,Error.call(this,w[e]),this.message=w[e],Error.captureStackTrace&&Error.captureStackTrace(this,B);return n.code=e,t&&(this.message=this.message+\": \"+t),n}function j(){}function F(e,t){this._node=e,this._refresh=t,I(this)}function I(e){var t=e._node._inc||e._node.ownerDocument._inc;if(e._inc!=t){var n=e._refresh(e._node);gt(e,\"length\",n.length),r(n,e),e._inc=t}}function q(){}function R(e,t){var n=e.length;while(n--)if(e[n]===t)return n}function U(e,t,n,r){r?t[R(t,r)]=n:t[t.length++]=n;if(e){n.ownerElement=e;var i=e.ownerDocument;i&&(r&&Q(i,e,r),K(i,e,n))}}function z(e,t,n){var r=R(t,n);if(!(r>=0))throw B(L,new Error);var i=t.length-1;while(r<i)t[r]=t[++r];t.length=i;if(e){var s=e.ownerDocument;s&&(Q(s,e,n),n.ownerElement=null)}}function W(e){this._features={};if(e)for(var t in e)this._features=e[t]}function X(){}function V(e){return e==\"<\"&&\"&lt;\"||e==\">\"&&\"&gt;\"||e==\"&\"&&\"&amp;\"||e=='\"'&&\"&quot;\"||\"&#\"+e.charCodeAt()+\";\"}function $(e,t){if(t(e))return!0;if(e=e.firstChild)do if($(e,t))return!0;while(e=e.nextSibling)}function J(){}function K(e,t,n){e&&e._inc++;var r=n.namespaceURI;r==\"http://www.w3.org/2000/xmlns/\"&&(t._nsMap[n.prefix?n.localName:\"\"]=n.value)}function Q(e,t,n,r){e&&e._inc++;var i=n.namespaceURI;i==\"http://www.w3.org/2000/xmlns/\"&&delete t._nsMap[n.prefix?n.localName:\"\"]}function G(e,t,n){if(e&&e._inc){e._inc++;var r=t.childNodes;if(n)r[r.length++]=n;else{var i=t.firstChild,s=0;while(i)r[s++]=i,i=i.nextSibling;r.length=s}}}function Y(e,t){var n=t.previousSibling,r=t.nextSibling;return n?n.nextSibling=r:e.firstChild=r,r?r.previousSibling=n:e.lastChild=n,G(e.ownerDocument,e),t}function Z(e,t,n){var r=t.parentNode;r&&r.removeChild(t);if(t.nodeType===g){var i=t.firstChild;if(i==null)return t;var s=t.lastChild}else i=s=t;var o=n?n.previousSibling:e.lastChild;i.previousSibling=o,s.nextSibling=n,o?o.nextSibling=i:e.firstChild=i,n==null?e.lastChild=s:n.previousSibling=s;do i.parentNode=e;while(i!==s&&(i=i.nextSibling));return G(e.ownerDocument||e,e),t.nodeType==g&&(t.firstChild=t.lastChild=null),t}function et(e,t){var n=t.parentNode;if(n){var r=e.lastChild;n.removeChild(t);var r=e.lastChild}var r=e.lastChild;return t.parentNode=e,t.previousSibling=r,t.nextSibling=null,r?r.nextSibling=t:e.firstChild=t,e.lastChild=t,G(e.ownerDocument,e,t),t}function tt(){this._nsMap={}}function nt(){}function rt(){}function it(){}function st(){}function ot(){}function ut(){}function at(){}function ft(){}function lt(){}function ct(){}function ht(){}function pt(){}function dt(e,t){switch(e.nodeType){case u:var n=e.attributes,r=n.length,i=e.firstChild,o=e.tagName,h=s===e.namespaceURI;t.push(\"<\",o);for(var y=0;y<r;y++)dt(n.item(y),t,h);if(i||h&&!/^(?:meta|link|img|br|hr|input|button)$/i.test(o)){t.push(\">\");if(h&&/^script$/i.test(o))i&&t.push(i.data);else while(i)dt(i,t),i=i.nextSibling;t.push(\"</\",o,\">\")}else t.push(\"/>\");return;case v:case g:var i=e.firstChild;while(i)dt(i,t),i=i.nextSibling;return;case a:return t.push(\" \",e.name,'=\"',e.value.replace(/[<&\"]/g,V),'\"');case f:return t.push(e.data.replace(/[<&]/g,V));case l:return t.push(\"<![CDATA[\",e.data,\"]]>\");case d:return t.push(\"<!--\",e.data,\"-->\");case m:var b=e.publicId,w=e.systemId;t.push(\"<!DOCTYPE \",e.name);if(b)t.push(' PUBLIC \"',b),w&&w!=\".\"&&t.push('\" \"',w),t.push('\">');else if(w&&w!=\".\")t.push(' SYSTEM \"',w,'\">');else{var E=e.internalSubset;E&&t.push(\" [\",E,\"]\"),t.push(\">\")}return;case p:return t.push(\"<?\",e.target,\" \",e.data,\"?>\");case c:return t.push(\"&\",e.nodeName,\";\");default:t.push(\"??\",e.nodeName)}}function vt(e,t,n){var r;switch(t.nodeType){case u:r=t.cloneNode(!1),r.ownerDocument=e;case g:break;case a:n=!0}r||(r=t.cloneNode(!1)),r.ownerDocument=e,r.parentNode=null;if(n){var i=t.firstChild;while(i)r.appendChild(vt(e,i,n)),i=i.nextSibling}return r}function mt(e,t,n){var r=new t.constructor;for(var i in t){var s=t[i];typeof s!=\"object\"&&s!=r[i]&&(r[i]=s)}t.childNodes&&(r.childNodes=new j),r.ownerDocument=e;switch(r.nodeType){case u:var o=t.attributes,f=r.attributes=new q,l=o.length;f._ownerElement=r;for(var c=0;c<l;c++)r.setAttributeNode(mt(e,o.item(c),!0));break;case a:n=!0}if(n){var h=t.firstChild;while(h)r.appendChild(mt(e,h,n)),h=h.nextSibling}return r}function gt(e,t,n){e[t]=n}var s=\"http://www.w3.org/1999/xhtml\",o={},u=o.ELEMENT_NODE=1,a=o.ATTRIBUTE_NODE=2,f=o.TEXT_NODE=3,l=o.CDATA_SECTION_NODE=4,c=o.ENTITY_REFERENCE_NODE=5,h=o.ENTITY_NODE=6,p=o.PROCESSING_INSTRUCTION_NODE=7,d=o.COMMENT_NODE=8,v=o.DOCUMENT_NODE=9,m=o.DOCUMENT_TYPE_NODE=10,g=o.DOCUMENT_FRAGMENT_NODE=11,y=o.NOTATION_NODE=12,b={},w={},E=b.INDEX_SIZE_ERR=(w[1]=\"Index size error\",1),S=b.DOMSTRING_SIZE_ERR=(w[2]=\"DOMString size error\",2),x=b.HIERARCHY_REQUEST_ERR=(w[3]=\"Hierarchy request error\",3),T=b.WRONG_DOCUMENT_ERR=(w[4]=\"Wrong document\",4),N=b.INVALID_CHARACTER_ERR=(w[5]=\"Invalid character\",5),C=b.NO_DATA_ALLOWED_ERR=(w[6]=\"No data allowed\",6),k=b.NO_MODIFICATION_ALLOWED_ERR=(w[7]=\"No modification allowed\",7),L=b.NOT_FOUND_ERR=(w[8]=\"Not found\",8),A=b.NOT_SUPPORTED_ERR=(w[9]=\"Not supported\",9),O=b.INUSE_ATTRIBUTE_ERR=(w[10]=\"Attribute in use\",10),M=b.INVALID_STATE_ERR=(w[11]=\"Invalid state\",11),_=b.SYNTAX_ERR=(w[12]=\"Syntax error\",12),D=b.INVALID_MODIFICATION_ERR=(w[13]=\"Invalid modification\",13),P=b.NAMESPACE_ERR=(w[14]=\"Invalid namespace\",14),H=b.INVALID_ACCESS_ERR=(w[15]=\"Invalid access\",15);B.prototype=Error.prototype,r(b,B),j.prototype={length:0,item:function(e){return this[e]||null}},F.prototype.item=function(e){return I(this),this[e]},i(F,j),q.prototype={length:0,item:j.prototype.item,getNamedItem:function(e){var t=this.length;while(t--){var n=this[t];if(n.nodeName==e)return n}},setNamedItem:function(e){var t=e.ownerElement;if(t&&t!=this._ownerElement)throw new B(O);var n=this.getNamedItem(e.nodeName);return U(this._ownerElement,this,e,n),n},setNamedItemNS:function(e){var t=e.ownerElement,n;if(t&&t!=this._ownerElement)throw new B(O);return n=this.getNamedItemNS(e.namespaceURI,e.localName),U(this._ownerElement,this,e,n),n},removeNamedItem:function(e){var t=this.getNamedItem(e);return z(this._ownerElement,this,t),t},removeNamedItemNS:function(e,t){var n=this.getNamedItemNS(e,t);return z(this._ownerElement,this,n),n},getNamedItemNS:function(e,t){var n=this.length;while(n--){var r=this[n];if(r.localName==t&&r.namespaceURI==e)return r}return null}},W.prototype={hasFeature:function(e,t){var n=this._features[e.toLowerCase()];return n&&(!t||t in n)?!0:!1},createDocument:function(e,t,n){var r=new J;r.implementation=this,r.childNodes=new j,r.doctype=n,n&&r.appendChild(n);if(t){var i=r.createElementNS(e,t);r.appendChild(i)}return r},createDocumentType:function(e,t,n){var r=new ut;return r.name=e,r.nodeName=e,r.publicId=t,r.systemId=n,r}},X.prototype={firstChild:null,lastChild:null,previousSibling:null,nextSibling:null,attributes:null,parentNode:null,childNodes:null,ownerDocument:null,nodeValue:null,namespaceURI:null,prefix:null,localName:null,insertBefore:function(e,t){return Z(this,e,t)},replaceChild:function(e,t){this.insertBefore(e,t),t&&this.removeChild(t)},removeChild:function(e){return Y(this,e)},appendChild:function(e){return this.insertBefore(e,null)},hasChildNodes:function(){return this.firstChild!=null},cloneNode:function(e){return mt(this.ownerDocument||this,this,e)},normalize:function(){var e=this.firstChild;while(e){var t=e.nextSibling;t&&t.nodeType==f&&e.nodeType==f?(this.removeChild(t),e.appendData(t.data)):(e.normalize(),e=t)}},isSupported:function(e,t){return this.ownerDocument.implementation.hasFeature(e,t)},hasAttributes:function(){return this.attributes.length>0},lookupPrefix:function(e){var t=this;while(t){var n=t._nsMap;if(n)for(var r in n)if(n[r]==e)return r;t=t.nodeType==2?t.ownerDocument:t.parentNode}return null},lookupNamespaceURI:function(e){var t=this;while(t){var n=t._nsMap;if(n&&e in n)return n[e];t=t.nodeType==2?t.ownerDocument:t.parentNode}return null},isDefaultNamespace:function(e){var t=this.lookupPrefix(e);return t==null}},r(o,X),r(o,X.prototype),J.prototype={nodeName:\"#document\",nodeType:v,doctype:null,documentElement:null,_inc:1,insertBefore:function(e,t){if(e.nodeType==g){var n=e.firstChild;while(n){var r=n.nextSibling;this.insertBefore(n,t),n=r}return e}return this.documentElement==null&&e.nodeType==1&&(this.documentElement=e),Z(this,e,t),e.ownerDocument=this,e},removeChild:function(e){return this.documentElement==e&&(this.documentElement=null),Y(this,e)},importNode:function(e,t){return vt(this,e,t)},getElementById:function(e){var t=null;return $(this.documentElement,function(n){if(n.nodeType==1&&n.getAttribute(\"id\")==e)return t=n,!0}),t},createElement:function(e){var t=new tt;t.ownerDocument=this,t.nodeName=e,t.tagName=e,t.childNodes=new j;var n=t.attributes=new q;return n._ownerElement=t,t},createDocumentFragment:function(){var e=new ct;return e.ownerDocument=this,e.childNodes=new j,e},createTextNode:function(e){var t=new it;return t.ownerDocument=this,t.appendData(e),t},createComment:function(e){var t=new st;return t.ownerDocument=this,t.appendData(e),t},createCDATASection:function(e){var t=new ot;return t.ownerDocument=this,t.appendData(e),t},createProcessingInstruction:function(e,t){var n=new ht;return n.ownerDocument=this,n.tagName=n.target=e,n.nodeValue=n.data=t,n},createAttribute:function(e){var t=new nt;return t.ownerDocument=this,t.name=e,t.nodeName=e,t.localName=e,t.specified=!0,t},createEntityReference:function(e){var t=new lt;return t.ownerDocument=this,t.nodeName=e,t},createElementNS:function(e,t){var n=new tt,r=t.split(\":\"),i=n.attributes=new q;return n.childNodes=new j,n.ownerDocument=this,n.nodeName=t,n.tagName=t,n.namespaceURI=e,r.length==2?(n.prefix=r[0],n.localName=r[1]):n.localName=t,i._ownerElement=n,n},createAttributeNS:function(e,t){var n=new nt,r=t.split(\":\");return n.ownerDocument=this,n.nodeName=t,n.name=t,n.namespaceURI=e,n.specified=!0,r.length==2?(n.prefix=r[0],n.localName=r[1]):n.localName=t,n}},i(J,X),tt.prototype={nodeType:u,hasAttribute:function(e){return this.getAttributeNode(e)!=null},getAttribute:function(e){var t=this.getAttributeNode(e);return t&&t.value||\"\"},getAttributeNode:function(e){return this.attributes.getNamedItem(e)},setAttribute:function(e,t){var n=this.ownerDocument.createAttribute(e);n.value=n.nodeValue=\"\"+t,this.setAttributeNode(n)},removeAttribute:function(e){var t=this.getAttributeNode(e);t&&this.removeAttributeNode(t)},appendChild:function(e){return e.nodeType===g?this.insertBefore(e,null):et(this,e)},setAttributeNode:function(e){return this.attributes.setNamedItem(e)},setAttributeNodeNS:function(e){return this.attributes.setNamedItemNS(e)},removeAttributeNode:function(e){return this.attributes.removeNamedItem(e.nodeName)},removeAttributeNS:function(e,t){var n=this.getAttributeNodeNS(e,t);n&&this.removeAttributeNode(n)},hasAttributeNS:function(e,t){return this.getAttributeNodeNS(e,t)!=null},getAttributeNS:function(e,t){var n=this.getAttributeNodeNS(e,t);return n&&n.value||\"\"},setAttributeNS:function(e,t,n){var r=this.ownerDocument.createAttributeNS(e,t);r.value=r.nodeValue=\"\"+n,this.setAttributeNode(r)},getAttributeNodeNS:function(e,t){return this.attributes.getNamedItemNS(e,t)},getElementsByTagName:function(e){return new F(this,function(t){var n=[];return $(t,function(r){r!==t&&r.nodeType==u&&(e===\"*\"||r.tagName==e)&&n.push(r)}),n})},getElementsByTagNameNS:function(e,t){return new F(this,function(n){var r=[];return $(n,function(i){i!==n&&i.nodeType===u&&(e===\"*\"||i.namespaceURI===e)&&(t===\"*\"||i.localName==t)&&r.push(i)}),r})}},J.prototype.getElementsByTagName=tt.prototype.getElementsByTagName,J.prototype.getElementsByTagNameNS=tt.prototype.getElementsByTagNameNS,i(tt,X),nt.prototype.nodeType=a,i(nt,X),rt.prototype={data:\"\",substringData:function(e,t){return this.data.substring(e,e+t)},appendData:function(e){e=this.data+e,this.nodeValue=this.data=e,this.length=e.length},insertData:function(e,t){this.replaceData(e,0,t)},appendChild:function(e){throw new Error(w[3])},deleteData:function(e,t){this.replaceData(e,t,\"\")},replaceData:function(e,t,n){var r=this.data.substring(0,e),i=this.data.substring(e+t);n=r+n+i,this.nodeValue=this.data=n,this.length=n.length}},i(rt,X),it.prototype={nodeName:\"#text\",nodeType:f,splitText:function(e){var t=this.data,n=t.substring(e);t=t.substring(0,e),this.data=this.nodeValue=t,this.length=t.length;var r=this.ownerDocument.createTextNode(n);return this.parentNode&&this.parentNode.insertBefore(r,this.nextSibling),r}},i(it,rt),st.prototype={nodeName:\"#comment\",nodeType:d},i(st,rt),ot.prototype={nodeName:\"#cdata-section\",nodeType:l},i(ot,rt),ut.prototype.nodeType=m,i(ut,X),at.prototype.nodeType=y,i(at,X),ft.prototype.nodeType=h,i(ft,X),lt.prototype.nodeType=c,i(lt,X),ct.prototype.nodeName=\"#document-fragment\",ct.prototype.nodeType=g,i(ct,X),ht.prototype.nodeType=p,i(ht,X),pt.prototype.serializeToString=function(e){var t=[];return dt(e,t),t.join(\"\")},X.prototype.toString=function(){return pt.prototype.serializeToString(this)};try{if(Object.defineProperty){Object.defineProperty(F.prototype,\"length\",{get:function(){return I(this),this.$$length}}),Object.defineProperty(X.prototype,\"textContent\",{get:function(){return yt(this)},set:function(e){switch(this.nodeType){case 1:case 11:while(this.firstChild)this.removeChild(this.firstChild);(e||String(e))&&this.appendChild(this.ownerDocument.createTextNode(e));break;default:this.data=e,this.value=value,this.nodeValue=e}}});function yt(e){switch(e.nodeType){case 1:case 11:var t=[];e=e.firstChild;while(e)e.nodeType!==7&&e.nodeType!==8&&t.push(yt(e)),e=e.nextSibling;return t.join(\"\");default:return e.nodeValue}}gt=function(e,t,n){e[\"$$\"+t]=n}}}catch(bt){}return W}),define(\"ace/mode/xml/dom-parser\",[\"require\",\"exports\",\"module\",\"ace/mode/xml/sax\",\"ace/mode/xml/dom\"],function(e,t,n){\"use strict\";function s(e){this.options=e||{locator:{}}}function o(e,t,n){function s(t){var s=e[t];if(!s)if(i)s=e.length==2?function(n){e(t,n)}:e;else{var o=arguments.length;while(--o)if(s=e[arguments[o]])break}r[t]=s&&function(e){s(e+f(n),e,n)}||function(){}}if(!e){if(t instanceof u)return t;e=t}var r={},i=e instanceof Function;return n=n||{},s(\"warning\",\"warn\"),s(\"error\",\"warn\",\"warning\"),s(\"fatalError\",\"warn\",\"warning\",\"error\"),r}function u(){this.cdata=!1}function a(e,t){t.lineNumber=e.lineNumber,t.columnNumber=e.columnNumber}function f(e){if(e)return\"\\n@\"+(e.systemId||\"\")+\"#[line:\"+e.lineNumber+\",col:\"+e.columnNumber+\"]\"}function l(e,t,n){return typeof e==\"string\"?e.substr(t,n):e.length>=t+n||t?new java.lang.String(e,t,n)+\"\":e}function c(e,t){e.currentElement?e.currentElement.appendChild(t):e.document.appendChild(t)}var r=e(\"./sax\"),i=e(\"./dom\");return s.prototype.parseFromString=function(e,t){var n=this.options,i=new r,s=n.domBuilder||new u,a=n.errorHandler,f=n.locator,l=n.xmlns||{},c={lt:\"<\",gt:\">\",amp:\"&\",quot:'\"',apos:\"'\"};return f&&s.setDocumentLocator(f),i.errorHandler=o(a,s,f),i.domBuilder=n.domBuilder||s,/\\/x?html?$/.test(t)&&(c.nbsp=\"\\u00a0\",c.copy=\"\\u00a9\",l[\"\"]=\"http://www.w3.org/1999/xhtml\"),e?i.parse(e,l,c):i.errorHandler.error(\"invalid document source\"),s.document},u.prototype={startDocument:function(){this.document=(new i).createDocument(null,null,null),this.locator&&(this.document.documentURI=this.locator.systemId)},startElement:function(e,t,n,r){var i=this.document,s=i.createElementNS(e,n||t),o=r.length;c(this,s),this.currentElement=s,this.locator&&a(this.locator,s);for(var u=0;u<o;u++){var e=r.getURI(u),f=r.getValue(u),n=r.getQName(u),l=i.createAttributeNS(e,n);l.getOffset&&a(l.getOffset(1),l),l.value=l.nodeValue=f,s.setAttributeNode(l)}},endElement:function(e,t,n){var r=this.currentElement,i=r.tagName;this.currentElement=r.parentNode},startPrefixMapping:function(e,t){},endPrefixMapping:function(e){},processingInstruction:function(e,t){var n=this.document.createProcessingInstruction(e,t);this.locator&&a(this.locator,n),c(this,n)},ignorableWhitespace:function(e,t,n){},characters:function(e,t,n){e=l.apply(this,arguments);if(this.currentElement&&e){if(this.cdata){var r=this.document.createCDATASection(e);this.currentElement.appendChild(r)}else{var r=this.document.createTextNode(e);this.currentElement.appendChild(r)}this.locator&&a(this.locator,r)}},skippedEntity:function(e){},endDocument:function(){this.document.normalize()},setDocumentLocator:function(e){if(this.locator=e)e.lineNumber=0},comment:function(e,t,n){e=l.apply(this,arguments);var r=this.document.createComment(e);this.locator&&a(this.locator,r),c(this,r)},startCDATA:function(){this.cdata=!0},endCDATA:function(){this.cdata=!1},startDTD:function(e,t,n){var r=this.document.implementation;if(r&&r.createDocumentType){var i=r.createDocumentType(e,t,n);this.locator&&a(this.locator,i),c(this,i)}},warning:function(e){console.warn(e,f(this.locator))},error:function(e){console.error(e,f(this.locator))},fatalError:function(e){throw console.error(e,f(this.locator)),e}},\"endDTD,startEntity,endEntity,attributeDecl,elementDecl,externalEntityDecl,internalEntityDecl,resolveEntity,getExternalSubset,notationDecl,unparsedEntityDecl\".replace(/\\w+/g,function(e){u.prototype[e]=function(){return null}}),{DOMParser:s}}),define(\"ace/mode/xml_worker\",[\"require\",\"exports\",\"module\",\"ace/lib/oop\",\"ace/lib/lang\",\"ace/worker/mirror\",\"ace/mode/xml/dom-parser\"],function(e,t,n){\"use strict\";var r=e(\"../lib/oop\"),i=e(\"../lib/lang\"),s=e(\"../worker/mirror\").Mirror,o=e(\"./xml/dom-parser\").DOMParser,u=t.Worker=function(e){s.call(this,e),this.setTimeout(400),this.context=null};r.inherits(u,s),function(){this.setOptions=function(e){this.context=e.context},this.onUpdate=function(){var e=this.doc.getValue();if(!e)return;var t=new o,n=[];t.options.errorHandler={fatalError:function(e,t,r){n.push({row:r.lineNumber,column:r.columnNumber,text:t,type:\"error\"})},error:function(e,t,r){n.push({row:r.lineNumber,column:r.columnNumber,text:t,type:\"error\"})},warning:function(e,t,r){n.push({row:r.lineNumber,column:r.columnNumber,text:t,type:\"warning\"})}},t.parseFromString(e),this.sender.emit(\"error\",n)}}.call(u.prototype)}),define(\"ace/lib/es5-shim\",[\"require\",\"exports\",\"module\"],function(e,t,n){function r(){}function w(e){try{return Object.defineProperty(e,\"sentinel\",{}),\"sentinel\"in e}catch(t){}}function H(e){return e=+e,e!==e?e=0:e!==0&&e!==1/0&&e!==-1/0&&(e=(e>0||-1)*Math.floor(Math.abs(e))),e}function B(e){var t=typeof e;return e===null||t===\"undefined\"||t===\"boolean\"||t===\"number\"||t===\"string\"}function j(e){var t,n,r;if(B(e))return e;n=e.valueOf;if(typeof n==\"function\"){t=n.call(e);if(B(t))return t}r=e.toString;if(typeof r==\"function\"){t=r.call(e);if(B(t))return t}throw new TypeError}Function.prototype.bind||(Function.prototype.bind=function(t){var n=this;if(typeof n!=\"function\")throw new TypeError(\"Function.prototype.bind called on incompatible \"+n);var i=u.call(arguments,1),s=function(){if(this instanceof s){var e=n.apply(this,i.concat(u.call(arguments)));return Object(e)===e?e:this}return n.apply(t,i.concat(u.call(arguments)))};return n.prototype&&(r.prototype=n.prototype,s.prototype=new r,r.prototype=null),s});var i=Function.prototype.call,s=Array.prototype,o=Object.prototype,u=s.slice,a=i.bind(o.toString),f=i.bind(o.hasOwnProperty),l,c,h,p,d;if(d=f(o,\"__defineGetter__\"))l=i.bind(o.__defineGetter__),c=i.bind(o.__defineSetter__),h=i.bind(o.__lookupGetter__),p=i.bind(o.__lookupSetter__);if([1,2].splice(0).length!=2)if(!function(){function e(e){var t=new Array(e+2);return t[0]=t[1]=0,t}var t=[],n;t.splice.apply(t,e(20)),t.splice.apply(t,e(26)),n=t.length,t.splice(5,0,\"XXX\"),n+1==t.length;if(n+1==t.length)return!0}())Array.prototype.splice=function(e,t){var n=this.length;e>0?e>n&&(e=n):e==void 0?e=0:e<0&&(e=Math.max(n+e,0)),e+t<n||(t=n-e);var r=this.slice(e,e+t),i=u.call(arguments,2),s=i.length;if(e===n)s&&this.push.apply(this,i);else{var o=Math.min(t,n-e),a=e+o,f=a+s-o,l=n-a,c=n-o;if(f<a)for(var h=0;h<l;++h)this[f+h]=this[a+h];else if(f>a)for(h=l;h--;)this[f+h]=this[a+h];if(s&&e===c)this.length=c,this.push.apply(this,i);else{this.length=c+s;for(h=0;h<s;++h)this[e+h]=i[h]}}return r};else{var v=Array.prototype.splice;Array.prototype.splice=function(e,t){return arguments.length?v.apply(this,[e===void 0?0:e,t===void 0?this.length-e:t].concat(u.call(arguments,2))):[]}}Array.isArray||(Array.isArray=function(t){return a(t)==\"[object Array]\"});var m=Object(\"a\"),g=m[0]!=\"a\"||!(0 in m);Array.prototype.forEach||(Array.prototype.forEach=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=arguments[1],s=-1,o=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError;while(++s<o)s in r&&t.call(i,r[s],s,n)}),Array.prototype.map||(Array.prototype.map=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=Array(i),o=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var u=0;u<i;u++)u in r&&(s[u]=t.call(o,r[u],u,n));return s}),Array.prototype.filter||(Array.prototype.filter=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=[],o,u=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var f=0;f<i;f++)f in r&&(o=r[f],t.call(u,o,f,n)&&s.push(o));return s}),Array.prototype.every||(Array.prototype.every=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&!t.call(s,r[o],o,n))return!1;return!0}),Array.prototype.some||(Array.prototype.some=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0,s=arguments[1];if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");for(var o=0;o<i;o++)if(o in r&&t.call(s,r[o],o,n))return!0;return!1}),Array.prototype.reduce||(Array.prototype.reduce=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduce of empty array with no initial value\");var s=0,o;if(arguments.length>=2)o=arguments[1];else do{if(s in r){o=r[s++];break}if(++s>=i)throw new TypeError(\"reduce of empty array with no initial value\")}while(!0);for(;s<i;s++)s in r&&(o=t.call(void 0,o,r[s],s,n));return o}),Array.prototype.reduceRight||(Array.prototype.reduceRight=function(t){var n=F(this),r=g&&a(this)==\"[object String]\"?this.split(\"\"):n,i=r.length>>>0;if(a(t)!=\"[object Function]\")throw new TypeError(t+\" is not a function\");if(!i&&arguments.length==1)throw new TypeError(\"reduceRight of empty array with no initial value\");var s,o=i-1;if(arguments.length>=2)s=arguments[1];else do{if(o in r){s=r[o--];break}if(--o<0)throw new TypeError(\"reduceRight of empty array with no initial value\")}while(!0);do o in this&&(s=t.call(void 0,s,r[o],o,n));while(o--);return s});if(!Array.prototype.indexOf||[0,1].indexOf(1,2)!=-1)Array.prototype.indexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=0;arguments.length>1&&(i=H(arguments[1])),i=i>=0?i:Math.max(0,r+i);for(;i<r;i++)if(i in n&&n[i]===t)return i;return-1};if(!Array.prototype.lastIndexOf||[0,1].lastIndexOf(0,-3)!=-1)Array.prototype.lastIndexOf=function(t){var n=g&&a(this)==\"[object String]\"?this.split(\"\"):F(this),r=n.length>>>0;if(!r)return-1;var i=r-1;arguments.length>1&&(i=Math.min(i,H(arguments[1]))),i=i>=0?i:r-Math.abs(i);for(;i>=0;i--)if(i in n&&t===n[i])return i;return-1};Object.getPrototypeOf||(Object.getPrototypeOf=function(t){return t.__proto__||(t.constructor?t.constructor.prototype:o)});if(!Object.getOwnPropertyDescriptor){var y=\"Object.getOwnPropertyDescriptor called on a non-object: \";Object.getOwnPropertyDescriptor=function(t,n){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(y+t);if(!f(t,n))return;var r,i,s;r={enumerable:!0,configurable:!0};if(d){var u=t.__proto__;t.__proto__=o;var i=h(t,n),s=p(t,n);t.__proto__=u;if(i||s)return i&&(r.get=i),s&&(r.set=s),r}return r.value=t[n],r}}Object.getOwnPropertyNames||(Object.getOwnPropertyNames=function(t){return Object.keys(t)});if(!Object.create){var b;Object.prototype.__proto__===null?b=function(){return{__proto__:null}}:b=function(){var e={};for(var t in e)e[t]=null;return e.constructor=e.hasOwnProperty=e.propertyIsEnumerable=e.isPrototypeOf=e.toLocaleString=e.toString=e.valueOf=e.__proto__=null,e},Object.create=function(t,n){var r;if(t===null)r=b();else{if(typeof t!=\"object\")throw new TypeError(\"typeof prototype[\"+typeof t+\"] != 'object'\");var i=function(){};i.prototype=t,r=new i,r.__proto__=t}return n!==void 0&&Object.defineProperties(r,n),r}}if(Object.defineProperty){var E=w({}),S=typeof document==\"undefined\"||w(document.createElement(\"div\"));if(!E||!S)var x=Object.defineProperty}if(!Object.defineProperty||x){var T=\"Property description must be an object: \",N=\"Object.defineProperty called on non-object: \",C=\"getters & setters can not be defined on this javascript engine\";Object.defineProperty=function(t,n,r){if(typeof t!=\"object\"&&typeof t!=\"function\"||t===null)throw new TypeError(N+t);if(typeof r!=\"object\"&&typeof r!=\"function\"||r===null)throw new TypeError(T+r);if(x)try{return x.call(Object,t,n,r)}catch(i){}if(f(r,\"value\"))if(d&&(h(t,n)||p(t,n))){var s=t.__proto__;t.__proto__=o,delete t[n],t[n]=r.value,t.__proto__=s}else t[n]=r.value;else{if(!d)throw new TypeError(C);f(r,\"get\")&&l(t,n,r.get),f(r,\"set\")&&c(t,n,r.set)}return t}}Object.defineProperties||(Object.defineProperties=function(t,n){for(var r in n)f(n,r)&&Object.defineProperty(t,r,n[r]);return t}),Object.seal||(Object.seal=function(t){return t}),Object.freeze||(Object.freeze=function(t){return t});try{Object.freeze(function(){})}catch(k){Object.freeze=function(t){return function(n){return typeof n==\"function\"?n:t(n)}}(Object.freeze)}Object.preventExtensions||(Object.preventExtensions=function(t){return t}),Object.isSealed||(Object.isSealed=function(t){return!1}),Object.isFrozen||(Object.isFrozen=function(t){return!1}),Object.isExtensible||(Object.isExtensible=function(t){if(Object(t)===t)throw new TypeError;var n=\"\";while(f(t,n))n+=\"?\";t[n]=!0;var r=f(t,n);return delete t[n],r});if(!Object.keys){var L=!0,A=[\"toString\",\"toLocaleString\",\"valueOf\",\"hasOwnProperty\",\"isPrototypeOf\",\"propertyIsEnumerable\",\"constructor\"],O=A.length;for(var M in{toString:null})L=!1;Object.keys=function I(e){if(typeof e!=\"object\"&&typeof e!=\"function\"||e===null)throw new TypeError(\"Object.keys called on a non-object\");var I=[];for(var t in e)f(e,t)&&I.push(t);if(L)for(var n=0,r=O;n<r;n++){var i=A[n];f(e,i)&&I.push(i)}return I}}Date.now||(Date.now=function(){return(new Date).getTime()});var _=\"\t\\n\u000b\\f\\r \\u00a0\\u1680\\u180e\\u2000\\u2001\\u2002\\u2003\\u2004\\u2005\\u2006\\u2007\\u2008\\u2009\\u200a\\u202f\\u205f\\u3000\\u2028\\u2029\\ufeff\";if(!String.prototype.trim||_.trim()){_=\"[\"+_+\"]\";var D=new RegExp(\"^\"+_+_+\"*\"),P=new RegExp(_+_+\"*$\");String.prototype.trim=function(){return String(this).replace(D,\"\").replace(P,\"\")}}var F=function(e){if(e==null)throw new TypeError(\"can't convert \"+e+\" to object\");return Object(e)}})"
  },
  {
    "path": "public/themes/pterodactyl/vendor/ansi/ansi_up.js",
    "content": "/*  ansi_up.js\n *  author : Dru Nelson\n *  license : MIT\n *  http://github.com/drudru/ansi_up\n */\n(function (factory) {\n    var v;\n    if (typeof module === \"object\" && typeof module.exports === \"object\") {\n        v = factory(require, exports);\n        if (\"undefined\" !== typeof v) module.exports = v;\n    }\n    else if (\"function\" === typeof define && define.amd) {\n        define([\"require\", \"exports\"], factory);\n    }\n    else {\n        var req, exp = {};\n        v = factory(req, exp);\n        window.AnsiUp = exp.default;\n    }\n})(function (require, exports) {\n\n    \"use strict\";\n    function rgx(tmplObj) {\n        var subst = [];\n        for (var _i = 1; _i < arguments.length; _i++) {\n            subst[_i - 1] = arguments[_i];\n        }\n        var regexText = tmplObj.raw[0];\n        var wsrgx = /^\\s+|\\s+\\n|\\s+#[\\s\\S]+?\\n/gm;\n        var txt2 = regexText.replace(wsrgx, '');\n        return new RegExp(txt2, 'm');\n    }\n    var AnsiUp = (function () {\n        function AnsiUp() {\n            this.VERSION = \"2.0.1\";\n            this.ansi_colors = [\n                [\n                    { rgb: [0, 0, 0], class_name: \"ansi-black\" },\n                    { rgb: [187, 0, 0], class_name: \"ansi-red\" },\n                    { rgb: [0, 187, 0], class_name: \"ansi-green\" },\n                    { rgb: [187, 187, 0], class_name: \"ansi-yellow\" },\n                    { rgb: [0, 0, 187], class_name: \"ansi-blue\" },\n                    { rgb: [187, 0, 187], class_name: \"ansi-magenta\" },\n                    { rgb: [0, 187, 187], class_name: \"ansi-cyan\" },\n                    { rgb: [255, 255, 255], class_name: \"ansi-white\" }\n                ],\n                [\n                    { rgb: [85, 85, 85], class_name: \"ansi-bright-black\" },\n                    { rgb: [255, 85, 85], class_name: \"ansi-bright-red\" },\n                    { rgb: [0, 255, 0], class_name: \"ansi-bright-green\" },\n                    { rgb: [255, 255, 85], class_name: \"ansi-bright-yellow\" },\n                    { rgb: [85, 85, 255], class_name: \"ansi-bright-blue\" },\n                    { rgb: [255, 85, 255], class_name: \"ansi-bright-magenta\" },\n                    { rgb: [85, 255, 255], class_name: \"ansi-bright-cyan\" },\n                    { rgb: [255, 255, 255], class_name: \"ansi-bright-white\" }\n                ]\n            ];\n            this.htmlFormatter = {\n                transform: function (fragment, instance) {\n                    var txt = fragment.text;\n                    if (txt.length === 0)\n                        return txt;\n                    if (instance._escape_for_html)\n                        txt = instance.old_escape_for_html(txt);\n                    if (!fragment.bright && fragment.fg === null && fragment.bg === null)\n                        return txt;\n                    var styles = [];\n                    var classes = [];\n                    var fg = fragment.fg;\n                    var bg = fragment.bg;\n                    if (fg === null && fragment.bright)\n                        fg = instance.ansi_colors[1][7];\n                    if (!instance._use_classes) {\n                        if (fg)\n                            styles.push(\"color:rgb(\" + fg.rgb.join(',') + \")\");\n                        if (bg)\n                            styles.push(\"background-color:rgb(\" + bg.rgb + \")\");\n                    }\n                    else {\n                        if (fg) {\n                            if (fg.class_name !== 'truecolor') {\n                                classes.push(fg.class_name + \"-fg\");\n                            }\n                            else {\n                                styles.push(\"color:rgb(\" + fg.rgb.join(',') + \")\");\n                            }\n                        }\n                        if (bg) {\n                            if (bg.class_name !== 'truecolor') {\n                                classes.push(bg.class_name + \"-bg\");\n                            }\n                            else {\n                                styles.push(\"background-color:rgb(\" + bg.rgb.join(',') + \")\");\n                            }\n                        }\n                    }\n                    var class_string = '';\n                    var style_string = '';\n                    if (classes.length)\n                        class_string = \" class=\\\"\" + classes.join(' ') + \"\\\"\";\n                    if (styles.length)\n                        style_string = \" style=\\\"\" + styles.join(';') + \"\\\"\";\n                    return \"<span\" + class_string + style_string + \">\" + txt + \"</span>\";\n                },\n                compose: function (segments, instance) {\n                    return segments.join(\"\");\n                }\n            };\n            this.textFormatter = {\n                transform: function (fragment, instance) {\n                    return fragment.text;\n                },\n                compose: function (segments, instance) {\n                    return segments.join(\"\");\n                }\n            };\n            this.setup_256_palette();\n            this._use_classes = false;\n            this._escape_for_html = true;\n            this.bright = false;\n            this.fg = this.bg = null;\n            this._buffer = '';\n        }\n        Object.defineProperty(AnsiUp.prototype, \"use_classes\", {\n            get: function () {\n                return this._use_classes;\n            },\n            set: function (arg) {\n                this._use_classes = arg;\n            },\n            enumerable: true,\n            configurable: true\n        });\n        Object.defineProperty(AnsiUp.prototype, \"escape_for_html\", {\n            get: function () {\n                return this._escape_for_html;\n            },\n            set: function (arg) {\n                this._escape_for_html = arg;\n            },\n            enumerable: true,\n            configurable: true\n        });\n        AnsiUp.prototype.setup_256_palette = function () {\n            var _this = this;\n            this.palette_256 = [];\n            this.ansi_colors.forEach(function (palette) {\n                palette.forEach(function (rec) {\n                    _this.palette_256.push(rec);\n                });\n            });\n            var levels = [0, 95, 135, 175, 215, 255];\n            for (var r = 0; r < 6; ++r) {\n                for (var g = 0; g < 6; ++g) {\n                    for (var b = 0; b < 6; ++b) {\n                        var col = { rgb: [levels[r], levels[g], levels[b]], class_name: 'truecolor' };\n                        this.palette_256.push(col);\n                    }\n                }\n            }\n            var grey_level = 8;\n            for (var i = 0; i < 24; ++i, grey_level += 10) {\n                var gry = { rgb: [grey_level, grey_level, grey_level], class_name: 'truecolor' };\n                this.palette_256.push(gry);\n            }\n        };\n        AnsiUp.prototype.old_escape_for_html = function (txt) {\n            return txt.replace(/[&<>]/gm, function (str) {\n                if (str === \"&\")\n                    return \"&amp;\";\n                if (str === \"<\")\n                    return \"&lt;\";\n                if (str === \">\")\n                    return \"&gt;\";\n            });\n        };\n        AnsiUp.prototype.old_linkify = function (txt) {\n            return txt.replace(/(https?:\\/\\/[^\\s]+)/gm, function (str) {\n                return \"<a href=\\\"\" + str + \"\\\">\" + str + \"</a>\";\n            });\n        };\n        AnsiUp.prototype.detect_incomplete_ansi = function (txt) {\n            return !(/.*?[\\x40-\\x7e]/.test(txt));\n        };\n        AnsiUp.prototype.detect_incomplete_link = function (txt) {\n            var found = false;\n            for (var i = txt.length - 1; i > 0; i--) {\n                if (/\\s|\\x1B/.test(txt[i])) {\n                    found = true;\n                    break;\n                }\n            }\n            if (!found) {\n                if (/(https?:\\/\\/[^\\s]+)/.test(txt))\n                    return 0;\n                else\n                    return -1;\n            }\n            var prefix = txt.substr(i + 1, 4);\n            if (prefix.length === 0)\n                return -1;\n            if (\"http\".indexOf(prefix) === 0)\n                return (i + 1);\n        };\n        AnsiUp.prototype.ansi_to = function (txt, formatter) {\n            var pkt = this._buffer + txt;\n            this._buffer = '';\n            var raw_text_pkts = pkt.split(/\\x1B\\[/);\n            if (raw_text_pkts.length === 1)\n                raw_text_pkts.push('');\n            this.handle_incomplete_sequences(raw_text_pkts);\n            var first_chunk = this.with_state(raw_text_pkts.shift());\n            var blocks = new Array(raw_text_pkts.length);\n            for (var i = 0, len = raw_text_pkts.length; i < len; ++i) {\n                blocks[i] = (formatter.transform(this.process_ansi(raw_text_pkts[i]), this));\n            }\n            if (first_chunk.text.length > 0)\n                blocks.unshift(formatter.transform(first_chunk, this));\n            return formatter.compose(blocks, this);\n        };\n        AnsiUp.prototype.ansi_to_html = function (txt) {\n            return this.ansi_to(txt, this.htmlFormatter);\n        };\n        AnsiUp.prototype.ansi_to_text = function (txt) {\n            return this.ansi_to(txt, this.textFormatter);\n        };\n        AnsiUp.prototype.with_state = function (text) {\n            return { bright: this.bright, fg: this.fg, bg: this.bg, text: text };\n        };\n        AnsiUp.prototype.handle_incomplete_sequences = function (chunks) {\n            var last_chunk = chunks[chunks.length - 1];\n            if ((last_chunk.length > 0) && this.detect_incomplete_ansi(last_chunk)) {\n                this._buffer = \"\\x1B[\" + last_chunk;\n                chunks.pop();\n                chunks.push('');\n            }\n            else {\n                if (last_chunk.slice(-1) === \"\\x1B\") {\n                    this._buffer = \"\\x1B\";\n                    console.log(\"raw\", chunks);\n                    chunks.pop();\n                    chunks.push(last_chunk.substr(0, last_chunk.length - 1));\n                    console.log(chunks);\n                    console.log(last_chunk);\n                }\n                if (chunks.length === 2 &&\n                    chunks[1] === \"\" &&\n                    chunks[0].slice(-1) === \"\\x1B\") {\n                    this._buffer = \"\\x1B\";\n                    last_chunk = chunks.shift();\n                    chunks.unshift(last_chunk.substr(0, last_chunk.length - 1));\n                }\n            }\n        };\n        AnsiUp.prototype.process_ansi = function (block) {\n            if (!this._sgr_regex) {\n                this._sgr_regex = (_a = [\"\\n            ^                           # beginning of line\\n            ([!<-?]?)             # a private-mode char (!, <, =, >, ?)\\n            ([d;]*)                    # any digits or semicolons\\n            ([ -/]?               # an intermediate modifier\\n            [@-~])                # the command\\n            ([sS]*)                   # any text following this CSI sequence\\n          \"], _a.raw = [\"\\n            ^                           # beginning of line\\n            ([!\\\\x3c-\\\\x3f]?)             # a private-mode char (!, <, =, >, ?)\\n            ([\\\\d;]*)                    # any digits or semicolons\\n            ([\\\\x20-\\\\x2f]?               # an intermediate modifier\\n            [\\\\x40-\\\\x7e])                # the command\\n            ([\\\\s\\\\S]*)                   # any text following this CSI sequence\\n          \"], rgx(_a));\n            }\n            var matches = block.match(this._sgr_regex);\n            if (!matches) {\n                return this.with_state(block);\n            }\n            var orig_txt = matches[4];\n            if (matches[1] !== '' || matches[3] !== 'm') {\n                return this.with_state(orig_txt);\n            }\n            var sgr_cmds = matches[2].split(';');\n            while (sgr_cmds.length > 0) {\n                var sgr_cmd_str = sgr_cmds.shift();\n                var num = parseInt(sgr_cmd_str, 10);\n                if (isNaN(num) || num === 0) {\n                    this.fg = this.bg = null;\n                    this.bright = false;\n                }\n                else if (num === 1) {\n                    this.bright = true;\n                }\n                else if (num === 22) {\n                    this.bright = false;\n                }\n                else if (num === 39) {\n                    this.fg = null;\n                }\n                else if (num === 49) {\n                    this.bg = null;\n                }\n                else if ((num >= 30) && (num < 38)) {\n                    var bidx = this.bright ? 1 : 0;\n                    this.fg = this.ansi_colors[bidx][(num - 30)];\n                }\n                else if ((num >= 90) && (num < 98)) {\n                    this.fg = this.ansi_colors[1][(num - 90)];\n                }\n                else if ((num >= 40) && (num < 48)) {\n                    this.bg = this.ansi_colors[0][(num - 40)];\n                }\n                else if ((num >= 100) && (num < 108)) {\n                    this.bg = this.ansi_colors[1][(num - 100)];\n                }\n                else if (num === 38 || num === 48) {\n                    if (sgr_cmds.length > 0) {\n                        var is_foreground = (num === 38);\n                        var mode_cmd = sgr_cmds.shift();\n                        if (mode_cmd === '5' && sgr_cmds.length > 0) {\n                            var palette_index = parseInt(sgr_cmds.shift(), 10);\n                            if (palette_index >= 0 && palette_index <= 255) {\n                                if (is_foreground)\n                                    this.fg = this.palette_256[palette_index];\n                                else\n                                    this.bg = this.palette_256[palette_index];\n                            }\n                        }\n                        if (mode_cmd === '2' && sgr_cmds.length > 2) {\n                            var r = parseInt(sgr_cmds.shift(), 10);\n                            var g = parseInt(sgr_cmds.shift(), 10);\n                            var b = parseInt(sgr_cmds.shift(), 10);\n                            if ((r >= 0 && r <= 255) && (g >= 0 && g <= 255) && (b >= 0 && b <= 255)) {\n                                var c = { rgb: [r, g, b], class_name: 'truecolor' };\n                                if (is_foreground)\n                                    this.fg = c;\n                                else\n                                    this.bg = c;\n                            }\n                        }\n                    }\n                }\n            }\n            return this.with_state(orig_txt);\n            var _a;\n        };\n        return AnsiUp;\n    }());\n    Object.defineProperty(exports, \"__esModule\", { value: true });\n    exports.default = AnsiUp;\n});\n"
  },
  {
    "path": "public/themes/pterodactyl/vendor/jquery/jquery.js",
    "content": "/*!\n * jQuery JavaScript Library v3.1.1\n * https://jquery.com/\n *\n * Includes Sizzle.js\n * https://sizzlejs.com/\n *\n * Copyright jQuery Foundation and other contributors\n * Released under the MIT license\n * https://jquery.org/license\n *\n * Date: 2016-09-22T22:30Z\n */\n( function( global, factory ) {\n\n\t\"use strict\";\n\n\tif ( typeof module === \"object\" && typeof module.exports === \"object\" ) {\n\n\t\t// For CommonJS and CommonJS-like environments where a proper `window`\n\t\t// is present, execute the factory and get jQuery.\n\t\t// For environments that do not have a `window` with a `document`\n\t\t// (such as Node.js), expose a factory as module.exports.\n\t\t// This accentuates the need for the creation of a real `window`.\n\t\t// e.g. var jQuery = require(\"jquery\")(window);\n\t\t// See ticket #14549 for more info.\n\t\tmodule.exports = global.document ?\n\t\t\tfactory( global, true ) :\n\t\t\tfunction( w ) {\n\t\t\t\tif ( !w.document ) {\n\t\t\t\t\tthrow new Error( \"jQuery requires a window with a document\" );\n\t\t\t\t}\n\t\t\t\treturn factory( w );\n\t\t\t};\n\t} else {\n\t\tfactory( global );\n\t}\n\n// Pass this if window is not defined yet\n} )( typeof window !== \"undefined\" ? window : this, function( window, noGlobal ) {\n\n// Edge <= 12 - 13+, Firefox <=18 - 45+, IE 10 - 11, Safari 5.1 - 9+, iOS 6 - 9.1\n// throw exceptions when non-strict code (e.g., ASP.NET 4.5) accesses strict mode\n// arguments.callee.caller (trac-13335). But as of jQuery 3.0 (2016), strict mode should be common\n// enough that all such attempts are guarded in a try block.\n\"use strict\";\n\nvar arr = [];\n\nvar document = window.document;\n\nvar getProto = Object.getPrototypeOf;\n\nvar slice = arr.slice;\n\nvar concat = arr.concat;\n\nvar push = arr.push;\n\nvar indexOf = arr.indexOf;\n\nvar class2type = {};\n\nvar toString = class2type.toString;\n\nvar hasOwn = class2type.hasOwnProperty;\n\nvar fnToString = hasOwn.toString;\n\nvar ObjectFunctionString = fnToString.call( Object );\n\nvar support = {};\n\n\n\n\tfunction DOMEval( code, doc ) {\n\t\tdoc = doc || document;\n\n\t\tvar script = doc.createElement( \"script\" );\n\n\t\tscript.text = code;\n\t\tdoc.head.appendChild( script ).parentNode.removeChild( script );\n\t}\n/* global Symbol */\n// Defining this global in .eslintrc.json would create a danger of using the global\n// unguarded in another place, it seems safer to define global only for this module\n\n\n\nvar\n\tversion = \"3.1.1\",\n\n\t// Define a local copy of jQuery\n\tjQuery = function( selector, context ) {\n\n\t\t// The jQuery object is actually just the init constructor 'enhanced'\n\t\t// Need init if jQuery is called (just allow error to be thrown if not included)\n\t\treturn new jQuery.fn.init( selector, context );\n\t},\n\n\t// Support: Android <=4.0 only\n\t// Make sure we trim BOM and NBSP\n\trtrim = /^[\\s\\uFEFF\\xA0]+|[\\s\\uFEFF\\xA0]+$/g,\n\n\t// Matches dashed string for camelizing\n\trmsPrefix = /^-ms-/,\n\trdashAlpha = /-([a-z])/g,\n\n\t// Used by jQuery.camelCase as callback to replace()\n\tfcamelCase = function( all, letter ) {\n\t\treturn letter.toUpperCase();\n\t};\n\njQuery.fn = jQuery.prototype = {\n\n\t// The current version of jQuery being used\n\tjquery: version,\n\n\tconstructor: jQuery,\n\n\t// The default length of a jQuery object is 0\n\tlength: 0,\n\n\ttoArray: function() {\n\t\treturn slice.call( this );\n\t},\n\n\t// Get the Nth element in the matched element set OR\n\t// Get the whole matched element set as a clean array\n\tget: function( num ) {\n\n\t\t// Return all the elements in a clean array\n\t\tif ( num == null ) {\n\t\t\treturn slice.call( this );\n\t\t}\n\n\t\t// Return just the one element from the set\n\t\treturn num < 0 ? this[ num + this.length ] : this[ num ];\n\t},\n\n\t// Take an array of elements and push it onto the stack\n\t// (returning the new matched element set)\n\tpushStack: function( elems ) {\n\n\t\t// Build a new jQuery matched element set\n\t\tvar ret = jQuery.merge( this.constructor(), elems );\n\n\t\t// Add the old object onto the stack (as a reference)\n\t\tret.prevObject = this;\n\n\t\t// Return the newly-formed element set\n\t\treturn ret;\n\t},\n\n\t// Execute a callback for every element in the matched set.\n\teach: function( callback ) {\n\t\treturn jQuery.each( this, callback );\n\t},\n\n\tmap: function( callback ) {\n\t\treturn this.pushStack( jQuery.map( this, function( elem, i ) {\n\t\t\treturn callback.call( elem, i, elem );\n\t\t} ) );\n\t},\n\n\tslice: function() {\n\t\treturn this.pushStack( slice.apply( this, arguments ) );\n\t},\n\n\tfirst: function() {\n\t\treturn this.eq( 0 );\n\t},\n\n\tlast: function() {\n\t\treturn this.eq( -1 );\n\t},\n\n\teq: function( i ) {\n\t\tvar len = this.length,\n\t\t\tj = +i + ( i < 0 ? len : 0 );\n\t\treturn this.pushStack( j >= 0 && j < len ? [ this[ j ] ] : [] );\n\t},\n\n\tend: function() {\n\t\treturn this.prevObject || this.constructor();\n\t},\n\n\t// For internal use only.\n\t// Behaves like an Array's method, not like a jQuery method.\n\tpush: push,\n\tsort: arr.sort,\n\tsplice: arr.splice\n};\n\njQuery.extend = jQuery.fn.extend = function() {\n\tvar options, name, src, copy, copyIsArray, clone,\n\t\ttarget = arguments[ 0 ] || {},\n\t\ti = 1,\n\t\tlength = arguments.length,\n\t\tdeep = false;\n\n\t// Handle a deep copy situation\n\tif ( typeof target === \"boolean\" ) {\n\t\tdeep = target;\n\n\t\t// Skip the boolean and the target\n\t\ttarget = arguments[ i ] || {};\n\t\ti++;\n\t}\n\n\t// Handle case when target is a string or something (possible in deep copy)\n\tif ( typeof target !== \"object\" && !jQuery.isFunction( target ) ) {\n\t\ttarget = {};\n\t}\n\n\t// Extend jQuery itself if only one argument is passed\n\tif ( i === length ) {\n\t\ttarget = this;\n\t\ti--;\n\t}\n\n\tfor ( ; i < length; i++ ) {\n\n\t\t// Only deal with non-null/undefined values\n\t\tif ( ( options = arguments[ i ] ) != null ) {\n\n\t\t\t// Extend the base object\n\t\t\tfor ( name in options ) {\n\t\t\t\tsrc = target[ name ];\n\t\t\t\tcopy = options[ name ];\n\n\t\t\t\t// Prevent never-ending loop\n\t\t\t\tif ( target === copy ) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\t// Recurse if we're merging plain objects or arrays\n\t\t\t\tif ( deep && copy && ( jQuery.isPlainObject( copy ) ||\n\t\t\t\t\t( copyIsArray = jQuery.isArray( copy ) ) ) ) {\n\n\t\t\t\t\tif ( copyIsArray ) {\n\t\t\t\t\t\tcopyIsArray = false;\n\t\t\t\t\t\tclone = src && jQuery.isArray( src ) ? src : [];\n\n\t\t\t\t\t} else {\n\t\t\t\t\t\tclone = src && jQuery.isPlainObject( src ) ? src : {};\n\t\t\t\t\t}\n\n\t\t\t\t\t// Never move original objects, clone them\n\t\t\t\t\ttarget[ name ] = jQuery.extend( deep, clone, copy );\n\n\t\t\t\t// Don't bring in undefined values\n\t\t\t\t} else if ( copy !== undefined ) {\n\t\t\t\t\ttarget[ name ] = copy;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// Return the modified object\n\treturn target;\n};\n\njQuery.extend( {\n\n\t// Unique for each copy of jQuery on the page\n\texpando: \"jQuery\" + ( version + Math.random() ).replace( /\\D/g, \"\" ),\n\n\t// Assume jQuery is ready without the ready module\n\tisReady: true,\n\n\terror: function( msg ) {\n\t\tthrow new Error( msg );\n\t},\n\n\tnoop: function() {},\n\n\tisFunction: function( obj ) {\n\t\treturn jQuery.type( obj ) === \"function\";\n\t},\n\n\tisArray: Array.isArray,\n\n\tisWindow: function( obj ) {\n\t\treturn obj != null && obj === obj.window;\n\t},\n\n\tisNumeric: function( obj ) {\n\n\t\t// As of jQuery 3.0, isNumeric is limited to\n\t\t// strings and numbers (primitives or objects)\n\t\t// that can be coerced to finite numbers (gh-2662)\n\t\tvar type = jQuery.type( obj );\n\t\treturn ( type === \"number\" || type === \"string\" ) &&\n\n\t\t\t// parseFloat NaNs numeric-cast false positives (\"\")\n\t\t\t// ...but misinterprets leading-number strings, particularly hex literals (\"0x...\")\n\t\t\t// subtraction forces infinities to NaN\n\t\t\t!isNaN( obj - parseFloat( obj ) );\n\t},\n\n\tisPlainObject: function( obj ) {\n\t\tvar proto, Ctor;\n\n\t\t// Detect obvious negatives\n\t\t// Use toString instead of jQuery.type to catch host objects\n\t\tif ( !obj || toString.call( obj ) !== \"[object Object]\" ) {\n\t\t\treturn false;\n\t\t}\n\n\t\tproto = getProto( obj );\n\n\t\t// Objects with no prototype (e.g., `Object.create( null )`) are plain\n\t\tif ( !proto ) {\n\t\t\treturn true;\n\t\t}\n\n\t\t// Objects with prototype are plain iff they were constructed by a global Object function\n\t\tCtor = hasOwn.call( proto, \"constructor\" ) && proto.constructor;\n\t\treturn typeof Ctor === \"function\" && fnToString.call( Ctor ) === ObjectFunctionString;\n\t},\n\n\tisEmptyObject: function( obj ) {\n\n\t\t/* eslint-disable no-unused-vars */\n\t\t// See https://github.com/eslint/eslint/issues/6125\n\t\tvar name;\n\n\t\tfor ( name in obj ) {\n\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t},\n\n\ttype: function( obj ) {\n\t\tif ( obj == null ) {\n\t\t\treturn obj + \"\";\n\t\t}\n\n\t\t// Support: Android <=2.3 only (functionish RegExp)\n\t\treturn typeof obj === \"object\" || typeof obj === \"function\" ?\n\t\t\tclass2type[ toString.call( obj ) ] || \"object\" :\n\t\t\ttypeof obj;\n\t},\n\n\t// Evaluates a script in a global context\n\tglobalEval: function( code ) {\n\t\tDOMEval( code );\n\t},\n\n\t// Convert dashed to camelCase; used by the css and data modules\n\t// Support: IE <=9 - 11, Edge 12 - 13\n\t// Microsoft forgot to hump their vendor prefix (#9572)\n\tcamelCase: function( string ) {\n\t\treturn string.replace( rmsPrefix, \"ms-\" ).replace( rdashAlpha, fcamelCase );\n\t},\n\n\tnodeName: function( elem, name ) {\n\t\treturn elem.nodeName && elem.nodeName.toLowerCase() === name.toLowerCase();\n\t},\n\n\teach: function( obj, callback ) {\n\t\tvar length, i = 0;\n\n\t\tif ( isArrayLike( obj ) ) {\n\t\t\tlength = obj.length;\n\t\t\tfor ( ; i < length; i++ ) {\n\t\t\t\tif ( callback.call( obj[ i ], i, obj[ i ] ) === false ) {\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t} else {\n\t\t\tfor ( i in obj ) {\n\t\t\t\tif ( callback.call( obj[ i ], i, obj[ i ] ) === false ) {\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn obj;\n\t},\n\n\t// Support: Android <=4.0 only\n\ttrim: function( text ) {\n\t\treturn text == null ?\n\t\t\t\"\" :\n\t\t\t( text + \"\" ).replace( rtrim, \"\" );\n\t},\n\n\t// results is for internal usage only\n\tmakeArray: function( arr, results ) {\n\t\tvar ret = results || [];\n\n\t\tif ( arr != null ) {\n\t\t\tif ( isArrayLike( Object( arr ) ) ) {\n\t\t\t\tjQuery.merge( ret,\n\t\t\t\t\ttypeof arr === \"string\" ?\n\t\t\t\t\t[ arr ] : arr\n\t\t\t\t);\n\t\t\t} else {\n\t\t\t\tpush.call( ret, arr );\n\t\t\t}\n\t\t}\n\n\t\treturn ret;\n\t},\n\n\tinArray: function( elem, arr, i ) {\n\t\treturn arr == null ? -1 : indexOf.call( arr, elem, i );\n\t},\n\n\t// Support: Android <=4.0 only, PhantomJS 1 only\n\t// push.apply(_, arraylike) throws on ancient WebKit\n\tmerge: function( first, second ) {\n\t\tvar len = +second.length,\n\t\t\tj = 0,\n\t\t\ti = first.length;\n\n\t\tfor ( ; j < len; j++ ) {\n\t\t\tfirst[ i++ ] = second[ j ];\n\t\t}\n\n\t\tfirst.length = i;\n\n\t\treturn first;\n\t},\n\n\tgrep: function( elems, callback, invert ) {\n\t\tvar callbackInverse,\n\t\t\tmatches = [],\n\t\t\ti = 0,\n\t\t\tlength = elems.length,\n\t\t\tcallbackExpect = !invert;\n\n\t\t// Go through the array, only saving the items\n\t\t// that pass the validator function\n\t\tfor ( ; i < length; i++ ) {\n\t\t\tcallbackInverse = !callback( elems[ i ], i );\n\t\t\tif ( callbackInverse !== callbackExpect ) {\n\t\t\t\tmatches.push( elems[ i ] );\n\t\t\t}\n\t\t}\n\n\t\treturn matches;\n\t},\n\n\t// arg is for internal usage only\n\tmap: function( elems, callback, arg ) {\n\t\tvar length, value,\n\t\t\ti = 0,\n\t\t\tret = [];\n\n\t\t// Go through the array, translating each of the items to their new values\n\t\tif ( isArrayLike( elems ) ) {\n\t\t\tlength = elems.length;\n\t\t\tfor ( ; i < length; i++ ) {\n\t\t\t\tvalue = callback( elems[ i ], i, arg );\n\n\t\t\t\tif ( value != null ) {\n\t\t\t\t\tret.push( value );\n\t\t\t\t}\n\t\t\t}\n\n\t\t// Go through every key on the object,\n\t\t} else {\n\t\t\tfor ( i in elems ) {\n\t\t\t\tvalue = callback( elems[ i ], i, arg );\n\n\t\t\t\tif ( value != null ) {\n\t\t\t\t\tret.push( value );\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Flatten any nested arrays\n\t\treturn concat.apply( [], ret );\n\t},\n\n\t// A global GUID counter for objects\n\tguid: 1,\n\n\t// Bind a function to a context, optionally partially applying any\n\t// arguments.\n\tproxy: function( fn, context ) {\n\t\tvar tmp, args, proxy;\n\n\t\tif ( typeof context === \"string\" ) {\n\t\t\ttmp = fn[ context ];\n\t\t\tcontext = fn;\n\t\t\tfn = tmp;\n\t\t}\n\n\t\t// Quick check to determine if target is callable, in the spec\n\t\t// this throws a TypeError, but we will just return undefined.\n\t\tif ( !jQuery.isFunction( fn ) ) {\n\t\t\treturn undefined;\n\t\t}\n\n\t\t// Simulated bind\n\t\targs = slice.call( arguments, 2 );\n\t\tproxy = function() {\n\t\t\treturn fn.apply( context || this, args.concat( slice.call( arguments ) ) );\n\t\t};\n\n\t\t// Set the guid of unique handler to the same of original handler, so it can be removed\n\t\tproxy.guid = fn.guid = fn.guid || jQuery.guid++;\n\n\t\treturn proxy;\n\t},\n\n\tnow: Date.now,\n\n\t// jQuery.support is not used in Core but other projects attach their\n\t// properties to it so it needs to exist.\n\tsupport: support\n} );\n\nif ( typeof Symbol === \"function\" ) {\n\tjQuery.fn[ Symbol.iterator ] = arr[ Symbol.iterator ];\n}\n\n// Populate the class2type map\njQuery.each( \"Boolean Number String Function Array Date RegExp Object Error Symbol\".split( \" \" ),\nfunction( i, name ) {\n\tclass2type[ \"[object \" + name + \"]\" ] = name.toLowerCase();\n} );\n\nfunction isArrayLike( obj ) {\n\n\t// Support: real iOS 8.2 only (not reproducible in simulator)\n\t// `in` check used to prevent JIT error (gh-2145)\n\t// hasOwn isn't used here due to false negatives\n\t// regarding Nodelist length in IE\n\tvar length = !!obj && \"length\" in obj && obj.length,\n\t\ttype = jQuery.type( obj );\n\n\tif ( type === \"function\" || jQuery.isWindow( obj ) ) {\n\t\treturn false;\n\t}\n\n\treturn type === \"array\" || length === 0 ||\n\t\ttypeof length === \"number\" && length > 0 && ( length - 1 ) in obj;\n}\nvar Sizzle =\n/*!\n * Sizzle CSS Selector Engine v2.3.3\n * https://sizzlejs.com/\n *\n * Copyright jQuery Foundation and other contributors\n * Released under the MIT license\n * http://jquery.org/license\n *\n * Date: 2016-08-08\n */\n(function( window ) {\n\nvar i,\n\tsupport,\n\tExpr,\n\tgetText,\n\tisXML,\n\ttokenize,\n\tcompile,\n\tselect,\n\toutermostContext,\n\tsortInput,\n\thasDuplicate,\n\n\t// Local document vars\n\tsetDocument,\n\tdocument,\n\tdocElem,\n\tdocumentIsHTML,\n\trbuggyQSA,\n\trbuggyMatches,\n\tmatches,\n\tcontains,\n\n\t// Instance-specific data\n\texpando = \"sizzle\" + 1 * new Date(),\n\tpreferredDoc = window.document,\n\tdirruns = 0,\n\tdone = 0,\n\tclassCache = createCache(),\n\ttokenCache = createCache(),\n\tcompilerCache = createCache(),\n\tsortOrder = function( a, b ) {\n\t\tif ( a === b ) {\n\t\t\thasDuplicate = true;\n\t\t}\n\t\treturn 0;\n\t},\n\n\t// Instance methods\n\thasOwn = ({}).hasOwnProperty,\n\tarr = [],\n\tpop = arr.pop,\n\tpush_native = arr.push,\n\tpush = arr.push,\n\tslice = arr.slice,\n\t// Use a stripped-down indexOf as it's faster than native\n\t// https://jsperf.com/thor-indexof-vs-for/5\n\tindexOf = function( list, elem ) {\n\t\tvar i = 0,\n\t\t\tlen = list.length;\n\t\tfor ( ; i < len; i++ ) {\n\t\t\tif ( list[i] === elem ) {\n\t\t\t\treturn i;\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t},\n\n\tbooleans = \"checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped\",\n\n\t// Regular expressions\n\n\t// http://www.w3.org/TR/css3-selectors/#whitespace\n\twhitespace = \"[\\\\x20\\\\t\\\\r\\\\n\\\\f]\",\n\n\t// http://www.w3.org/TR/CSS21/syndata.html#value-def-identifier\n\tidentifier = \"(?:\\\\\\\\.|[\\\\w-]|[^\\0-\\\\xa0])+\",\n\n\t// Attribute selectors: http://www.w3.org/TR/selectors/#attribute-selectors\n\tattributes = \"\\\\[\" + whitespace + \"*(\" + identifier + \")(?:\" + whitespace +\n\t\t// Operator (capture 2)\n\t\t\"*([*^$|!~]?=)\" + whitespace +\n\t\t// \"Attribute values must be CSS identifiers [capture 5] or strings [capture 3 or capture 4]\"\n\t\t\"*(?:'((?:\\\\\\\\.|[^\\\\\\\\'])*)'|\\\"((?:\\\\\\\\.|[^\\\\\\\\\\\"])*)\\\"|(\" + identifier + \"))|)\" + whitespace +\n\t\t\"*\\\\]\",\n\n\tpseudos = \":(\" + identifier + \")(?:\\\\((\" +\n\t\t// To reduce the number of selectors needing tokenize in the preFilter, prefer arguments:\n\t\t// 1. quoted (capture 3; capture 4 or capture 5)\n\t\t\"('((?:\\\\\\\\.|[^\\\\\\\\'])*)'|\\\"((?:\\\\\\\\.|[^\\\\\\\\\\\"])*)\\\")|\" +\n\t\t// 2. simple (capture 6)\n\t\t\"((?:\\\\\\\\.|[^\\\\\\\\()[\\\\]]|\" + attributes + \")*)|\" +\n\t\t// 3. anything else (capture 2)\n\t\t\".*\" +\n\t\t\")\\\\)|)\",\n\n\t// Leading and non-escaped trailing whitespace, capturing some non-whitespace characters preceding the latter\n\trwhitespace = new RegExp( whitespace + \"+\", \"g\" ),\n\trtrim = new RegExp( \"^\" + whitespace + \"+|((?:^|[^\\\\\\\\])(?:\\\\\\\\.)*)\" + whitespace + \"+$\", \"g\" ),\n\n\trcomma = new RegExp( \"^\" + whitespace + \"*,\" + whitespace + \"*\" ),\n\trcombinators = new RegExp( \"^\" + whitespace + \"*([>+~]|\" + whitespace + \")\" + whitespace + \"*\" ),\n\n\trattributeQuotes = new RegExp( \"=\" + whitespace + \"*([^\\\\]'\\\"]*?)\" + whitespace + \"*\\\\]\", \"g\" ),\n\n\trpseudo = new RegExp( pseudos ),\n\tridentifier = new RegExp( \"^\" + identifier + \"$\" ),\n\n\tmatchExpr = {\n\t\t\"ID\": new RegExp( \"^#(\" + identifier + \")\" ),\n\t\t\"CLASS\": new RegExp( \"^\\\\.(\" + identifier + \")\" ),\n\t\t\"TAG\": new RegExp( \"^(\" + identifier + \"|[*])\" ),\n\t\t\"ATTR\": new RegExp( \"^\" + attributes ),\n\t\t\"PSEUDO\": new RegExp( \"^\" + pseudos ),\n\t\t\"CHILD\": new RegExp( \"^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\\\(\" + whitespace +\n\t\t\t\"*(even|odd|(([+-]|)(\\\\d*)n|)\" + whitespace + \"*(?:([+-]|)\" + whitespace +\n\t\t\t\"*(\\\\d+)|))\" + whitespace + \"*\\\\)|)\", \"i\" ),\n\t\t\"bool\": new RegExp( \"^(?:\" + booleans + \")$\", \"i\" ),\n\t\t// For use in libraries implementing .is()\n\t\t// We use this for POS matching in `select`\n\t\t\"needsContext\": new RegExp( \"^\" + whitespace + \"*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\\\(\" +\n\t\t\twhitespace + \"*((?:-\\\\d)?\\\\d*)\" + whitespace + \"*\\\\)|)(?=[^-]|$)\", \"i\" )\n\t},\n\n\trinputs = /^(?:input|select|textarea|button)$/i,\n\trheader = /^h\\d$/i,\n\n\trnative = /^[^{]+\\{\\s*\\[native \\w/,\n\n\t// Easily-parseable/retrievable ID or TAG or CLASS selectors\n\trquickExpr = /^(?:#([\\w-]+)|(\\w+)|\\.([\\w-]+))$/,\n\n\trsibling = /[+~]/,\n\n\t// CSS escapes\n\t// http://www.w3.org/TR/CSS21/syndata.html#escaped-characters\n\trunescape = new RegExp( \"\\\\\\\\([\\\\da-f]{1,6}\" + whitespace + \"?|(\" + whitespace + \")|.)\", \"ig\" ),\n\tfunescape = function( _, escaped, escapedWhitespace ) {\n\t\tvar high = \"0x\" + escaped - 0x10000;\n\t\t// NaN means non-codepoint\n\t\t// Support: Firefox<24\n\t\t// Workaround erroneous numeric interpretation of +\"0x\"\n\t\treturn high !== high || escapedWhitespace ?\n\t\t\tescaped :\n\t\t\thigh < 0 ?\n\t\t\t\t// BMP codepoint\n\t\t\t\tString.fromCharCode( high + 0x10000 ) :\n\t\t\t\t// Supplemental Plane codepoint (surrogate pair)\n\t\t\t\tString.fromCharCode( high >> 10 | 0xD800, high & 0x3FF | 0xDC00 );\n\t},\n\n\t// CSS string/identifier serialization\n\t// https://drafts.csswg.org/cssom/#common-serializing-idioms\n\trcssescape = /([\\0-\\x1f\\x7f]|^-?\\d)|^-$|[^\\0-\\x1f\\x7f-\\uFFFF\\w-]/g,\n\tfcssescape = function( ch, asCodePoint ) {\n\t\tif ( asCodePoint ) {\n\n\t\t\t// U+0000 NULL becomes U+FFFD REPLACEMENT CHARACTER\n\t\t\tif ( ch === \"\\0\" ) {\n\t\t\t\treturn \"\\uFFFD\";\n\t\t\t}\n\n\t\t\t// Control characters and (dependent upon position) numbers get escaped as code points\n\t\t\treturn ch.slice( 0, -1 ) + \"\\\\\" + ch.charCodeAt( ch.length - 1 ).toString( 16 ) + \" \";\n\t\t}\n\n\t\t// Other potentially-special ASCII characters get backslash-escaped\n\t\treturn \"\\\\\" + ch;\n\t},\n\n\t// Used for iframes\n\t// See setDocument()\n\t// Removing the function wrapper causes a \"Permission Denied\"\n\t// error in IE\n\tunloadHandler = function() {\n\t\tsetDocument();\n\t},\n\n\tdisabledAncestor = addCombinator(\n\t\tfunction( elem ) {\n\t\t\treturn elem.disabled === true && (\"form\" in elem || \"label\" in elem);\n\t\t},\n\t\t{ dir: \"parentNode\", next: \"legend\" }\n\t);\n\n// Optimize for push.apply( _, NodeList )\ntry {\n\tpush.apply(\n\t\t(arr = slice.call( preferredDoc.childNodes )),\n\t\tpreferredDoc.childNodes\n\t);\n\t// Support: Android<4.0\n\t// Detect silently failing push.apply\n\tarr[ preferredDoc.childNodes.length ].nodeType;\n} catch ( e ) {\n\tpush = { apply: arr.length ?\n\n\t\t// Leverage slice if possible\n\t\tfunction( target, els ) {\n\t\t\tpush_native.apply( target, slice.call(els) );\n\t\t} :\n\n\t\t// Support: IE<9\n\t\t// Otherwise append directly\n\t\tfunction( target, els ) {\n\t\t\tvar j = target.length,\n\t\t\t\ti = 0;\n\t\t\t// Can't trust NodeList.length\n\t\t\twhile ( (target[j++] = els[i++]) ) {}\n\t\t\ttarget.length = j - 1;\n\t\t}\n\t};\n}\n\nfunction Sizzle( selector, context, results, seed ) {\n\tvar m, i, elem, nid, match, groups, newSelector,\n\t\tnewContext = context && context.ownerDocument,\n\n\t\t// nodeType defaults to 9, since context defaults to document\n\t\tnodeType = context ? context.nodeType : 9;\n\n\tresults = results || [];\n\n\t// Return early from calls with invalid selector or context\n\tif ( typeof selector !== \"string\" || !selector ||\n\t\tnodeType !== 1 && nodeType !== 9 && nodeType !== 11 ) {\n\n\t\treturn results;\n\t}\n\n\t// Try to shortcut find operations (as opposed to filters) in HTML documents\n\tif ( !seed ) {\n\n\t\tif ( ( context ? context.ownerDocument || context : preferredDoc ) !== document ) {\n\t\t\tsetDocument( context );\n\t\t}\n\t\tcontext = context || document;\n\n\t\tif ( documentIsHTML ) {\n\n\t\t\t// If the selector is sufficiently simple, try using a \"get*By*\" DOM method\n\t\t\t// (excepting DocumentFragment context, where the methods don't exist)\n\t\t\tif ( nodeType !== 11 && (match = rquickExpr.exec( selector )) ) {\n\n\t\t\t\t// ID selector\n\t\t\t\tif ( (m = match[1]) ) {\n\n\t\t\t\t\t// Document context\n\t\t\t\t\tif ( nodeType === 9 ) {\n\t\t\t\t\t\tif ( (elem = context.getElementById( m )) ) {\n\n\t\t\t\t\t\t\t// Support: IE, Opera, Webkit\n\t\t\t\t\t\t\t// TODO: identify versions\n\t\t\t\t\t\t\t// getElementById can match elements by name instead of ID\n\t\t\t\t\t\t\tif ( elem.id === m ) {\n\t\t\t\t\t\t\t\tresults.push( elem );\n\t\t\t\t\t\t\t\treturn results;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\treturn results;\n\t\t\t\t\t\t}\n\n\t\t\t\t\t// Element context\n\t\t\t\t\t} else {\n\n\t\t\t\t\t\t// Support: IE, Opera, Webkit\n\t\t\t\t\t\t// TODO: identify versions\n\t\t\t\t\t\t// getElementById can match elements by name instead of ID\n\t\t\t\t\t\tif ( newContext && (elem = newContext.getElementById( m )) &&\n\t\t\t\t\t\t\tcontains( context, elem ) &&\n\t\t\t\t\t\t\telem.id === m ) {\n\n\t\t\t\t\t\t\tresults.push( elem );\n\t\t\t\t\t\t\treturn results;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t// Type selector\n\t\t\t\t} else if ( match[2] ) {\n\t\t\t\t\tpush.apply( results, context.getElementsByTagName( selector ) );\n\t\t\t\t\treturn results;\n\n\t\t\t\t// Class selector\n\t\t\t\t} else if ( (m = match[3]) && support.getElementsByClassName &&\n\t\t\t\t\tcontext.getElementsByClassName ) {\n\n\t\t\t\t\tpush.apply( results, context.getElementsByClassName( m ) );\n\t\t\t\t\treturn results;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Take advantage of querySelectorAll\n\t\t\tif ( support.qsa &&\n\t\t\t\t!compilerCache[ selector + \" \" ] &&\n\t\t\t\t(!rbuggyQSA || !rbuggyQSA.test( selector )) ) {\n\n\t\t\t\tif ( nodeType !== 1 ) {\n\t\t\t\t\tnewContext = context;\n\t\t\t\t\tnewSelector = selector;\n\n\t\t\t\t// qSA looks outside Element context, which is not what we want\n\t\t\t\t// Thanks to Andrew Dupont for this workaround technique\n\t\t\t\t// Support: IE <=8\n\t\t\t\t// Exclude object elements\n\t\t\t\t} else if ( context.nodeName.toLowerCase() !== \"object\" ) {\n\n\t\t\t\t\t// Capture the context ID, setting it first if necessary\n\t\t\t\t\tif ( (nid = context.getAttribute( \"id\" )) ) {\n\t\t\t\t\t\tnid = nid.replace( rcssescape, fcssescape );\n\t\t\t\t\t} else {\n\t\t\t\t\t\tcontext.setAttribute( \"id\", (nid = expando) );\n\t\t\t\t\t}\n\n\t\t\t\t\t// Prefix every selector in the list\n\t\t\t\t\tgroups = tokenize( selector );\n\t\t\t\t\ti = groups.length;\n\t\t\t\t\twhile ( i-- ) {\n\t\t\t\t\t\tgroups[i] = \"#\" + nid + \" \" + toSelector( groups[i] );\n\t\t\t\t\t}\n\t\t\t\t\tnewSelector = groups.join( \",\" );\n\n\t\t\t\t\t// Expand context for sibling selectors\n\t\t\t\t\tnewContext = rsibling.test( selector ) && testContext( context.parentNode ) ||\n\t\t\t\t\t\tcontext;\n\t\t\t\t}\n\n\t\t\t\tif ( newSelector ) {\n\t\t\t\t\ttry {\n\t\t\t\t\t\tpush.apply( results,\n\t\t\t\t\t\t\tnewContext.querySelectorAll( newSelector )\n\t\t\t\t\t\t);\n\t\t\t\t\t\treturn results;\n\t\t\t\t\t} catch ( qsaError ) {\n\t\t\t\t\t} finally {\n\t\t\t\t\t\tif ( nid === expando ) {\n\t\t\t\t\t\t\tcontext.removeAttribute( \"id\" );\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// All others\n\treturn select( selector.replace( rtrim, \"$1\" ), context, results, seed );\n}\n\n/**\n * Create key-value caches of limited size\n * @returns {function(string, object)} Returns the Object data after storing it on itself with\n *\tproperty name the (space-suffixed) string and (if the cache is larger than Expr.cacheLength)\n *\tdeleting the oldest entry\n */\nfunction createCache() {\n\tvar keys = [];\n\n\tfunction cache( key, value ) {\n\t\t// Use (key + \" \") to avoid collision with native prototype properties (see Issue #157)\n\t\tif ( keys.push( key + \" \" ) > Expr.cacheLength ) {\n\t\t\t// Only keep the most recent entries\n\t\t\tdelete cache[ keys.shift() ];\n\t\t}\n\t\treturn (cache[ key + \" \" ] = value);\n\t}\n\treturn cache;\n}\n\n/**\n * Mark a function for special use by Sizzle\n * @param {Function} fn The function to mark\n */\nfunction markFunction( fn ) {\n\tfn[ expando ] = true;\n\treturn fn;\n}\n\n/**\n * Support testing using an element\n * @param {Function} fn Passed the created element and returns a boolean result\n */\nfunction assert( fn ) {\n\tvar el = document.createElement(\"fieldset\");\n\n\ttry {\n\t\treturn !!fn( el );\n\t} catch (e) {\n\t\treturn false;\n\t} finally {\n\t\t// Remove from its parent by default\n\t\tif ( el.parentNode ) {\n\t\t\tel.parentNode.removeChild( el );\n\t\t}\n\t\t// release memory in IE\n\t\tel = null;\n\t}\n}\n\n/**\n * Adds the same handler for all of the specified attrs\n * @param {String} attrs Pipe-separated list of attributes\n * @param {Function} handler The method that will be applied\n */\nfunction addHandle( attrs, handler ) {\n\tvar arr = attrs.split(\"|\"),\n\t\ti = arr.length;\n\n\twhile ( i-- ) {\n\t\tExpr.attrHandle[ arr[i] ] = handler;\n\t}\n}\n\n/**\n * Checks document order of two siblings\n * @param {Element} a\n * @param {Element} b\n * @returns {Number} Returns less than 0 if a precedes b, greater than 0 if a follows b\n */\nfunction siblingCheck( a, b ) {\n\tvar cur = b && a,\n\t\tdiff = cur && a.nodeType === 1 && b.nodeType === 1 &&\n\t\t\ta.sourceIndex - b.sourceIndex;\n\n\t// Use IE sourceIndex if available on both nodes\n\tif ( diff ) {\n\t\treturn diff;\n\t}\n\n\t// Check if b follows a\n\tif ( cur ) {\n\t\twhile ( (cur = cur.nextSibling) ) {\n\t\t\tif ( cur === b ) {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\t}\n\n\treturn a ? 1 : -1;\n}\n\n/**\n * Returns a function to use in pseudos for input types\n * @param {String} type\n */\nfunction createInputPseudo( type ) {\n\treturn function( elem ) {\n\t\tvar name = elem.nodeName.toLowerCase();\n\t\treturn name === \"input\" && elem.type === type;\n\t};\n}\n\n/**\n * Returns a function to use in pseudos for buttons\n * @param {String} type\n */\nfunction createButtonPseudo( type ) {\n\treturn function( elem ) {\n\t\tvar name = elem.nodeName.toLowerCase();\n\t\treturn (name === \"input\" || name === \"button\") && elem.type === type;\n\t};\n}\n\n/**\n * Returns a function to use in pseudos for :enabled/:disabled\n * @param {Boolean} disabled true for :disabled; false for :enabled\n */\nfunction createDisabledPseudo( disabled ) {\n\n\t// Known :disabled false positives: fieldset[disabled] > legend:nth-of-type(n+2) :can-disable\n\treturn function( elem ) {\n\n\t\t// Only certain elements can match :enabled or :disabled\n\t\t// https://html.spec.whatwg.org/multipage/scripting.html#selector-enabled\n\t\t// https://html.spec.whatwg.org/multipage/scripting.html#selector-disabled\n\t\tif ( \"form\" in elem ) {\n\n\t\t\t// Check for inherited disabledness on relevant non-disabled elements:\n\t\t\t// * listed form-associated elements in a disabled fieldset\n\t\t\t//   https://html.spec.whatwg.org/multipage/forms.html#category-listed\n\t\t\t//   https://html.spec.whatwg.org/multipage/forms.html#concept-fe-disabled\n\t\t\t// * option elements in a disabled optgroup\n\t\t\t//   https://html.spec.whatwg.org/multipage/forms.html#concept-option-disabled\n\t\t\t// All such elements have a \"form\" property.\n\t\t\tif ( elem.parentNode && elem.disabled === false ) {\n\n\t\t\t\t// Option elements defer to a parent optgroup if present\n\t\t\t\tif ( \"label\" in elem ) {\n\t\t\t\t\tif ( \"label\" in elem.parentNode ) {\n\t\t\t\t\t\treturn elem.parentNode.disabled === disabled;\n\t\t\t\t\t} else {\n\t\t\t\t\t\treturn elem.disabled === disabled;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// Support: IE 6 - 11\n\t\t\t\t// Use the isDisabled shortcut property to check for disabled fieldset ancestors\n\t\t\t\treturn elem.isDisabled === disabled ||\n\n\t\t\t\t\t// Where there is no isDisabled, check manually\n\t\t\t\t\t/* jshint -W018 */\n\t\t\t\t\telem.isDisabled !== !disabled &&\n\t\t\t\t\t\tdisabledAncestor( elem ) === disabled;\n\t\t\t}\n\n\t\t\treturn elem.disabled === disabled;\n\n\t\t// Try to winnow out elements that can't be disabled before trusting the disabled property.\n\t\t// Some victims get caught in our net (label, legend, menu, track), but it shouldn't\n\t\t// even exist on them, let alone have a boolean value.\n\t\t} else if ( \"label\" in elem ) {\n\t\t\treturn elem.disabled === disabled;\n\t\t}\n\n\t\t// Remaining elements are neither :enabled nor :disabled\n\t\treturn false;\n\t};\n}\n\n/**\n * Returns a function to use in pseudos for positionals\n * @param {Function} fn\n */\nfunction createPositionalPseudo( fn ) {\n\treturn markFunction(function( argument ) {\n\t\targument = +argument;\n\t\treturn markFunction(function( seed, matches ) {\n\t\t\tvar j,\n\t\t\t\tmatchIndexes = fn( [], seed.length, argument ),\n\t\t\t\ti = matchIndexes.length;\n\n\t\t\t// Match elements found at the specified indexes\n\t\t\twhile ( i-- ) {\n\t\t\t\tif ( seed[ (j = matchIndexes[i]) ] ) {\n\t\t\t\t\tseed[j] = !(matches[j] = seed[j]);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t});\n}\n\n/**\n * Checks a node for validity as a Sizzle context\n * @param {Element|Object=} context\n * @returns {Element|Object|Boolean} The input node if acceptable, otherwise a falsy value\n */\nfunction testContext( context ) {\n\treturn context && typeof context.getElementsByTagName !== \"undefined\" && context;\n}\n\n// Expose support vars for convenience\nsupport = Sizzle.support = {};\n\n/**\n * Detects XML nodes\n * @param {Element|Object} elem An element or a document\n * @returns {Boolean} True iff elem is a non-HTML XML node\n */\nisXML = Sizzle.isXML = function( elem ) {\n\t// documentElement is verified for cases where it doesn't yet exist\n\t// (such as loading iframes in IE - #4833)\n\tvar documentElement = elem && (elem.ownerDocument || elem).documentElement;\n\treturn documentElement ? documentElement.nodeName !== \"HTML\" : false;\n};\n\n/**\n * Sets document-related variables once based on the current document\n * @param {Element|Object} [doc] An element or document object to use to set the document\n * @returns {Object} Returns the current document\n */\nsetDocument = Sizzle.setDocument = function( node ) {\n\tvar hasCompare, subWindow,\n\t\tdoc = node ? node.ownerDocument || node : preferredDoc;\n\n\t// Return early if doc is invalid or already selected\n\tif ( doc === document || doc.nodeType !== 9 || !doc.documentElement ) {\n\t\treturn document;\n\t}\n\n\t// Update global variables\n\tdocument = doc;\n\tdocElem = document.documentElement;\n\tdocumentIsHTML = !isXML( document );\n\n\t// Support: IE 9-11, Edge\n\t// Accessing iframe documents after unload throws \"permission denied\" errors (jQuery #13936)\n\tif ( preferredDoc !== document &&\n\t\t(subWindow = document.defaultView) && subWindow.top !== subWindow ) {\n\n\t\t// Support: IE 11, Edge\n\t\tif ( subWindow.addEventListener ) {\n\t\t\tsubWindow.addEventListener( \"unload\", unloadHandler, false );\n\n\t\t// Support: IE 9 - 10 only\n\t\t} else if ( subWindow.attachEvent ) {\n\t\t\tsubWindow.attachEvent( \"onunload\", unloadHandler );\n\t\t}\n\t}\n\n\t/* Attributes\n\t---------------------------------------------------------------------- */\n\n\t// Support: IE<8\n\t// Verify that getAttribute really returns attributes and not properties\n\t// (excepting IE8 booleans)\n\tsupport.attributes = assert(function( el ) {\n\t\tel.className = \"i\";\n\t\treturn !el.getAttribute(\"className\");\n\t});\n\n\t/* getElement(s)By*\n\t---------------------------------------------------------------------- */\n\n\t// Check if getElementsByTagName(\"*\") returns only elements\n\tsupport.getElementsByTagName = assert(function( el ) {\n\t\tel.appendChild( document.createComment(\"\") );\n\t\treturn !el.getElementsByTagName(\"*\").length;\n\t});\n\n\t// Support: IE<9\n\tsupport.getElementsByClassName = rnative.test( document.getElementsByClassName );\n\n\t// Support: IE<10\n\t// Check if getElementById returns elements by name\n\t// The broken getElementById methods don't pick up programmatically-set names,\n\t// so use a roundabout getElementsByName test\n\tsupport.getById = assert(function( el ) {\n\t\tdocElem.appendChild( el ).id = expando;\n\t\treturn !document.getElementsByName || !document.getElementsByName( expando ).length;\n\t});\n\n\t// ID filter and find\n\tif ( support.getById ) {\n\t\tExpr.filter[\"ID\"] = function( id ) {\n\t\t\tvar attrId = id.replace( runescape, funescape );\n\t\t\treturn function( elem ) {\n\t\t\t\treturn elem.getAttribute(\"id\") === attrId;\n\t\t\t};\n\t\t};\n\t\tExpr.find[\"ID\"] = function( id, context ) {\n\t\t\tif ( typeof context.getElementById !== \"undefined\" && documentIsHTML ) {\n\t\t\t\tvar elem = context.getElementById( id );\n\t\t\t\treturn elem ? [ elem ] : [];\n\t\t\t}\n\t\t};\n\t} else {\n\t\tExpr.filter[\"ID\"] =  function( id ) {\n\t\t\tvar attrId = id.replace( runescape, funescape );\n\t\t\treturn function( elem ) {\n\t\t\t\tvar node = typeof elem.getAttributeNode !== \"undefined\" &&\n\t\t\t\t\telem.getAttributeNode(\"id\");\n\t\t\t\treturn node && node.value === attrId;\n\t\t\t};\n\t\t};\n\n\t\t// Support: IE 6 - 7 only\n\t\t// getElementById is not reliable as a find shortcut\n\t\tExpr.find[\"ID\"] = function( id, context ) {\n\t\t\tif ( typeof context.getElementById !== \"undefined\" && documentIsHTML ) {\n\t\t\t\tvar node, i, elems,\n\t\t\t\t\telem = context.getElementById( id );\n\n\t\t\t\tif ( elem ) {\n\n\t\t\t\t\t// Verify the id attribute\n\t\t\t\t\tnode = elem.getAttributeNode(\"id\");\n\t\t\t\t\tif ( node && node.value === id ) {\n\t\t\t\t\t\treturn [ elem ];\n\t\t\t\t\t}\n\n\t\t\t\t\t// Fall back on getElementsByName\n\t\t\t\t\telems = context.getElementsByName( id );\n\t\t\t\t\ti = 0;\n\t\t\t\t\twhile ( (elem = elems[i++]) ) {\n\t\t\t\t\t\tnode = elem.getAttributeNode(\"id\");\n\t\t\t\t\t\tif ( node && node.value === id ) {\n\t\t\t\t\t\t\treturn [ elem ];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\treturn [];\n\t\t\t}\n\t\t};\n\t}\n\n\t// Tag\n\tExpr.find[\"TAG\"] = support.getElementsByTagName ?\n\t\tfunction( tag, context ) {\n\t\t\tif ( typeof context.getElementsByTagName !== \"undefined\" ) {\n\t\t\t\treturn context.getElementsByTagName( tag );\n\n\t\t\t// DocumentFragment nodes don't have gEBTN\n\t\t\t} else if ( support.qsa ) {\n\t\t\t\treturn context.querySelectorAll( tag );\n\t\t\t}\n\t\t} :\n\n\t\tfunction( tag, context ) {\n\t\t\tvar elem,\n\t\t\t\ttmp = [],\n\t\t\t\ti = 0,\n\t\t\t\t// By happy coincidence, a (broken) gEBTN appears on DocumentFragment nodes too\n\t\t\t\tresults = context.getElementsByTagName( tag );\n\n\t\t\t// Filter out possible comments\n\t\t\tif ( tag === \"*\" ) {\n\t\t\t\twhile ( (elem = results[i++]) ) {\n\t\t\t\t\tif ( elem.nodeType === 1 ) {\n\t\t\t\t\t\ttmp.push( elem );\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\treturn tmp;\n\t\t\t}\n\t\t\treturn results;\n\t\t};\n\n\t// Class\n\tExpr.find[\"CLASS\"] = support.getElementsByClassName && function( className, context ) {\n\t\tif ( typeof context.getElementsByClassName !== \"undefined\" && documentIsHTML ) {\n\t\t\treturn context.getElementsByClassName( className );\n\t\t}\n\t};\n\n\t/* QSA/matchesSelector\n\t---------------------------------------------------------------------- */\n\n\t// QSA and matchesSelector support\n\n\t// matchesSelector(:active) reports false when true (IE9/Opera 11.5)\n\trbuggyMatches = [];\n\n\t// qSa(:focus) reports false when true (Chrome 21)\n\t// We allow this because of a bug in IE8/9 that throws an error\n\t// whenever `document.activeElement` is accessed on an iframe\n\t// So, we allow :focus to pass through QSA all the time to avoid the IE error\n\t// See https://bugs.jquery.com/ticket/13378\n\trbuggyQSA = [];\n\n\tif ( (support.qsa = rnative.test( document.querySelectorAll )) ) {\n\t\t// Build QSA regex\n\t\t// Regex strategy adopted from Diego Perini\n\t\tassert(function( el ) {\n\t\t\t// Select is set to empty string on purpose\n\t\t\t// This is to test IE's treatment of not explicitly\n\t\t\t// setting a boolean content attribute,\n\t\t\t// since its presence should be enough\n\t\t\t// https://bugs.jquery.com/ticket/12359\n\t\t\tdocElem.appendChild( el ).innerHTML = \"<a id='\" + expando + \"'></a>\" +\n\t\t\t\t\"<select id='\" + expando + \"-\\r\\\\' msallowcapture=''>\" +\n\t\t\t\t\"<option selected=''></option></select>\";\n\n\t\t\t// Support: IE8, Opera 11-12.16\n\t\t\t// Nothing should be selected when empty strings follow ^= or $= or *=\n\t\t\t// The test attribute must be unknown in Opera but \"safe\" for WinRT\n\t\t\t// https://msdn.microsoft.com/en-us/library/ie/hh465388.aspx#attribute_section\n\t\t\tif ( el.querySelectorAll(\"[msallowcapture^='']\").length ) {\n\t\t\t\trbuggyQSA.push( \"[*^$]=\" + whitespace + \"*(?:''|\\\"\\\")\" );\n\t\t\t}\n\n\t\t\t// Support: IE8\n\t\t\t// Boolean attributes and \"value\" are not treated correctly\n\t\t\tif ( !el.querySelectorAll(\"[selected]\").length ) {\n\t\t\t\trbuggyQSA.push( \"\\\\[\" + whitespace + \"*(?:value|\" + booleans + \")\" );\n\t\t\t}\n\n\t\t\t// Support: Chrome<29, Android<4.4, Safari<7.0+, iOS<7.0+, PhantomJS<1.9.8+\n\t\t\tif ( !el.querySelectorAll( \"[id~=\" + expando + \"-]\" ).length ) {\n\t\t\t\trbuggyQSA.push(\"~=\");\n\t\t\t}\n\n\t\t\t// Webkit/Opera - :checked should return selected option elements\n\t\t\t// http://www.w3.org/TR/2011/REC-css3-selectors-20110929/#checked\n\t\t\t// IE8 throws error here and will not see later tests\n\t\t\tif ( !el.querySelectorAll(\":checked\").length ) {\n\t\t\t\trbuggyQSA.push(\":checked\");\n\t\t\t}\n\n\t\t\t// Support: Safari 8+, iOS 8+\n\t\t\t// https://bugs.webkit.org/show_bug.cgi?id=136851\n\t\t\t// In-page `selector#id sibling-combinator selector` fails\n\t\t\tif ( !el.querySelectorAll( \"a#\" + expando + \"+*\" ).length ) {\n\t\t\t\trbuggyQSA.push(\".#.+[+~]\");\n\t\t\t}\n\t\t});\n\n\t\tassert(function( el ) {\n\t\t\tel.innerHTML = \"<a href='' disabled='disabled'></a>\" +\n\t\t\t\t\"<select disabled='disabled'><option/></select>\";\n\n\t\t\t// Support: Windows 8 Native Apps\n\t\t\t// The type and name attributes are restricted during .innerHTML assignment\n\t\t\tvar input = document.createElement(\"input\");\n\t\t\tinput.setAttribute( \"type\", \"hidden\" );\n\t\t\tel.appendChild( input ).setAttribute( \"name\", \"D\" );\n\n\t\t\t// Support: IE8\n\t\t\t// Enforce case-sensitivity of name attribute\n\t\t\tif ( el.querySelectorAll(\"[name=d]\").length ) {\n\t\t\t\trbuggyQSA.push( \"name\" + whitespace + \"*[*^$|!~]?=\" );\n\t\t\t}\n\n\t\t\t// FF 3.5 - :enabled/:disabled and hidden elements (hidden elements are still enabled)\n\t\t\t// IE8 throws error here and will not see later tests\n\t\t\tif ( el.querySelectorAll(\":enabled\").length !== 2 ) {\n\t\t\t\trbuggyQSA.push( \":enabled\", \":disabled\" );\n\t\t\t}\n\n\t\t\t// Support: IE9-11+\n\t\t\t// IE's :disabled selector does not pick up the children of disabled fieldsets\n\t\t\tdocElem.appendChild( el ).disabled = true;\n\t\t\tif ( el.querySelectorAll(\":disabled\").length !== 2 ) {\n\t\t\t\trbuggyQSA.push( \":enabled\", \":disabled\" );\n\t\t\t}\n\n\t\t\t// Opera 10-11 does not throw on post-comma invalid pseudos\n\t\t\tel.querySelectorAll(\"*,:x\");\n\t\t\trbuggyQSA.push(\",.*:\");\n\t\t});\n\t}\n\n\tif ( (support.matchesSelector = rnative.test( (matches = docElem.matches ||\n\t\tdocElem.webkitMatchesSelector ||\n\t\tdocElem.mozMatchesSelector ||\n\t\tdocElem.oMatchesSelector ||\n\t\tdocElem.msMatchesSelector) )) ) {\n\n\t\tassert(function( el ) {\n\t\t\t// Check to see if it's possible to do matchesSelector\n\t\t\t// on a disconnected node (IE 9)\n\t\t\tsupport.disconnectedMatch = matches.call( el, \"*\" );\n\n\t\t\t// This should fail with an exception\n\t\t\t// Gecko does not error, returns false instead\n\t\t\tmatches.call( el, \"[s!='']:x\" );\n\t\t\trbuggyMatches.push( \"!=\", pseudos );\n\t\t});\n\t}\n\n\trbuggyQSA = rbuggyQSA.length && new RegExp( rbuggyQSA.join(\"|\") );\n\trbuggyMatches = rbuggyMatches.length && new RegExp( rbuggyMatches.join(\"|\") );\n\n\t/* Contains\n\t---------------------------------------------------------------------- */\n\thasCompare = rnative.test( docElem.compareDocumentPosition );\n\n\t// Element contains another\n\t// Purposefully self-exclusive\n\t// As in, an element does not contain itself\n\tcontains = hasCompare || rnative.test( docElem.contains ) ?\n\t\tfunction( a, b ) {\n\t\t\tvar adown = a.nodeType === 9 ? a.documentElement : a,\n\t\t\t\tbup = b && b.parentNode;\n\t\t\treturn a === bup || !!( bup && bup.nodeType === 1 && (\n\t\t\t\tadown.contains ?\n\t\t\t\t\tadown.contains( bup ) :\n\t\t\t\t\ta.compareDocumentPosition && a.compareDocumentPosition( bup ) & 16\n\t\t\t));\n\t\t} :\n\t\tfunction( a, b ) {\n\t\t\tif ( b ) {\n\t\t\t\twhile ( (b = b.parentNode) ) {\n\t\t\t\t\tif ( b === a ) {\n\t\t\t\t\t\treturn true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn false;\n\t\t};\n\n\t/* Sorting\n\t---------------------------------------------------------------------- */\n\n\t// Document order sorting\n\tsortOrder = hasCompare ?\n\tfunction( a, b ) {\n\n\t\t// Flag for duplicate removal\n\t\tif ( a === b ) {\n\t\t\thasDuplicate = true;\n\t\t\treturn 0;\n\t\t}\n\n\t\t// Sort on method existence if only one input has compareDocumentPosition\n\t\tvar compare = !a.compareDocumentPosition - !b.compareDocumentPosition;\n\t\tif ( compare ) {\n\t\t\treturn compare;\n\t\t}\n\n\t\t// Calculate position if both inputs belong to the same document\n\t\tcompare = ( a.ownerDocument || a ) === ( b.ownerDocument || b ) ?\n\t\t\ta.compareDocumentPosition( b ) :\n\n\t\t\t// Otherwise we know they are disconnected\n\t\t\t1;\n\n\t\t// Disconnected nodes\n\t\tif ( compare & 1 ||\n\t\t\t(!support.sortDetached && b.compareDocumentPosition( a ) === compare) ) {\n\n\t\t\t// Choose the first element that is related to our preferred document\n\t\t\tif ( a === document || a.ownerDocument === preferredDoc && contains(preferredDoc, a) ) {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t\tif ( b === document || b.ownerDocument === preferredDoc && contains(preferredDoc, b) ) {\n\t\t\t\treturn 1;\n\t\t\t}\n\n\t\t\t// Maintain original order\n\t\t\treturn sortInput ?\n\t\t\t\t( indexOf( sortInput, a ) - indexOf( sortInput, b ) ) :\n\t\t\t\t0;\n\t\t}\n\n\t\treturn compare & 4 ? -1 : 1;\n\t} :\n\tfunction( a, b ) {\n\t\t// Exit early if the nodes are identical\n\t\tif ( a === b ) {\n\t\t\thasDuplicate = true;\n\t\t\treturn 0;\n\t\t}\n\n\t\tvar cur,\n\t\t\ti = 0,\n\t\t\taup = a.parentNode,\n\t\t\tbup = b.parentNode,\n\t\t\tap = [ a ],\n\t\t\tbp = [ b ];\n\n\t\t// Parentless nodes are either documents or disconnected\n\t\tif ( !aup || !bup ) {\n\t\t\treturn a === document ? -1 :\n\t\t\t\tb === document ? 1 :\n\t\t\t\taup ? -1 :\n\t\t\t\tbup ? 1 :\n\t\t\t\tsortInput ?\n\t\t\t\t( indexOf( sortInput, a ) - indexOf( sortInput, b ) ) :\n\t\t\t\t0;\n\n\t\t// If the nodes are siblings, we can do a quick check\n\t\t} else if ( aup === bup ) {\n\t\t\treturn siblingCheck( a, b );\n\t\t}\n\n\t\t// Otherwise we need full lists of their ancestors for comparison\n\t\tcur = a;\n\t\twhile ( (cur = cur.parentNode) ) {\n\t\t\tap.unshift( cur );\n\t\t}\n\t\tcur = b;\n\t\twhile ( (cur = cur.parentNode) ) {\n\t\t\tbp.unshift( cur );\n\t\t}\n\n\t\t// Walk down the tree looking for a discrepancy\n\t\twhile ( ap[i] === bp[i] ) {\n\t\t\ti++;\n\t\t}\n\n\t\treturn i ?\n\t\t\t// Do a sibling check if the nodes have a common ancestor\n\t\t\tsiblingCheck( ap[i], bp[i] ) :\n\n\t\t\t// Otherwise nodes in our document sort first\n\t\t\tap[i] === preferredDoc ? -1 :\n\t\t\tbp[i] === preferredDoc ? 1 :\n\t\t\t0;\n\t};\n\n\treturn document;\n};\n\nSizzle.matches = function( expr, elements ) {\n\treturn Sizzle( expr, null, null, elements );\n};\n\nSizzle.matchesSelector = function( elem, expr ) {\n\t// Set document vars if needed\n\tif ( ( elem.ownerDocument || elem ) !== document ) {\n\t\tsetDocument( elem );\n\t}\n\n\t// Make sure that attribute selectors are quoted\n\texpr = expr.replace( rattributeQuotes, \"='$1']\" );\n\n\tif ( support.matchesSelector && documentIsHTML &&\n\t\t!compilerCache[ expr + \" \" ] &&\n\t\t( !rbuggyMatches || !rbuggyMatches.test( expr ) ) &&\n\t\t( !rbuggyQSA     || !rbuggyQSA.test( expr ) ) ) {\n\n\t\ttry {\n\t\t\tvar ret = matches.call( elem, expr );\n\n\t\t\t// IE 9's matchesSelector returns false on disconnected nodes\n\t\t\tif ( ret || support.disconnectedMatch ||\n\t\t\t\t\t// As well, disconnected nodes are said to be in a document\n\t\t\t\t\t// fragment in IE 9\n\t\t\t\t\telem.document && elem.document.nodeType !== 11 ) {\n\t\t\t\treturn ret;\n\t\t\t}\n\t\t} catch (e) {}\n\t}\n\n\treturn Sizzle( expr, document, null, [ elem ] ).length > 0;\n};\n\nSizzle.contains = function( context, elem ) {\n\t// Set document vars if needed\n\tif ( ( context.ownerDocument || context ) !== document ) {\n\t\tsetDocument( context );\n\t}\n\treturn contains( context, elem );\n};\n\nSizzle.attr = function( elem, name ) {\n\t// Set document vars if needed\n\tif ( ( elem.ownerDocument || elem ) !== document ) {\n\t\tsetDocument( elem );\n\t}\n\n\tvar fn = Expr.attrHandle[ name.toLowerCase() ],\n\t\t// Don't get fooled by Object.prototype properties (jQuery #13807)\n\t\tval = fn && hasOwn.call( Expr.attrHandle, name.toLowerCase() ) ?\n\t\t\tfn( elem, name, !documentIsHTML ) :\n\t\t\tundefined;\n\n\treturn val !== undefined ?\n\t\tval :\n\t\tsupport.attributes || !documentIsHTML ?\n\t\t\telem.getAttribute( name ) :\n\t\t\t(val = elem.getAttributeNode(name)) && val.specified ?\n\t\t\t\tval.value :\n\t\t\t\tnull;\n};\n\nSizzle.escape = function( sel ) {\n\treturn (sel + \"\").replace( rcssescape, fcssescape );\n};\n\nSizzle.error = function( msg ) {\n\tthrow new Error( \"Syntax error, unrecognized expression: \" + msg );\n};\n\n/**\n * Document sorting and removing duplicates\n * @param {ArrayLike} results\n */\nSizzle.uniqueSort = function( results ) {\n\tvar elem,\n\t\tduplicates = [],\n\t\tj = 0,\n\t\ti = 0;\n\n\t// Unless we *know* we can detect duplicates, assume their presence\n\thasDuplicate = !support.detectDuplicates;\n\tsortInput = !support.sortStable && results.slice( 0 );\n\tresults.sort( sortOrder );\n\n\tif ( hasDuplicate ) {\n\t\twhile ( (elem = results[i++]) ) {\n\t\t\tif ( elem === results[ i ] ) {\n\t\t\t\tj = duplicates.push( i );\n\t\t\t}\n\t\t}\n\t\twhile ( j-- ) {\n\t\t\tresults.splice( duplicates[ j ], 1 );\n\t\t}\n\t}\n\n\t// Clear input after sorting to release objects\n\t// See https://github.com/jquery/sizzle/pull/225\n\tsortInput = null;\n\n\treturn results;\n};\n\n/**\n * Utility function for retrieving the text value of an array of DOM nodes\n * @param {Array|Element} elem\n */\ngetText = Sizzle.getText = function( elem ) {\n\tvar node,\n\t\tret = \"\",\n\t\ti = 0,\n\t\tnodeType = elem.nodeType;\n\n\tif ( !nodeType ) {\n\t\t// If no nodeType, this is expected to be an array\n\t\twhile ( (node = elem[i++]) ) {\n\t\t\t// Do not traverse comment nodes\n\t\t\tret += getText( node );\n\t\t}\n\t} else if ( nodeType === 1 || nodeType === 9 || nodeType === 11 ) {\n\t\t// Use textContent for elements\n\t\t// innerText usage removed for consistency of new lines (jQuery #11153)\n\t\tif ( typeof elem.textContent === \"string\" ) {\n\t\t\treturn elem.textContent;\n\t\t} else {\n\t\t\t// Traverse its children\n\t\t\tfor ( elem = elem.firstChild; elem; elem = elem.nextSibling ) {\n\t\t\t\tret += getText( elem );\n\t\t\t}\n\t\t}\n\t} else if ( nodeType === 3 || nodeType === 4 ) {\n\t\treturn elem.nodeValue;\n\t}\n\t// Do not include comment or processing instruction nodes\n\n\treturn ret;\n};\n\nExpr = Sizzle.selectors = {\n\n\t// Can be adjusted by the user\n\tcacheLength: 50,\n\n\tcreatePseudo: markFunction,\n\n\tmatch: matchExpr,\n\n\tattrHandle: {},\n\n\tfind: {},\n\n\trelative: {\n\t\t\">\": { dir: \"parentNode\", first: true },\n\t\t\" \": { dir: \"parentNode\" },\n\t\t\"+\": { dir: \"previousSibling\", first: true },\n\t\t\"~\": { dir: \"previousSibling\" }\n\t},\n\n\tpreFilter: {\n\t\t\"ATTR\": function( match ) {\n\t\t\tmatch[1] = match[1].replace( runescape, funescape );\n\n\t\t\t// Move the given value to match[3] whether quoted or unquoted\n\t\t\tmatch[3] = ( match[3] || match[4] || match[5] || \"\" ).replace( runescape, funescape );\n\n\t\t\tif ( match[2] === \"~=\" ) {\n\t\t\t\tmatch[3] = \" \" + match[3] + \" \";\n\t\t\t}\n\n\t\t\treturn match.slice( 0, 4 );\n\t\t},\n\n\t\t\"CHILD\": function( match ) {\n\t\t\t/* matches from matchExpr[\"CHILD\"]\n\t\t\t\t1 type (only|nth|...)\n\t\t\t\t2 what (child|of-type)\n\t\t\t\t3 argument (even|odd|\\d*|\\d*n([+-]\\d+)?|...)\n\t\t\t\t4 xn-component of xn+y argument ([+-]?\\d*n|)\n\t\t\t\t5 sign of xn-component\n\t\t\t\t6 x of xn-component\n\t\t\t\t7 sign of y-component\n\t\t\t\t8 y of y-component\n\t\t\t*/\n\t\t\tmatch[1] = match[1].toLowerCase();\n\n\t\t\tif ( match[1].slice( 0, 3 ) === \"nth\" ) {\n\t\t\t\t// nth-* requires argument\n\t\t\t\tif ( !match[3] ) {\n\t\t\t\t\tSizzle.error( match[0] );\n\t\t\t\t}\n\n\t\t\t\t// numeric x and y parameters for Expr.filter.CHILD\n\t\t\t\t// remember that false/true cast respectively to 0/1\n\t\t\t\tmatch[4] = +( match[4] ? match[5] + (match[6] || 1) : 2 * ( match[3] === \"even\" || match[3] === \"odd\" ) );\n\t\t\t\tmatch[5] = +( ( match[7] + match[8] ) || match[3] === \"odd\" );\n\n\t\t\t// other types prohibit arguments\n\t\t\t} else if ( match[3] ) {\n\t\t\t\tSizzle.error( match[0] );\n\t\t\t}\n\n\t\t\treturn match;\n\t\t},\n\n\t\t\"PSEUDO\": function( match ) {\n\t\t\tvar excess,\n\t\t\t\tunquoted = !match[6] && match[2];\n\n\t\t\tif ( matchExpr[\"CHILD\"].test( match[0] ) ) {\n\t\t\t\treturn null;\n\t\t\t}\n\n\t\t\t// Accept quoted arguments as-is\n\t\t\tif ( match[3] ) {\n\t\t\t\tmatch[2] = match[4] || match[5] || \"\";\n\n\t\t\t// Strip excess characters from unquoted arguments\n\t\t\t} else if ( unquoted && rpseudo.test( unquoted ) &&\n\t\t\t\t// Get excess from tokenize (recursively)\n\t\t\t\t(excess = tokenize( unquoted, true )) &&\n\t\t\t\t// advance to the next closing parenthesis\n\t\t\t\t(excess = unquoted.indexOf( \")\", unquoted.length - excess ) - unquoted.length) ) {\n\n\t\t\t\t// excess is a negative index\n\t\t\t\tmatch[0] = match[0].slice( 0, excess );\n\t\t\t\tmatch[2] = unquoted.slice( 0, excess );\n\t\t\t}\n\n\t\t\t// Return only captures needed by the pseudo filter method (type and argument)\n\t\t\treturn match.slice( 0, 3 );\n\t\t}\n\t},\n\n\tfilter: {\n\n\t\t\"TAG\": function( nodeNameSelector ) {\n\t\t\tvar nodeName = nodeNameSelector.replace( runescape, funescape ).toLowerCase();\n\t\t\treturn nodeNameSelector === \"*\" ?\n\t\t\t\tfunction() { return true; } :\n\t\t\t\tfunction( elem ) {\n\t\t\t\t\treturn elem.nodeName && elem.nodeName.toLowerCase() === nodeName;\n\t\t\t\t};\n\t\t},\n\n\t\t\"CLASS\": function( className ) {\n\t\t\tvar pattern = classCache[ className + \" \" ];\n\n\t\t\treturn pattern ||\n\t\t\t\t(pattern = new RegExp( \"(^|\" + whitespace + \")\" + className + \"(\" + whitespace + \"|$)\" )) &&\n\t\t\t\tclassCache( className, function( elem ) {\n\t\t\t\t\treturn pattern.test( typeof elem.className === \"string\" && elem.className || typeof elem.getAttribute !== \"undefined\" && elem.getAttribute(\"class\") || \"\" );\n\t\t\t\t});\n\t\t},\n\n\t\t\"ATTR\": function( name, operator, check ) {\n\t\t\treturn function( elem ) {\n\t\t\t\tvar result = Sizzle.attr( elem, name );\n\n\t\t\t\tif ( result == null ) {\n\t\t\t\t\treturn operator === \"!=\";\n\t\t\t\t}\n\t\t\t\tif ( !operator ) {\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\n\t\t\t\tresult += \"\";\n\n\t\t\t\treturn operator === \"=\" ? result === check :\n\t\t\t\t\toperator === \"!=\" ? result !== check :\n\t\t\t\t\toperator === \"^=\" ? check && result.indexOf( check ) === 0 :\n\t\t\t\t\toperator === \"*=\" ? check && result.indexOf( check ) > -1 :\n\t\t\t\t\toperator === \"$=\" ? check && result.slice( -check.length ) === check :\n\t\t\t\t\toperator === \"~=\" ? ( \" \" + result.replace( rwhitespace, \" \" ) + \" \" ).indexOf( check ) > -1 :\n\t\t\t\t\toperator === \"|=\" ? result === check || result.slice( 0, check.length + 1 ) === check + \"-\" :\n\t\t\t\t\tfalse;\n\t\t\t};\n\t\t},\n\n\t\t\"CHILD\": function( type, what, argument, first, last ) {\n\t\t\tvar simple = type.slice( 0, 3 ) !== \"nth\",\n\t\t\t\tforward = type.slice( -4 ) !== \"last\",\n\t\t\t\tofType = what === \"of-type\";\n\n\t\t\treturn first === 1 && last === 0 ?\n\n\t\t\t\t// Shortcut for :nth-*(n)\n\t\t\t\tfunction( elem ) {\n\t\t\t\t\treturn !!elem.parentNode;\n\t\t\t\t} :\n\n\t\t\t\tfunction( elem, context, xml ) {\n\t\t\t\t\tvar cache, uniqueCache, outerCache, node, nodeIndex, start,\n\t\t\t\t\t\tdir = simple !== forward ? \"nextSibling\" : \"previousSibling\",\n\t\t\t\t\t\tparent = elem.parentNode,\n\t\t\t\t\t\tname = ofType && elem.nodeName.toLowerCase(),\n\t\t\t\t\t\tuseCache = !xml && !ofType,\n\t\t\t\t\t\tdiff = false;\n\n\t\t\t\t\tif ( parent ) {\n\n\t\t\t\t\t\t// :(first|last|only)-(child|of-type)\n\t\t\t\t\t\tif ( simple ) {\n\t\t\t\t\t\t\twhile ( dir ) {\n\t\t\t\t\t\t\t\tnode = elem;\n\t\t\t\t\t\t\t\twhile ( (node = node[ dir ]) ) {\n\t\t\t\t\t\t\t\t\tif ( ofType ?\n\t\t\t\t\t\t\t\t\t\tnode.nodeName.toLowerCase() === name :\n\t\t\t\t\t\t\t\t\t\tnode.nodeType === 1 ) {\n\n\t\t\t\t\t\t\t\t\t\treturn false;\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t// Reverse direction for :only-* (if we haven't yet done so)\n\t\t\t\t\t\t\t\tstart = dir = type === \"only\" && !start && \"nextSibling\";\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\treturn true;\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\tstart = [ forward ? parent.firstChild : parent.lastChild ];\n\n\t\t\t\t\t\t// non-xml :nth-child(...) stores cache data on `parent`\n\t\t\t\t\t\tif ( forward && useCache ) {\n\n\t\t\t\t\t\t\t// Seek `elem` from a previously-cached index\n\n\t\t\t\t\t\t\t// ...in a gzip-friendly way\n\t\t\t\t\t\t\tnode = parent;\n\t\t\t\t\t\t\touterCache = node[ expando ] || (node[ expando ] = {});\n\n\t\t\t\t\t\t\t// Support: IE <9 only\n\t\t\t\t\t\t\t// Defend against cloned attroperties (jQuery gh-1709)\n\t\t\t\t\t\t\tuniqueCache = outerCache[ node.uniqueID ] ||\n\t\t\t\t\t\t\t\t(outerCache[ node.uniqueID ] = {});\n\n\t\t\t\t\t\t\tcache = uniqueCache[ type ] || [];\n\t\t\t\t\t\t\tnodeIndex = cache[ 0 ] === dirruns && cache[ 1 ];\n\t\t\t\t\t\t\tdiff = nodeIndex && cache[ 2 ];\n\t\t\t\t\t\t\tnode = nodeIndex && parent.childNodes[ nodeIndex ];\n\n\t\t\t\t\t\t\twhile ( (node = ++nodeIndex && node && node[ dir ] ||\n\n\t\t\t\t\t\t\t\t// Fallback to seeking `elem` from the start\n\t\t\t\t\t\t\t\t(diff = nodeIndex = 0) || start.pop()) ) {\n\n\t\t\t\t\t\t\t\t// When found, cache indexes on `parent` and break\n\t\t\t\t\t\t\t\tif ( node.nodeType === 1 && ++diff && node === elem ) {\n\t\t\t\t\t\t\t\t\tuniqueCache[ type ] = [ dirruns, nodeIndex, diff ];\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t// Use previously-cached element index if available\n\t\t\t\t\t\t\tif ( useCache ) {\n\t\t\t\t\t\t\t\t// ...in a gzip-friendly way\n\t\t\t\t\t\t\t\tnode = elem;\n\t\t\t\t\t\t\t\touterCache = node[ expando ] || (node[ expando ] = {});\n\n\t\t\t\t\t\t\t\t// Support: IE <9 only\n\t\t\t\t\t\t\t\t// Defend against cloned attroperties (jQuery gh-1709)\n\t\t\t\t\t\t\t\tuniqueCache = outerCache[ node.uniqueID ] ||\n\t\t\t\t\t\t\t\t\t(outerCache[ node.uniqueID ] = {});\n\n\t\t\t\t\t\t\t\tcache = uniqueCache[ type ] || [];\n\t\t\t\t\t\t\t\tnodeIndex = cache[ 0 ] === dirruns && cache[ 1 ];\n\t\t\t\t\t\t\t\tdiff = nodeIndex;\n\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\t// xml :nth-child(...)\n\t\t\t\t\t\t\t// or :nth-last-child(...) or :nth(-last)?-of-type(...)\n\t\t\t\t\t\t\tif ( diff === false ) {\n\t\t\t\t\t\t\t\t// Use the same loop as above to seek `elem` from the start\n\t\t\t\t\t\t\t\twhile ( (node = ++nodeIndex && node && node[ dir ] ||\n\t\t\t\t\t\t\t\t\t(diff = nodeIndex = 0) || start.pop()) ) {\n\n\t\t\t\t\t\t\t\t\tif ( ( ofType ?\n\t\t\t\t\t\t\t\t\t\tnode.nodeName.toLowerCase() === name :\n\t\t\t\t\t\t\t\t\t\tnode.nodeType === 1 ) &&\n\t\t\t\t\t\t\t\t\t\t++diff ) {\n\n\t\t\t\t\t\t\t\t\t\t// Cache the index of each encountered element\n\t\t\t\t\t\t\t\t\t\tif ( useCache ) {\n\t\t\t\t\t\t\t\t\t\t\touterCache = node[ expando ] || (node[ expando ] = {});\n\n\t\t\t\t\t\t\t\t\t\t\t// Support: IE <9 only\n\t\t\t\t\t\t\t\t\t\t\t// Defend against cloned attroperties (jQuery gh-1709)\n\t\t\t\t\t\t\t\t\t\t\tuniqueCache = outerCache[ node.uniqueID ] ||\n\t\t\t\t\t\t\t\t\t\t\t\t(outerCache[ node.uniqueID ] = {});\n\n\t\t\t\t\t\t\t\t\t\t\tuniqueCache[ type ] = [ dirruns, diff ];\n\t\t\t\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\t\t\t\tif ( node === elem ) {\n\t\t\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t// Incorporate the offset, then check against cycle size\n\t\t\t\t\t\tdiff -= last;\n\t\t\t\t\t\treturn diff === first || ( diff % first === 0 && diff / first >= 0 );\n\t\t\t\t\t}\n\t\t\t\t};\n\t\t},\n\n\t\t\"PSEUDO\": function( pseudo, argument ) {\n\t\t\t// pseudo-class names are case-insensitive\n\t\t\t// http://www.w3.org/TR/selectors/#pseudo-classes\n\t\t\t// Prioritize by case sensitivity in case custom pseudos are added with uppercase letters\n\t\t\t// Remember that setFilters inherits from pseudos\n\t\t\tvar args,\n\t\t\t\tfn = Expr.pseudos[ pseudo ] || Expr.setFilters[ pseudo.toLowerCase() ] ||\n\t\t\t\t\tSizzle.error( \"unsupported pseudo: \" + pseudo );\n\n\t\t\t// The user may use createPseudo to indicate that\n\t\t\t// arguments are needed to create the filter function\n\t\t\t// just as Sizzle does\n\t\t\tif ( fn[ expando ] ) {\n\t\t\t\treturn fn( argument );\n\t\t\t}\n\n\t\t\t// But maintain support for old signatures\n\t\t\tif ( fn.length > 1 ) {\n\t\t\t\targs = [ pseudo, pseudo, \"\", argument ];\n\t\t\t\treturn Expr.setFilters.hasOwnProperty( pseudo.toLowerCase() ) ?\n\t\t\t\t\tmarkFunction(function( seed, matches ) {\n\t\t\t\t\t\tvar idx,\n\t\t\t\t\t\t\tmatched = fn( seed, argument ),\n\t\t\t\t\t\t\ti = matched.length;\n\t\t\t\t\t\twhile ( i-- ) {\n\t\t\t\t\t\t\tidx = indexOf( seed, matched[i] );\n\t\t\t\t\t\t\tseed[ idx ] = !( matches[ idx ] = matched[i] );\n\t\t\t\t\t\t}\n\t\t\t\t\t}) :\n\t\t\t\t\tfunction( elem ) {\n\t\t\t\t\t\treturn fn( elem, 0, args );\n\t\t\t\t\t};\n\t\t\t}\n\n\t\t\treturn fn;\n\t\t}\n\t},\n\n\tpseudos: {\n\t\t// Potentially complex pseudos\n\t\t\"not\": markFunction(function( selector ) {\n\t\t\t// Trim the selector passed to compile\n\t\t\t// to avoid treating leading and trailing\n\t\t\t// spaces as combinators\n\t\t\tvar input = [],\n\t\t\t\tresults = [],\n\t\t\t\tmatcher = compile( selector.replace( rtrim, \"$1\" ) );\n\n\t\t\treturn matcher[ expando ] ?\n\t\t\t\tmarkFunction(function( seed, matches, context, xml ) {\n\t\t\t\t\tvar elem,\n\t\t\t\t\t\tunmatched = matcher( seed, null, xml, [] ),\n\t\t\t\t\t\ti = seed.length;\n\n\t\t\t\t\t// Match elements unmatched by `matcher`\n\t\t\t\t\twhile ( i-- ) {\n\t\t\t\t\t\tif ( (elem = unmatched[i]) ) {\n\t\t\t\t\t\t\tseed[i] = !(matches[i] = elem);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}) :\n\t\t\t\tfunction( elem, context, xml ) {\n\t\t\t\t\tinput[0] = elem;\n\t\t\t\t\tmatcher( input, null, xml, results );\n\t\t\t\t\t// Don't keep the element (issue #299)\n\t\t\t\t\tinput[0] = null;\n\t\t\t\t\treturn !results.pop();\n\t\t\t\t};\n\t\t}),\n\n\t\t\"has\": markFunction(function( selector ) {\n\t\t\treturn function( elem ) {\n\t\t\t\treturn Sizzle( selector, elem ).length > 0;\n\t\t\t};\n\t\t}),\n\n\t\t\"contains\": markFunction(function( text ) {\n\t\t\ttext = text.replace( runescape, funescape );\n\t\t\treturn function( elem ) {\n\t\t\t\treturn ( elem.textContent || elem.innerText || getText( elem ) ).indexOf( text ) > -1;\n\t\t\t};\n\t\t}),\n\n\t\t// \"Whether an element is represented by a :lang() selector\n\t\t// is based solely on the element's language value\n\t\t// being equal to the identifier C,\n\t\t// or beginning with the identifier C immediately followed by \"-\".\n\t\t// The matching of C against the element's language value is performed case-insensitively.\n\t\t// The identifier C does not have to be a valid language name.\"\n\t\t// http://www.w3.org/TR/selectors/#lang-pseudo\n\t\t\"lang\": markFunction( function( lang ) {\n\t\t\t// lang value must be a valid identifier\n\t\t\tif ( !ridentifier.test(lang || \"\") ) {\n\t\t\t\tSizzle.error( \"unsupported lang: \" + lang );\n\t\t\t}\n\t\t\tlang = lang.replace( runescape, funescape ).toLowerCase();\n\t\t\treturn function( elem ) {\n\t\t\t\tvar elemLang;\n\t\t\t\tdo {\n\t\t\t\t\tif ( (elemLang = documentIsHTML ?\n\t\t\t\t\t\telem.lang :\n\t\t\t\t\t\telem.getAttribute(\"xml:lang\") || elem.getAttribute(\"lang\")) ) {\n\n\t\t\t\t\t\telemLang = elemLang.toLowerCase();\n\t\t\t\t\t\treturn elemLang === lang || elemLang.indexOf( lang + \"-\" ) === 0;\n\t\t\t\t\t}\n\t\t\t\t} while ( (elem = elem.parentNode) && elem.nodeType === 1 );\n\t\t\t\treturn false;\n\t\t\t};\n\t\t}),\n\n\t\t// Miscellaneous\n\t\t\"target\": function( elem ) {\n\t\t\tvar hash = window.location && window.location.hash;\n\t\t\treturn hash && hash.slice( 1 ) === elem.id;\n\t\t},\n\n\t\t\"root\": function( elem ) {\n\t\t\treturn elem === docElem;\n\t\t},\n\n\t\t\"focus\": function( elem ) {\n\t\t\treturn elem === document.activeElement && (!document.hasFocus || document.hasFocus()) && !!(elem.type || elem.href || ~elem.tabIndex);\n\t\t},\n\n\t\t// Boolean properties\n\t\t\"enabled\": createDisabledPseudo( false ),\n\t\t\"disabled\": createDisabledPseudo( true ),\n\n\t\t\"checked\": function( elem ) {\n\t\t\t// In CSS3, :checked should return both checked and selected elements\n\t\t\t// http://www.w3.org/TR/2011/REC-css3-selectors-20110929/#checked\n\t\t\tvar nodeName = elem.nodeName.toLowerCase();\n\t\t\treturn (nodeName === \"input\" && !!elem.checked) || (nodeName === \"option\" && !!elem.selected);\n\t\t},\n\n\t\t\"selected\": function( elem ) {\n\t\t\t// Accessing this property makes selected-by-default\n\t\t\t// options in Safari work properly\n\t\t\tif ( elem.parentNode ) {\n\t\t\t\telem.parentNode.selectedIndex;\n\t\t\t}\n\n\t\t\treturn elem.selected === true;\n\t\t},\n\n\t\t// Contents\n\t\t\"empty\": function( elem ) {\n\t\t\t// http://www.w3.org/TR/selectors/#empty-pseudo\n\t\t\t// :empty is negated by element (1) or content nodes (text: 3; cdata: 4; entity ref: 5),\n\t\t\t//   but not by others (comment: 8; processing instruction: 7; etc.)\n\t\t\t// nodeType < 6 works because attributes (2) do not appear as children\n\t\t\tfor ( elem = elem.firstChild; elem; elem = elem.nextSibling ) {\n\t\t\t\tif ( elem.nodeType < 6 ) {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn true;\n\t\t},\n\n\t\t\"parent\": function( elem ) {\n\t\t\treturn !Expr.pseudos[\"empty\"]( elem );\n\t\t},\n\n\t\t// Element/input types\n\t\t\"header\": function( elem ) {\n\t\t\treturn rheader.test( elem.nodeName );\n\t\t},\n\n\t\t\"input\": function( elem ) {\n\t\t\treturn rinputs.test( elem.nodeName );\n\t\t},\n\n\t\t\"button\": function( elem ) {\n\t\t\tvar name = elem.nodeName.toLowerCase();\n\t\t\treturn name === \"input\" && elem.type === \"button\" || name === \"button\";\n\t\t},\n\n\t\t\"text\": function( elem ) {\n\t\t\tvar attr;\n\t\t\treturn elem.nodeName.toLowerCase() === \"input\" &&\n\t\t\t\telem.type === \"text\" &&\n\n\t\t\t\t// Support: IE<8\n\t\t\t\t// New HTML5 attribute values (e.g., \"search\") appear with elem.type === \"text\"\n\t\t\t\t( (attr = elem.getAttribute(\"type\")) == null || attr.toLowerCase() === \"text\" );\n\t\t},\n\n\t\t// Position-in-collection\n\t\t\"first\": createPositionalPseudo(function() {\n\t\t\treturn [ 0 ];\n\t\t}),\n\n\t\t\"last\": createPositionalPseudo(function( matchIndexes, length ) {\n\t\t\treturn [ length - 1 ];\n\t\t}),\n\n\t\t\"eq\": createPositionalPseudo(function( matchIndexes, length, argument ) {\n\t\t\treturn [ argument < 0 ? argument + length : argument ];\n\t\t}),\n\n\t\t\"even\": createPositionalPseudo(function( matchIndexes, length ) {\n\t\t\tvar i = 0;\n\t\t\tfor ( ; i < length; i += 2 ) {\n\t\t\t\tmatchIndexes.push( i );\n\t\t\t}\n\t\t\treturn matchIndexes;\n\t\t}),\n\n\t\t\"odd\": createPositionalPseudo(function( matchIndexes, length ) {\n\t\t\tvar i = 1;\n\t\t\tfor ( ; i < length; i += 2 ) {\n\t\t\t\tmatchIndexes.push( i );\n\t\t\t}\n\t\t\treturn matchIndexes;\n\t\t}),\n\n\t\t\"lt\": createPositionalPseudo(function( matchIndexes, length, argument ) {\n\t\t\tvar i = argument < 0 ? argument + length : argument;\n\t\t\tfor ( ; --i >= 0; ) {\n\t\t\t\tmatchIndexes.push( i );\n\t\t\t}\n\t\t\treturn matchIndexes;\n\t\t}),\n\n\t\t\"gt\": createPositionalPseudo(function( matchIndexes, length, argument ) {\n\t\t\tvar i = argument < 0 ? argument + length : argument;\n\t\t\tfor ( ; ++i < length; ) {\n\t\t\t\tmatchIndexes.push( i );\n\t\t\t}\n\t\t\treturn matchIndexes;\n\t\t})\n\t}\n};\n\nExpr.pseudos[\"nth\"] = Expr.pseudos[\"eq\"];\n\n// Add button/input type pseudos\nfor ( i in { radio: true, checkbox: true, file: true, password: true, image: true } ) {\n\tExpr.pseudos[ i ] = createInputPseudo( i );\n}\nfor ( i in { submit: true, reset: true } ) {\n\tExpr.pseudos[ i ] = createButtonPseudo( i );\n}\n\n// Easy API for creating new setFilters\nfunction setFilters() {}\nsetFilters.prototype = Expr.filters = Expr.pseudos;\nExpr.setFilters = new setFilters();\n\ntokenize = Sizzle.tokenize = function( selector, parseOnly ) {\n\tvar matched, match, tokens, type,\n\t\tsoFar, groups, preFilters,\n\t\tcached = tokenCache[ selector + \" \" ];\n\n\tif ( cached ) {\n\t\treturn parseOnly ? 0 : cached.slice( 0 );\n\t}\n\n\tsoFar = selector;\n\tgroups = [];\n\tpreFilters = Expr.preFilter;\n\n\twhile ( soFar ) {\n\n\t\t// Comma and first run\n\t\tif ( !matched || (match = rcomma.exec( soFar )) ) {\n\t\t\tif ( match ) {\n\t\t\t\t// Don't consume trailing commas as valid\n\t\t\t\tsoFar = soFar.slice( match[0].length ) || soFar;\n\t\t\t}\n\t\t\tgroups.push( (tokens = []) );\n\t\t}\n\n\t\tmatched = false;\n\n\t\t// Combinators\n\t\tif ( (match = rcombinators.exec( soFar )) ) {\n\t\t\tmatched = match.shift();\n\t\t\ttokens.push({\n\t\t\t\tvalue: matched,\n\t\t\t\t// Cast descendant combinators to space\n\t\t\t\ttype: match[0].replace( rtrim, \" \" )\n\t\t\t});\n\t\t\tsoFar = soFar.slice( matched.length );\n\t\t}\n\n\t\t// Filters\n\t\tfor ( type in Expr.filter ) {\n\t\t\tif ( (match = matchExpr[ type ].exec( soFar )) && (!preFilters[ type ] ||\n\t\t\t\t(match = preFilters[ type ]( match ))) ) {\n\t\t\t\tmatched = match.shift();\n\t\t\t\ttokens.push({\n\t\t\t\t\tvalue: matched,\n\t\t\t\t\ttype: type,\n\t\t\t\t\tmatches: match\n\t\t\t\t});\n\t\t\t\tsoFar = soFar.slice( matched.length );\n\t\t\t}\n\t\t}\n\n\t\tif ( !matched ) {\n\t\t\tbreak;\n\t\t}\n\t}\n\n\t// Return the length of the invalid excess\n\t// if we're just parsing\n\t// Otherwise, throw an error or return tokens\n\treturn parseOnly ?\n\t\tsoFar.length :\n\t\tsoFar ?\n\t\t\tSizzle.error( selector ) :\n\t\t\t// Cache the tokens\n\t\t\ttokenCache( selector, groups ).slice( 0 );\n};\n\nfunction toSelector( tokens ) {\n\tvar i = 0,\n\t\tlen = tokens.length,\n\t\tselector = \"\";\n\tfor ( ; i < len; i++ ) {\n\t\tselector += tokens[i].value;\n\t}\n\treturn selector;\n}\n\nfunction addCombinator( matcher, combinator, base ) {\n\tvar dir = combinator.dir,\n\t\tskip = combinator.next,\n\t\tkey = skip || dir,\n\t\tcheckNonElements = base && key === \"parentNode\",\n\t\tdoneName = done++;\n\n\treturn combinator.first ?\n\t\t// Check against closest ancestor/preceding element\n\t\tfunction( elem, context, xml ) {\n\t\t\twhile ( (elem = elem[ dir ]) ) {\n\t\t\t\tif ( elem.nodeType === 1 || checkNonElements ) {\n\t\t\t\t\treturn matcher( elem, context, xml );\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn false;\n\t\t} :\n\n\t\t// Check against all ancestor/preceding elements\n\t\tfunction( elem, context, xml ) {\n\t\t\tvar oldCache, uniqueCache, outerCache,\n\t\t\t\tnewCache = [ dirruns, doneName ];\n\n\t\t\t// We can't set arbitrary data on XML nodes, so they don't benefit from combinator caching\n\t\t\tif ( xml ) {\n\t\t\t\twhile ( (elem = elem[ dir ]) ) {\n\t\t\t\t\tif ( elem.nodeType === 1 || checkNonElements ) {\n\t\t\t\t\t\tif ( matcher( elem, context, xml ) ) {\n\t\t\t\t\t\t\treturn true;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\twhile ( (elem = elem[ dir ]) ) {\n\t\t\t\t\tif ( elem.nodeType === 1 || checkNonElements ) {\n\t\t\t\t\t\touterCache = elem[ expando ] || (elem[ expando ] = {});\n\n\t\t\t\t\t\t// Support: IE <9 only\n\t\t\t\t\t\t// Defend against cloned attroperties (jQuery gh-1709)\n\t\t\t\t\t\tuniqueCache = outerCache[ elem.uniqueID ] || (outerCache[ elem.uniqueID ] = {});\n\n\t\t\t\t\t\tif ( skip && skip === elem.nodeName.toLowerCase() ) {\n\t\t\t\t\t\t\telem = elem[ dir ] || elem;\n\t\t\t\t\t\t} else if ( (oldCache = uniqueCache[ key ]) &&\n\t\t\t\t\t\t\toldCache[ 0 ] === dirruns && oldCache[ 1 ] === doneName ) {\n\n\t\t\t\t\t\t\t// Assign to newCache so results back-propagate to previous elements\n\t\t\t\t\t\t\treturn (newCache[ 2 ] = oldCache[ 2 ]);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t// Reuse newcache so results back-propagate to previous elements\n\t\t\t\t\t\t\tuniqueCache[ key ] = newCache;\n\n\t\t\t\t\t\t\t// A match means we're done; a fail means we have to keep checking\n\t\t\t\t\t\t\tif ( (newCache[ 2 ] = matcher( elem, context, xml )) ) {\n\t\t\t\t\t\t\t\treturn true;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn false;\n\t\t};\n}\n\nfunction elementMatcher( matchers ) {\n\treturn matchers.length > 1 ?\n\t\tfunction( elem, context, xml ) {\n\t\t\tvar i = matchers.length;\n\t\t\twhile ( i-- ) {\n\t\t\t\tif ( !matchers[i]( elem, context, xml ) ) {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn true;\n\t\t} :\n\t\tmatchers[0];\n}\n\nfunction multipleContexts( selector, contexts, results ) {\n\tvar i = 0,\n\t\tlen = contexts.length;\n\tfor ( ; i < len; i++ ) {\n\t\tSizzle( selector, contexts[i], results );\n\t}\n\treturn results;\n}\n\nfunction condense( unmatched, map, filter, context, xml ) {\n\tvar elem,\n\t\tnewUnmatched = [],\n\t\ti = 0,\n\t\tlen = unmatched.length,\n\t\tmapped = map != null;\n\n\tfor ( ; i < len; i++ ) {\n\t\tif ( (elem = unmatched[i]) ) {\n\t\t\tif ( !filter || filter( elem, context, xml ) ) {\n\t\t\t\tnewUnmatched.push( elem );\n\t\t\t\tif ( mapped ) {\n\t\t\t\t\tmap.push( i );\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\treturn newUnmatched;\n}\n\nfunction setMatcher( preFilter, selector, matcher, postFilter, postFinder, postSelector ) {\n\tif ( postFilter && !postFilter[ expando ] ) {\n\t\tpostFilter = setMatcher( postFilter );\n\t}\n\tif ( postFinder && !postFinder[ expando ] ) {\n\t\tpostFinder = setMatcher( postFinder, postSelector );\n\t}\n\treturn markFunction(function( seed, results, context, xml ) {\n\t\tvar temp, i, elem,\n\t\t\tpreMap = [],\n\t\t\tpostMap = [],\n\t\t\tpreexisting = results.length,\n\n\t\t\t// Get initial elements from seed or context\n\t\t\telems = seed || multipleContexts( selector || \"*\", context.nodeType ? [ context ] : context, [] ),\n\n\t\t\t// Prefilter to get matcher input, preserving a map for seed-results synchronization\n\t\t\tmatcherIn = preFilter && ( seed || !selector ) ?\n\t\t\t\tcondense( elems, preMap, preFilter, context, xml ) :\n\t\t\t\telems,\n\n\t\t\tmatcherOut = matcher ?\n\t\t\t\t// If we have a postFinder, or filtered seed, or non-seed postFilter or preexisting results,\n\t\t\t\tpostFinder || ( seed ? preFilter : preexisting || postFilter ) ?\n\n\t\t\t\t\t// ...intermediate processing is necessary\n\t\t\t\t\t[] :\n\n\t\t\t\t\t// ...otherwise use results directly\n\t\t\t\t\tresults :\n\t\t\t\tmatcherIn;\n\n\t\t// Find primary matches\n\t\tif ( matcher ) {\n\t\t\tmatcher( matcherIn, matcherOut, context, xml );\n\t\t}\n\n\t\t// Apply postFilter\n\t\tif ( postFilter ) {\n\t\t\ttemp = condense( matcherOut, postMap );\n\t\t\tpostFilter( temp, [], context, xml );\n\n\t\t\t// Un-match failing elements by moving them back to matcherIn\n\t\t\ti = temp.length;\n\t\t\twhile ( i-- ) {\n\t\t\t\tif ( (elem = temp[i]) ) {\n\t\t\t\t\tmatcherOut[ postMap[i] ] = !(matcherIn[ postMap[i] ] = elem);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif ( seed ) {\n\t\t\tif ( postFinder || preFilter ) {\n\t\t\t\tif ( postFinder ) {\n\t\t\t\t\t// Get the final matcherOut by condensing this intermediate into postFinder contexts\n\t\t\t\t\ttemp = [];\n\t\t\t\t\ti = matcherOut.length;\n\t\t\t\t\twhile ( i-- ) {\n\t\t\t\t\t\tif ( (elem = matcherOut[i]) ) {\n\t\t\t\t\t\t\t// Restore matcherIn since elem is not yet a final match\n\t\t\t\t\t\t\ttemp.push( (matcherIn[i] = elem) );\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tpostFinder( null, (matcherOut = []), temp, xml );\n\t\t\t\t}\n\n\t\t\t\t// Move matched elements from seed to results to keep them synchronized\n\t\t\t\ti = matcherOut.length;\n\t\t\t\twhile ( i-- ) {\n\t\t\t\t\tif ( (elem = matcherOut[i]) &&\n\t\t\t\t\t\t(temp = postFinder ? indexOf( seed, elem ) : preMap[i]) > -1 ) {\n\n\t\t\t\t\t\tseed[temp] = !(results[temp] = elem);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t// Add elements to results, through postFinder if defined\n\t\t} else {\n\t\t\tmatcherOut = condense(\n\t\t\t\tmatcherOut === results ?\n\t\t\t\t\tmatcherOut.splice( preexisting, matcherOut.length ) :\n\t\t\t\t\tmatcherOut\n\t\t\t);\n\t\t\tif ( postFinder ) {\n\t\t\t\tpostFinder( null, results, matcherOut, xml );\n\t\t\t} else {\n\t\t\t\tpush.apply( results, matcherOut );\n\t\t\t}\n\t\t}\n\t});\n}\n\nfunction matcherFromTokens( tokens ) {\n\tvar checkContext, matcher, j,\n\t\tlen = tokens.length,\n\t\tleadingRelative = Expr.relative[ tokens[0].type ],\n\t\timplicitRelative = leadingRelative || Expr.relative[\" \"],\n\t\ti = leadingRelative ? 1 : 0,\n\n\t\t// The foundational matcher ensures that elements are reachable from top-level context(s)\n\t\tmatchContext = addCombinator( function( elem ) {\n\t\t\treturn elem === checkContext;\n\t\t}, implicitRelative, true ),\n\t\tmatchAnyContext = addCombinator( function( elem ) {\n\t\t\treturn indexOf( checkContext, elem ) > -1;\n\t\t}, implicitRelative, true ),\n\t\tmatchers = [ function( elem, context, xml ) {\n\t\t\tvar ret = ( !leadingRelative && ( xml || context !== outermostContext ) ) || (\n\t\t\t\t(checkContext = context).nodeType ?\n\t\t\t\t\tmatchContext( elem, context, xml ) :\n\t\t\t\t\tmatchAnyContext( elem, context, xml ) );\n\t\t\t// Avoid hanging onto element (issue #299)\n\t\t\tcheckContext = null;\n\t\t\treturn ret;\n\t\t} ];\n\n\tfor ( ; i < len; i++ ) {\n\t\tif ( (matcher = Expr.relative[ tokens[i].type ]) ) {\n\t\t\tmatchers = [ addCombinator(elementMatcher( matchers ), matcher) ];\n\t\t} else {\n\t\t\tmatcher = Expr.filter[ tokens[i].type ].apply( null, tokens[i].matches );\n\n\t\t\t// Return special upon seeing a positional matcher\n\t\t\tif ( matcher[ expando ] ) {\n\t\t\t\t// Find the next relative operator (if any) for proper handling\n\t\t\t\tj = ++i;\n\t\t\t\tfor ( ; j < len; j++ ) {\n\t\t\t\t\tif ( Expr.relative[ tokens[j].type ] ) {\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\treturn setMatcher(\n\t\t\t\t\ti > 1 && elementMatcher( matchers ),\n\t\t\t\t\ti > 1 && toSelector(\n\t\t\t\t\t\t// If the preceding token was a descendant combinator, insert an implicit any-element `*`\n\t\t\t\t\t\ttokens.slice( 0, i - 1 ).concat({ value: tokens[ i - 2 ].type === \" \" ? \"*\" : \"\" })\n\t\t\t\t\t).replace( rtrim, \"$1\" ),\n\t\t\t\t\tmatcher,\n\t\t\t\t\ti < j && matcherFromTokens( tokens.slice( i, j ) ),\n\t\t\t\t\tj < len && matcherFromTokens( (tokens = tokens.slice( j )) ),\n\t\t\t\t\tj < len && toSelector( tokens )\n\t\t\t\t);\n\t\t\t}\n\t\t\tmatchers.push( matcher );\n\t\t}\n\t}\n\n\treturn elementMatcher( matchers );\n}\n\nfunction matcherFromGroupMatchers( elementMatchers, setMatchers ) {\n\tvar bySet = setMatchers.length > 0,\n\t\tbyElement = elementMatchers.length > 0,\n\t\tsuperMatcher = function( seed, context, xml, results, outermost ) {\n\t\t\tvar elem, j, matcher,\n\t\t\t\tmatchedCount = 0,\n\t\t\t\ti = \"0\",\n\t\t\t\tunmatched = seed && [],\n\t\t\t\tsetMatched = [],\n\t\t\t\tcontextBackup = outermostContext,\n\t\t\t\t// We must always have either seed elements or outermost context\n\t\t\t\telems = seed || byElement && Expr.find[\"TAG\"]( \"*\", outermost ),\n\t\t\t\t// Use integer dirruns iff this is the outermost matcher\n\t\t\t\tdirrunsUnique = (dirruns += contextBackup == null ? 1 : Math.random() || 0.1),\n\t\t\t\tlen = elems.length;\n\n\t\t\tif ( outermost ) {\n\t\t\t\toutermostContext = context === document || context || outermost;\n\t\t\t}\n\n\t\t\t// Add elements passing elementMatchers directly to results\n\t\t\t// Support: IE<9, Safari\n\t\t\t// Tolerate NodeList properties (IE: \"length\"; Safari: <number>) matching elements by id\n\t\t\tfor ( ; i !== len && (elem = elems[i]) != null; i++ ) {\n\t\t\t\tif ( byElement && elem ) {\n\t\t\t\t\tj = 0;\n\t\t\t\t\tif ( !context && elem.ownerDocument !== document ) {\n\t\t\t\t\t\tsetDocument( elem );\n\t\t\t\t\t\txml = !documentIsHTML;\n\t\t\t\t\t}\n\t\t\t\t\twhile ( (matcher = elementMatchers[j++]) ) {\n\t\t\t\t\t\tif ( matcher( elem, context || document, xml) ) {\n\t\t\t\t\t\t\tresults.push( elem );\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif ( outermost ) {\n\t\t\t\t\t\tdirruns = dirrunsUnique;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// Track unmatched elements for set filters\n\t\t\t\tif ( bySet ) {\n\t\t\t\t\t// They will have gone through all possible matchers\n\t\t\t\t\tif ( (elem = !matcher && elem) ) {\n\t\t\t\t\t\tmatchedCount--;\n\t\t\t\t\t}\n\n\t\t\t\t\t// Lengthen the array for every element, matched or not\n\t\t\t\t\tif ( seed ) {\n\t\t\t\t\t\tunmatched.push( elem );\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// `i` is now the count of elements visited above, and adding it to `matchedCount`\n\t\t\t// makes the latter nonnegative.\n\t\t\tmatchedCount += i;\n\n\t\t\t// Apply set filters to unmatched elements\n\t\t\t// NOTE: This can be skipped if there are no unmatched elements (i.e., `matchedCount`\n\t\t\t// equals `i`), unless we didn't visit _any_ elements in the above loop because we have\n\t\t\t// no element matchers and no seed.\n\t\t\t// Incrementing an initially-string \"0\" `i` allows `i` to remain a string only in that\n\t\t\t// case, which will result in a \"00\" `matchedCount` that differs from `i` but is also\n\t\t\t// numerically zero.\n\t\t\tif ( bySet && i !== matchedCount ) {\n\t\t\t\tj = 0;\n\t\t\t\twhile ( (matcher = setMatchers[j++]) ) {\n\t\t\t\t\tmatcher( unmatched, setMatched, context, xml );\n\t\t\t\t}\n\n\t\t\t\tif ( seed ) {\n\t\t\t\t\t// Reintegrate element matches to eliminate the need for sorting\n\t\t\t\t\tif ( matchedCount > 0 ) {\n\t\t\t\t\t\twhile ( i-- ) {\n\t\t\t\t\t\t\tif ( !(unmatched[i] || setMatched[i]) ) {\n\t\t\t\t\t\t\t\tsetMatched[i] = pop.call( results );\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\t// Discard index placeholder values to get only actual matches\n\t\t\t\t\tsetMatched = condense( setMatched );\n\t\t\t\t}\n\n\t\t\t\t// Add matches to results\n\t\t\t\tpush.apply( results, setMatched );\n\n\t\t\t\t// Seedless set matches succeeding multiple successful matchers stipulate sorting\n\t\t\t\tif ( outermost && !seed && setMatched.length > 0 &&\n\t\t\t\t\t( matchedCount + setMatchers.length ) > 1 ) {\n\n\t\t\t\t\tSizzle.uniqueSort( results );\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Override manipulation of globals by nested matchers\n\t\t\tif ( outermost ) {\n\t\t\t\tdirruns = dirrunsUnique;\n\t\t\t\toutermostContext = contextBackup;\n\t\t\t}\n\n\t\t\treturn unmatched;\n\t\t};\n\n\treturn bySet ?\n\t\tmarkFunction( superMatcher ) :\n\t\tsuperMatcher;\n}\n\ncompile = Sizzle.compile = function( selector, match /* Internal Use Only */ ) {\n\tvar i,\n\t\tsetMatchers = [],\n\t\telementMatchers = [],\n\t\tcached = compilerCache[ selector + \" \" ];\n\n\tif ( !cached ) {\n\t\t// Generate a function of recursive functions that can be used to check each element\n\t\tif ( !match ) {\n\t\t\tmatch = tokenize( selector );\n\t\t}\n\t\ti = match.length;\n\t\twhile ( i-- ) {\n\t\t\tcached = matcherFromTokens( match[i] );\n\t\t\tif ( cached[ expando ] ) {\n\t\t\t\tsetMatchers.push( cached );\n\t\t\t} else {\n\t\t\t\telementMatchers.push( cached );\n\t\t\t}\n\t\t}\n\n\t\t// Cache the compiled function\n\t\tcached = compilerCache( selector, matcherFromGroupMatchers( elementMatchers, setMatchers ) );\n\n\t\t// Save selector and tokenization\n\t\tcached.selector = selector;\n\t}\n\treturn cached;\n};\n\n/**\n * A low-level selection function that works with Sizzle's compiled\n *  selector functions\n * @param {String|Function} selector A selector or a pre-compiled\n *  selector function built with Sizzle.compile\n * @param {Element} context\n * @param {Array} [results]\n * @param {Array} [seed] A set of elements to match against\n */\nselect = Sizzle.select = function( selector, context, results, seed ) {\n\tvar i, tokens, token, type, find,\n\t\tcompiled = typeof selector === \"function\" && selector,\n\t\tmatch = !seed && tokenize( (selector = compiled.selector || selector) );\n\n\tresults = results || [];\n\n\t// Try to minimize operations if there is only one selector in the list and no seed\n\t// (the latter of which guarantees us context)\n\tif ( match.length === 1 ) {\n\n\t\t// Reduce context if the leading compound selector is an ID\n\t\ttokens = match[0] = match[0].slice( 0 );\n\t\tif ( tokens.length > 2 && (token = tokens[0]).type === \"ID\" &&\n\t\t\t\tcontext.nodeType === 9 && documentIsHTML && Expr.relative[ tokens[1].type ] ) {\n\n\t\t\tcontext = ( Expr.find[\"ID\"]( token.matches[0].replace(runescape, funescape), context ) || [] )[0];\n\t\t\tif ( !context ) {\n\t\t\t\treturn results;\n\n\t\t\t// Precompiled matchers will still verify ancestry, so step up a level\n\t\t\t} else if ( compiled ) {\n\t\t\t\tcontext = context.parentNode;\n\t\t\t}\n\n\t\t\tselector = selector.slice( tokens.shift().value.length );\n\t\t}\n\n\t\t// Fetch a seed set for right-to-left matching\n\t\ti = matchExpr[\"needsContext\"].test( selector ) ? 0 : tokens.length;\n\t\twhile ( i-- ) {\n\t\t\ttoken = tokens[i];\n\n\t\t\t// Abort if we hit a combinator\n\t\t\tif ( Expr.relative[ (type = token.type) ] ) {\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif ( (find = Expr.find[ type ]) ) {\n\t\t\t\t// Search, expanding context for leading sibling combinators\n\t\t\t\tif ( (seed = find(\n\t\t\t\t\ttoken.matches[0].replace( runescape, funescape ),\n\t\t\t\t\trsibling.test( tokens[0].type ) && testContext( context.parentNode ) || context\n\t\t\t\t)) ) {\n\n\t\t\t\t\t// If seed is empty or no tokens remain, we can return early\n\t\t\t\t\ttokens.splice( i, 1 );\n\t\t\t\t\tselector = seed.length && toSelector( tokens );\n\t\t\t\t\tif ( !selector ) {\n\t\t\t\t\t\tpush.apply( results, seed );\n\t\t\t\t\t\treturn results;\n\t\t\t\t\t}\n\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// Compile and execute a filtering function if one is not provided\n\t// Provide `match` to avoid retokenization if we modified the selector above\n\t( compiled || compile( selector, match ) )(\n\t\tseed,\n\t\tcontext,\n\t\t!documentIsHTML,\n\t\tresults,\n\t\t!context || rsibling.test( selector ) && testContext( context.parentNode ) || context\n\t);\n\treturn results;\n};\n\n// One-time assignments\n\n// Sort stability\nsupport.sortStable = expando.split(\"\").sort( sortOrder ).join(\"\") === expando;\n\n// Support: Chrome 14-35+\n// Always assume duplicates if they aren't passed to the comparison function\nsupport.detectDuplicates = !!hasDuplicate;\n\n// Initialize against the default document\nsetDocument();\n\n// Support: Webkit<537.32 - Safari 6.0.3/Chrome 25 (fixed in Chrome 27)\n// Detached nodes confoundingly follow *each other*\nsupport.sortDetached = assert(function( el ) {\n\t// Should return 1, but returns 4 (following)\n\treturn el.compareDocumentPosition( document.createElement(\"fieldset\") ) & 1;\n});\n\n// Support: IE<8\n// Prevent attribute/property \"interpolation\"\n// https://msdn.microsoft.com/en-us/library/ms536429%28VS.85%29.aspx\nif ( !assert(function( el ) {\n\tel.innerHTML = \"<a href='#'></a>\";\n\treturn el.firstChild.getAttribute(\"href\") === \"#\" ;\n}) ) {\n\taddHandle( \"type|href|height|width\", function( elem, name, isXML ) {\n\t\tif ( !isXML ) {\n\t\t\treturn elem.getAttribute( name, name.toLowerCase() === \"type\" ? 1 : 2 );\n\t\t}\n\t});\n}\n\n// Support: IE<9\n// Use defaultValue in place of getAttribute(\"value\")\nif ( !support.attributes || !assert(function( el ) {\n\tel.innerHTML = \"<input/>\";\n\tel.firstChild.setAttribute( \"value\", \"\" );\n\treturn el.firstChild.getAttribute( \"value\" ) === \"\";\n}) ) {\n\taddHandle( \"value\", function( elem, name, isXML ) {\n\t\tif ( !isXML && elem.nodeName.toLowerCase() === \"input\" ) {\n\t\t\treturn elem.defaultValue;\n\t\t}\n\t});\n}\n\n// Support: IE<9\n// Use getAttributeNode to fetch booleans when getAttribute lies\nif ( !assert(function( el ) {\n\treturn el.getAttribute(\"disabled\") == null;\n}) ) {\n\taddHandle( booleans, function( elem, name, isXML ) {\n\t\tvar val;\n\t\tif ( !isXML ) {\n\t\t\treturn elem[ name ] === true ? name.toLowerCase() :\n\t\t\t\t\t(val = elem.getAttributeNode( name )) && val.specified ?\n\t\t\t\t\tval.value :\n\t\t\t\tnull;\n\t\t}\n\t});\n}\n\nreturn Sizzle;\n\n})( window );\n\n\n\njQuery.find = Sizzle;\njQuery.expr = Sizzle.selectors;\n\n// Deprecated\njQuery.expr[ \":\" ] = jQuery.expr.pseudos;\njQuery.uniqueSort = jQuery.unique = Sizzle.uniqueSort;\njQuery.text = Sizzle.getText;\njQuery.isXMLDoc = Sizzle.isXML;\njQuery.contains = Sizzle.contains;\njQuery.escapeSelector = Sizzle.escape;\n\n\n\n\nvar dir = function( elem, dir, until ) {\n\tvar matched = [],\n\t\ttruncate = until !== undefined;\n\n\twhile ( ( elem = elem[ dir ] ) && elem.nodeType !== 9 ) {\n\t\tif ( elem.nodeType === 1 ) {\n\t\t\tif ( truncate && jQuery( elem ).is( until ) ) {\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tmatched.push( elem );\n\t\t}\n\t}\n\treturn matched;\n};\n\n\nvar siblings = function( n, elem ) {\n\tvar matched = [];\n\n\tfor ( ; n; n = n.nextSibling ) {\n\t\tif ( n.nodeType === 1 && n !== elem ) {\n\t\t\tmatched.push( n );\n\t\t}\n\t}\n\n\treturn matched;\n};\n\n\nvar rneedsContext = jQuery.expr.match.needsContext;\n\nvar rsingleTag = ( /^<([a-z][^\\/\\0>:\\x20\\t\\r\\n\\f]*)[\\x20\\t\\r\\n\\f]*\\/?>(?:<\\/\\1>|)$/i );\n\n\n\nvar risSimple = /^.[^:#\\[\\.,]*$/;\n\n// Implement the identical functionality for filter and not\nfunction winnow( elements, qualifier, not ) {\n\tif ( jQuery.isFunction( qualifier ) ) {\n\t\treturn jQuery.grep( elements, function( elem, i ) {\n\t\t\treturn !!qualifier.call( elem, i, elem ) !== not;\n\t\t} );\n\t}\n\n\t// Single element\n\tif ( qualifier.nodeType ) {\n\t\treturn jQuery.grep( elements, function( elem ) {\n\t\t\treturn ( elem === qualifier ) !== not;\n\t\t} );\n\t}\n\n\t// Arraylike of elements (jQuery, arguments, Array)\n\tif ( typeof qualifier !== \"string\" ) {\n\t\treturn jQuery.grep( elements, function( elem ) {\n\t\t\treturn ( indexOf.call( qualifier, elem ) > -1 ) !== not;\n\t\t} );\n\t}\n\n\t// Simple selector that can be filtered directly, removing non-Elements\n\tif ( risSimple.test( qualifier ) ) {\n\t\treturn jQuery.filter( qualifier, elements, not );\n\t}\n\n\t// Complex selector, compare the two sets, removing non-Elements\n\tqualifier = jQuery.filter( qualifier, elements );\n\treturn jQuery.grep( elements, function( elem ) {\n\t\treturn ( indexOf.call( qualifier, elem ) > -1 ) !== not && elem.nodeType === 1;\n\t} );\n}\n\njQuery.filter = function( expr, elems, not ) {\n\tvar elem = elems[ 0 ];\n\n\tif ( not ) {\n\t\texpr = \":not(\" + expr + \")\";\n\t}\n\n\tif ( elems.length === 1 && elem.nodeType === 1 ) {\n\t\treturn jQuery.find.matchesSelector( elem, expr ) ? [ elem ] : [];\n\t}\n\n\treturn jQuery.find.matches( expr, jQuery.grep( elems, function( elem ) {\n\t\treturn elem.nodeType === 1;\n\t} ) );\n};\n\njQuery.fn.extend( {\n\tfind: function( selector ) {\n\t\tvar i, ret,\n\t\t\tlen = this.length,\n\t\t\tself = this;\n\n\t\tif ( typeof selector !== \"string\" ) {\n\t\t\treturn this.pushStack( jQuery( selector ).filter( function() {\n\t\t\t\tfor ( i = 0; i < len; i++ ) {\n\t\t\t\t\tif ( jQuery.contains( self[ i ], this ) ) {\n\t\t\t\t\t\treturn true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} ) );\n\t\t}\n\n\t\tret = this.pushStack( [] );\n\n\t\tfor ( i = 0; i < len; i++ ) {\n\t\t\tjQuery.find( selector, self[ i ], ret );\n\t\t}\n\n\t\treturn len > 1 ? jQuery.uniqueSort( ret ) : ret;\n\t},\n\tfilter: function( selector ) {\n\t\treturn this.pushStack( winnow( this, selector || [], false ) );\n\t},\n\tnot: function( selector ) {\n\t\treturn this.pushStack( winnow( this, selector || [], true ) );\n\t},\n\tis: function( selector ) {\n\t\treturn !!winnow(\n\t\t\tthis,\n\n\t\t\t// If this is a positional/relative selector, check membership in the returned set\n\t\t\t// so $(\"p:first\").is(\"p:last\") won't return true for a doc with two \"p\".\n\t\t\ttypeof selector === \"string\" && rneedsContext.test( selector ) ?\n\t\t\t\tjQuery( selector ) :\n\t\t\t\tselector || [],\n\t\t\tfalse\n\t\t).length;\n\t}\n} );\n\n\n// Initialize a jQuery object\n\n\n// A central reference to the root jQuery(document)\nvar rootjQuery,\n\n\t// A simple way to check for HTML strings\n\t// Prioritize #id over <tag> to avoid XSS via location.hash (#9521)\n\t// Strict HTML recognition (#11290: must start with <)\n\t// Shortcut simple #id case for speed\n\trquickExpr = /^(?:\\s*(<[\\w\\W]+>)[^>]*|#([\\w-]+))$/,\n\n\tinit = jQuery.fn.init = function( selector, context, root ) {\n\t\tvar match, elem;\n\n\t\t// HANDLE: $(\"\"), $(null), $(undefined), $(false)\n\t\tif ( !selector ) {\n\t\t\treturn this;\n\t\t}\n\n\t\t// Method init() accepts an alternate rootjQuery\n\t\t// so migrate can support jQuery.sub (gh-2101)\n\t\troot = root || rootjQuery;\n\n\t\t// Handle HTML strings\n\t\tif ( typeof selector === \"string\" ) {\n\t\t\tif ( selector[ 0 ] === \"<\" &&\n\t\t\t\tselector[ selector.length - 1 ] === \">\" &&\n\t\t\t\tselector.length >= 3 ) {\n\n\t\t\t\t// Assume that strings that start and end with <> are HTML and skip the regex check\n\t\t\t\tmatch = [ null, selector, null ];\n\n\t\t\t} else {\n\t\t\t\tmatch = rquickExpr.exec( selector );\n\t\t\t}\n\n\t\t\t// Match html or make sure no context is specified for #id\n\t\t\tif ( match && ( match[ 1 ] || !context ) ) {\n\n\t\t\t\t// HANDLE: $(html) -> $(array)\n\t\t\t\tif ( match[ 1 ] ) {\n\t\t\t\t\tcontext = context instanceof jQuery ? context[ 0 ] : context;\n\n\t\t\t\t\t// Option to run scripts is true for back-compat\n\t\t\t\t\t// Intentionally let the error be thrown if parseHTML is not present\n\t\t\t\t\tjQuery.merge( this, jQuery.parseHTML(\n\t\t\t\t\t\tmatch[ 1 ],\n\t\t\t\t\t\tcontext && context.nodeType ? context.ownerDocument || context : document,\n\t\t\t\t\t\ttrue\n\t\t\t\t\t) );\n\n\t\t\t\t\t// HANDLE: $(html, props)\n\t\t\t\t\tif ( rsingleTag.test( match[ 1 ] ) && jQuery.isPlainObject( context ) ) {\n\t\t\t\t\t\tfor ( match in context ) {\n\n\t\t\t\t\t\t\t// Properties of context are called as methods if possible\n\t\t\t\t\t\t\tif ( jQuery.isFunction( this[ match ] ) ) {\n\t\t\t\t\t\t\t\tthis[ match ]( context[ match ] );\n\n\t\t\t\t\t\t\t// ...and otherwise set as attributes\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tthis.attr( match, context[ match ] );\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\treturn this;\n\n\t\t\t\t// HANDLE: $(#id)\n\t\t\t\t} else {\n\t\t\t\t\telem = document.getElementById( match[ 2 ] );\n\n\t\t\t\t\tif ( elem ) {\n\n\t\t\t\t\t\t// Inject the element directly into the jQuery object\n\t\t\t\t\t\tthis[ 0 ] = elem;\n\t\t\t\t\t\tthis.length = 1;\n\t\t\t\t\t}\n\t\t\t\t\treturn this;\n\t\t\t\t}\n\n\t\t\t// HANDLE: $(expr, $(...))\n\t\t\t} else if ( !context || context.jquery ) {\n\t\t\t\treturn ( context || root ).find( selector );\n\n\t\t\t// HANDLE: $(expr, context)\n\t\t\t// (which is just equivalent to: $(context).find(expr)\n\t\t\t} else {\n\t\t\t\treturn this.constructor( context ).find( selector );\n\t\t\t}\n\n\t\t// HANDLE: $(DOMElement)\n\t\t} else if ( selector.nodeType ) {\n\t\t\tthis[ 0 ] = selector;\n\t\t\tthis.length = 1;\n\t\t\treturn this;\n\n\t\t// HANDLE: $(function)\n\t\t// Shortcut for document ready\n\t\t} else if ( jQuery.isFunction( selector ) ) {\n\t\t\treturn root.ready !== undefined ?\n\t\t\t\troot.ready( selector ) :\n\n\t\t\t\t// Execute immediately if ready is not present\n\t\t\t\tselector( jQuery );\n\t\t}\n\n\t\treturn jQuery.makeArray( selector, this );\n\t};\n\n// Give the init function the jQuery prototype for later instantiation\ninit.prototype = jQuery.fn;\n\n// Initialize central reference\nrootjQuery = jQuery( document );\n\n\nvar rparentsprev = /^(?:parents|prev(?:Until|All))/,\n\n\t// Methods guaranteed to produce a unique set when starting from a unique set\n\tguaranteedUnique = {\n\t\tchildren: true,\n\t\tcontents: true,\n\t\tnext: true,\n\t\tprev: true\n\t};\n\njQuery.fn.extend( {\n\thas: function( target ) {\n\t\tvar targets = jQuery( target, this ),\n\t\t\tl = targets.length;\n\n\t\treturn this.filter( function() {\n\t\t\tvar i = 0;\n\t\t\tfor ( ; i < l; i++ ) {\n\t\t\t\tif ( jQuery.contains( this, targets[ i ] ) ) {\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t} );\n\t},\n\n\tclosest: function( selectors, context ) {\n\t\tvar cur,\n\t\t\ti = 0,\n\t\t\tl = this.length,\n\t\t\tmatched = [],\n\t\t\ttargets = typeof selectors !== \"string\" && jQuery( selectors );\n\n\t\t// Positional selectors never match, since there's no _selection_ context\n\t\tif ( !rneedsContext.test( selectors ) ) {\n\t\t\tfor ( ; i < l; i++ ) {\n\t\t\t\tfor ( cur = this[ i ]; cur && cur !== context; cur = cur.parentNode ) {\n\n\t\t\t\t\t// Always skip document fragments\n\t\t\t\t\tif ( cur.nodeType < 11 && ( targets ?\n\t\t\t\t\t\ttargets.index( cur ) > -1 :\n\n\t\t\t\t\t\t// Don't pass non-elements to Sizzle\n\t\t\t\t\t\tcur.nodeType === 1 &&\n\t\t\t\t\t\t\tjQuery.find.matchesSelector( cur, selectors ) ) ) {\n\n\t\t\t\t\t\tmatched.push( cur );\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn this.pushStack( matched.length > 1 ? jQuery.uniqueSort( matched ) : matched );\n\t},\n\n\t// Determine the position of an element within the set\n\tindex: function( elem ) {\n\n\t\t// No argument, return index in parent\n\t\tif ( !elem ) {\n\t\t\treturn ( this[ 0 ] && this[ 0 ].parentNode ) ? this.first().prevAll().length : -1;\n\t\t}\n\n\t\t// Index in selector\n\t\tif ( typeof elem === \"string\" ) {\n\t\t\treturn indexOf.call( jQuery( elem ), this[ 0 ] );\n\t\t}\n\n\t\t// Locate the position of the desired element\n\t\treturn indexOf.call( this,\n\n\t\t\t// If it receives a jQuery object, the first element is used\n\t\t\telem.jquery ? elem[ 0 ] : elem\n\t\t);\n\t},\n\n\tadd: function( selector, context ) {\n\t\treturn this.pushStack(\n\t\t\tjQuery.uniqueSort(\n\t\t\t\tjQuery.merge( this.get(), jQuery( selector, context ) )\n\t\t\t)\n\t\t);\n\t},\n\n\taddBack: function( selector ) {\n\t\treturn this.add( selector == null ?\n\t\t\tthis.prevObject : this.prevObject.filter( selector )\n\t\t);\n\t}\n} );\n\nfunction sibling( cur, dir ) {\n\twhile ( ( cur = cur[ dir ] ) && cur.nodeType !== 1 ) {}\n\treturn cur;\n}\n\njQuery.each( {\n\tparent: function( elem ) {\n\t\tvar parent = elem.parentNode;\n\t\treturn parent && parent.nodeType !== 11 ? parent : null;\n\t},\n\tparents: function( elem ) {\n\t\treturn dir( elem, \"parentNode\" );\n\t},\n\tparentsUntil: function( elem, i, until ) {\n\t\treturn dir( elem, \"parentNode\", until );\n\t},\n\tnext: function( elem ) {\n\t\treturn sibling( elem, \"nextSibling\" );\n\t},\n\tprev: function( elem ) {\n\t\treturn sibling( elem, \"previousSibling\" );\n\t},\n\tnextAll: function( elem ) {\n\t\treturn dir( elem, \"nextSibling\" );\n\t},\n\tprevAll: function( elem ) {\n\t\treturn dir( elem, \"previousSibling\" );\n\t},\n\tnextUntil: function( elem, i, until ) {\n\t\treturn dir( elem, \"nextSibling\", until );\n\t},\n\tprevUntil: function( elem, i, until ) {\n\t\treturn dir( elem, \"previousSibling\", until );\n\t},\n\tsiblings: function( elem ) {\n\t\treturn siblings( ( elem.parentNode || {} ).firstChild, elem );\n\t},\n\tchildren: function( elem ) {\n\t\treturn siblings( elem.firstChild );\n\t},\n\tcontents: function( elem ) {\n\t\treturn elem.contentDocument || jQuery.merge( [], elem.childNodes );\n\t}\n}, function( name, fn ) {\n\tjQuery.fn[ name ] = function( until, selector ) {\n\t\tvar matched = jQuery.map( this, fn, until );\n\n\t\tif ( name.slice( -5 ) !== \"Until\" ) {\n\t\t\tselector = until;\n\t\t}\n\n\t\tif ( selector && typeof selector === \"string\" ) {\n\t\t\tmatched = jQuery.filter( selector, matched );\n\t\t}\n\n\t\tif ( this.length > 1 ) {\n\n\t\t\t// Remove duplicates\n\t\t\tif ( !guaranteedUnique[ name ] ) {\n\t\t\t\tjQuery.uniqueSort( matched );\n\t\t\t}\n\n\t\t\t// Reverse order for parents* and prev-derivatives\n\t\t\tif ( rparentsprev.test( name ) ) {\n\t\t\t\tmatched.reverse();\n\t\t\t}\n\t\t}\n\n\t\treturn this.pushStack( matched );\n\t};\n} );\nvar rnothtmlwhite = ( /[^\\x20\\t\\r\\n\\f]+/g );\n\n\n\n// Convert String-formatted options into Object-formatted ones\nfunction createOptions( options ) {\n\tvar object = {};\n\tjQuery.each( options.match( rnothtmlwhite ) || [], function( _, flag ) {\n\t\tobject[ flag ] = true;\n\t} );\n\treturn object;\n}\n\n/*\n * Create a callback list using the following parameters:\n *\n *\toptions: an optional list of space-separated options that will change how\n *\t\t\tthe callback list behaves or a more traditional option object\n *\n * By default a callback list will act like an event callback list and can be\n * \"fired\" multiple times.\n *\n * Possible options:\n *\n *\tonce:\t\t\twill ensure the callback list can only be fired once (like a Deferred)\n *\n *\tmemory:\t\t\twill keep track of previous values and will call any callback added\n *\t\t\t\t\tafter the list has been fired right away with the latest \"memorized\"\n *\t\t\t\t\tvalues (like a Deferred)\n *\n *\tunique:\t\t\twill ensure a callback can only be added once (no duplicate in the list)\n *\n *\tstopOnFalse:\tinterrupt callings when a callback returns false\n *\n */\njQuery.Callbacks = function( options ) {\n\n\t// Convert options from String-formatted to Object-formatted if needed\n\t// (we check in cache first)\n\toptions = typeof options === \"string\" ?\n\t\tcreateOptions( options ) :\n\t\tjQuery.extend( {}, options );\n\n\tvar // Flag to know if list is currently firing\n\t\tfiring,\n\n\t\t// Last fire value for non-forgettable lists\n\t\tmemory,\n\n\t\t// Flag to know if list was already fired\n\t\tfired,\n\n\t\t// Flag to prevent firing\n\t\tlocked,\n\n\t\t// Actual callback list\n\t\tlist = [],\n\n\t\t// Queue of execution data for repeatable lists\n\t\tqueue = [],\n\n\t\t// Index of currently firing callback (modified by add/remove as needed)\n\t\tfiringIndex = -1,\n\n\t\t// Fire callbacks\n\t\tfire = function() {\n\n\t\t\t// Enforce single-firing\n\t\t\tlocked = options.once;\n\n\t\t\t// Execute callbacks for all pending executions,\n\t\t\t// respecting firingIndex overrides and runtime changes\n\t\t\tfired = firing = true;\n\t\t\tfor ( ; queue.length; firingIndex = -1 ) {\n\t\t\t\tmemory = queue.shift();\n\t\t\t\twhile ( ++firingIndex < list.length ) {\n\n\t\t\t\t\t// Run callback and check for early termination\n\t\t\t\t\tif ( list[ firingIndex ].apply( memory[ 0 ], memory[ 1 ] ) === false &&\n\t\t\t\t\t\toptions.stopOnFalse ) {\n\n\t\t\t\t\t\t// Jump to end and forget the data so .add doesn't re-fire\n\t\t\t\t\t\tfiringIndex = list.length;\n\t\t\t\t\t\tmemory = false;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Forget the data if we're done with it\n\t\t\tif ( !options.memory ) {\n\t\t\t\tmemory = false;\n\t\t\t}\n\n\t\t\tfiring = false;\n\n\t\t\t// Clean up if we're done firing for good\n\t\t\tif ( locked ) {\n\n\t\t\t\t// Keep an empty list if we have data for future add calls\n\t\t\t\tif ( memory ) {\n\t\t\t\t\tlist = [];\n\n\t\t\t\t// Otherwise, this object is spent\n\t\t\t\t} else {\n\t\t\t\t\tlist = \"\";\n\t\t\t\t}\n\t\t\t}\n\t\t},\n\n\t\t// Actual Callbacks object\n\t\tself = {\n\n\t\t\t// Add a callback or a collection of callbacks to the list\n\t\t\tadd: function() {\n\t\t\t\tif ( list ) {\n\n\t\t\t\t\t// If we have memory from a past run, we should fire after adding\n\t\t\t\t\tif ( memory && !firing ) {\n\t\t\t\t\t\tfiringIndex = list.length - 1;\n\t\t\t\t\t\tqueue.push( memory );\n\t\t\t\t\t}\n\n\t\t\t\t\t( function add( args ) {\n\t\t\t\t\t\tjQuery.each( args, function( _, arg ) {\n\t\t\t\t\t\t\tif ( jQuery.isFunction( arg ) ) {\n\t\t\t\t\t\t\t\tif ( !options.unique || !self.has( arg ) ) {\n\t\t\t\t\t\t\t\t\tlist.push( arg );\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t} else if ( arg && arg.length && jQuery.type( arg ) !== \"string\" ) {\n\n\t\t\t\t\t\t\t\t// Inspect recursively\n\t\t\t\t\t\t\t\tadd( arg );\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} );\n\t\t\t\t\t} )( arguments );\n\n\t\t\t\t\tif ( memory && !firing ) {\n\t\t\t\t\t\tfire();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\treturn this;\n\t\t\t},\n\n\t\t\t// Remove a callback from the list\n\t\t\tremove: function() {\n\t\t\t\tjQuery.each( arguments, function( _, arg ) {\n\t\t\t\t\tvar index;\n\t\t\t\t\twhile ( ( index = jQuery.inArray( arg, list, index ) ) > -1 ) {\n\t\t\t\t\t\tlist.splice( index, 1 );\n\n\t\t\t\t\t\t// Handle firing indexes\n\t\t\t\t\t\tif ( index <= firingIndex ) {\n\t\t\t\t\t\t\tfiringIndex--;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} );\n\t\t\t\treturn this;\n\t\t\t},\n\n\t\t\t// Check if a given callback is in the list.\n\t\t\t// If no argument is given, return whether or not list has callbacks attached.\n\t\t\thas: function( fn ) {\n\t\t\t\treturn fn ?\n\t\t\t\t\tjQuery.inArray( fn, list ) > -1 :\n\t\t\t\t\tlist.length > 0;\n\t\t\t},\n\n\t\t\t// Remove all callbacks from the list\n\t\t\tempty: function() {\n\t\t\t\tif ( list ) {\n\t\t\t\t\tlist = [];\n\t\t\t\t}\n\t\t\t\treturn this;\n\t\t\t},\n\n\t\t\t// Disable .fire and .add\n\t\t\t// Abort any current/pending executions\n\t\t\t// Clear all callbacks and values\n\t\t\tdisable: function() {\n\t\t\t\tlocked = queue = [];\n\t\t\t\tlist = memory = \"\";\n\t\t\t\treturn this;\n\t\t\t},\n\t\t\tdisabled: function() {\n\t\t\t\treturn !list;\n\t\t\t},\n\n\t\t\t// Disable .fire\n\t\t\t// Also disable .add unless we have memory (since it would have no effect)\n\t\t\t// Abort any pending executions\n\t\t\tlock: function() {\n\t\t\t\tlocked = queue = [];\n\t\t\t\tif ( !memory && !firing ) {\n\t\t\t\t\tlist = memory = \"\";\n\t\t\t\t}\n\t\t\t\treturn this;\n\t\t\t},\n\t\t\tlocked: function() {\n\t\t\t\treturn !!locked;\n\t\t\t},\n\n\t\t\t// Call all callbacks with the given context and arguments\n\t\t\tfireWith: function( context, args ) {\n\t\t\t\tif ( !locked ) {\n\t\t\t\t\targs = args || [];\n\t\t\t\t\targs = [ context, args.slice ? args.slice() : args ];\n\t\t\t\t\tqueue.push( args );\n\t\t\t\t\tif ( !firing ) {\n\t\t\t\t\t\tfire();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\treturn this;\n\t\t\t},\n\n\t\t\t// Call all the callbacks with the given arguments\n\t\t\tfire: function() {\n\t\t\t\tself.fireWith( this, arguments );\n\t\t\t\treturn this;\n\t\t\t},\n\n\t\t\t// To know if the callbacks have already been called at least once\n\t\t\tfired: function() {\n\t\t\t\treturn !!fired;\n\t\t\t}\n\t\t};\n\n\treturn self;\n};\n\n\nfunction Identity( v ) {\n\treturn v;\n}\nfunction Thrower( ex ) {\n\tthrow ex;\n}\n\nfunction adoptValue( value, resolve, reject ) {\n\tvar method;\n\n\ttry {\n\n\t\t// Check for promise aspect first to privilege synchronous behavior\n\t\tif ( value && jQuery.isFunction( ( method = value.promise ) ) ) {\n\t\t\tmethod.call( value ).done( resolve ).fail( reject );\n\n\t\t// Other thenables\n\t\t} else if ( value && jQuery.isFunction( ( method = value.then ) ) ) {\n\t\t\tmethod.call( value, resolve, reject );\n\n\t\t// Other non-thenables\n\t\t} else {\n\n\t\t\t// Support: Android 4.0 only\n\t\t\t// Strict mode functions invoked without .call/.apply get global-object context\n\t\t\tresolve.call( undefined, value );\n\t\t}\n\n\t// For Promises/A+, convert exceptions into rejections\n\t// Since jQuery.when doesn't unwrap thenables, we can skip the extra checks appearing in\n\t// Deferred#then to conditionally suppress rejection.\n\t} catch ( value ) {\n\n\t\t// Support: Android 4.0 only\n\t\t// Strict mode functions invoked without .call/.apply get global-object context\n\t\treject.call( undefined, value );\n\t}\n}\n\njQuery.extend( {\n\n\tDeferred: function( func ) {\n\t\tvar tuples = [\n\n\t\t\t\t// action, add listener, callbacks,\n\t\t\t\t// ... .then handlers, argument index, [final state]\n\t\t\t\t[ \"notify\", \"progress\", jQuery.Callbacks( \"memory\" ),\n\t\t\t\t\tjQuery.Callbacks( \"memory\" ), 2 ],\n\t\t\t\t[ \"resolve\", \"done\", jQuery.Callbacks( \"once memory\" ),\n\t\t\t\t\tjQuery.Callbacks( \"once memory\" ), 0, \"resolved\" ],\n\t\t\t\t[ \"reject\", \"fail\", jQuery.Callbacks( \"once memory\" ),\n\t\t\t\t\tjQuery.Callbacks( \"once memory\" ), 1, \"rejected\" ]\n\t\t\t],\n\t\t\tstate = \"pending\",\n\t\t\tpromise = {\n\t\t\t\tstate: function() {\n\t\t\t\t\treturn state;\n\t\t\t\t},\n\t\t\t\talways: function() {\n\t\t\t\t\tdeferred.done( arguments ).fail( arguments );\n\t\t\t\t\treturn this;\n\t\t\t\t},\n\t\t\t\t\"catch\": function( fn ) {\n\t\t\t\t\treturn promise.then( null, fn );\n\t\t\t\t},\n\n\t\t\t\t// Keep pipe for back-compat\n\t\t\t\tpipe: function( /* fnDone, fnFail, fnProgress */ ) {\n\t\t\t\t\tvar fns = arguments;\n\n\t\t\t\t\treturn jQuery.Deferred( function( newDefer ) {\n\t\t\t\t\t\tjQuery.each( tuples, function( i, tuple ) {\n\n\t\t\t\t\t\t\t// Map tuples (progress, done, fail) to arguments (done, fail, progress)\n\t\t\t\t\t\t\tvar fn = jQuery.isFunction( fns[ tuple[ 4 ] ] ) && fns[ tuple[ 4 ] ];\n\n\t\t\t\t\t\t\t// deferred.progress(function() { bind to newDefer or newDefer.notify })\n\t\t\t\t\t\t\t// deferred.done(function() { bind to newDefer or newDefer.resolve })\n\t\t\t\t\t\t\t// deferred.fail(function() { bind to newDefer or newDefer.reject })\n\t\t\t\t\t\t\tdeferred[ tuple[ 1 ] ]( function() {\n\t\t\t\t\t\t\t\tvar returned = fn && fn.apply( this, arguments );\n\t\t\t\t\t\t\t\tif ( returned && jQuery.isFunction( returned.promise ) ) {\n\t\t\t\t\t\t\t\t\treturned.promise()\n\t\t\t\t\t\t\t\t\t\t.progress( newDefer.notify )\n\t\t\t\t\t\t\t\t\t\t.done( newDefer.resolve )\n\t\t\t\t\t\t\t\t\t\t.fail( newDefer.reject );\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\tnewDefer[ tuple[ 0 ] + \"With\" ](\n\t\t\t\t\t\t\t\t\t\tthis,\n\t\t\t\t\t\t\t\t\t\tfn ? [ returned ] : arguments\n\t\t\t\t\t\t\t\t\t);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t} );\n\t\t\t\t\t\t} );\n\t\t\t\t\t\tfns = null;\n\t\t\t\t\t} ).promise();\n\t\t\t\t},\n\t\t\t\tthen: function( onFulfilled, onRejected, onProgress ) {\n\t\t\t\t\tvar maxDepth = 0;\n\t\t\t\t\tfunction resolve( depth, deferred, handler, special ) {\n\t\t\t\t\t\treturn function() {\n\t\t\t\t\t\t\tvar that = this,\n\t\t\t\t\t\t\t\targs = arguments,\n\t\t\t\t\t\t\t\tmightThrow = function() {\n\t\t\t\t\t\t\t\t\tvar returned, then;\n\n\t\t\t\t\t\t\t\t\t// Support: Promises/A+ section 2.3.3.3.3\n\t\t\t\t\t\t\t\t\t// https://promisesaplus.com/#point-59\n\t\t\t\t\t\t\t\t\t// Ignore double-resolution attempts\n\t\t\t\t\t\t\t\t\tif ( depth < maxDepth ) {\n\t\t\t\t\t\t\t\t\t\treturn;\n\t\t\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\t\t\treturned = handler.apply( that, args );\n\n\t\t\t\t\t\t\t\t\t// Support: Promises/A+ section 2.3.1\n\t\t\t\t\t\t\t\t\t// https://promisesaplus.com/#point-48\n\t\t\t\t\t\t\t\t\tif ( returned === deferred.promise() ) {\n\t\t\t\t\t\t\t\t\t\tthrow new TypeError( \"Thenable self-resolution\" );\n\t\t\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\t\t\t// Support: Promises/A+ sections 2.3.3.1, 3.5\n\t\t\t\t\t\t\t\t\t// https://promisesaplus.com/#point-54\n\t\t\t\t\t\t\t\t\t// https://promisesaplus.com/#point-75\n\t\t\t\t\t\t\t\t\t// Retrieve `then` only once\n\t\t\t\t\t\t\t\t\tthen = returned &&\n\n\t\t\t\t\t\t\t\t\t\t// Support: Promises/A+ section 2.3.4\n\t\t\t\t\t\t\t\t\t\t// https://promisesaplus.com/#point-64\n\t\t\t\t\t\t\t\t\t\t// Only check objects and functions for thenability\n\t\t\t\t\t\t\t\t\t\t( typeof returned === \"object\" ||\n\t\t\t\t\t\t\t\t\t\t\ttypeof returned === \"function\" ) &&\n\t\t\t\t\t\t\t\t\t\treturned.then;\n\n\t\t\t\t\t\t\t\t\t// Handle a returned thenable\n\t\t\t\t\t\t\t\t\tif ( jQuery.isFunction( then ) ) {\n\n\t\t\t\t\t\t\t\t\t\t// Special processors (notify) just wait for resolution\n\t\t\t\t\t\t\t\t\t\tif ( special ) {\n\t\t\t\t\t\t\t\t\t\t\tthen.call(\n\t\t\t\t\t\t\t\t\t\t\t\treturned,\n\t\t\t\t\t\t\t\t\t\t\t\tresolve( maxDepth, deferred, Identity, special ),\n\t\t\t\t\t\t\t\t\t\t\t\tresolve( maxDepth, deferred, Thrower, special )\n\t\t\t\t\t\t\t\t\t\t\t);\n\n\t\t\t\t\t\t\t\t\t\t// Normal processors (resolve) also hook into progress\n\t\t\t\t\t\t\t\t\t\t} else {\n\n\t\t\t\t\t\t\t\t\t\t\t// ...and disregard older resolution values\n\t\t\t\t\t\t\t\t\t\t\tmaxDepth++;\n\n\t\t\t\t\t\t\t\t\t\t\tthen.call(\n\t\t\t\t\t\t\t\t\t\t\t\treturned,\n\t\t\t\t\t\t\t\t\t\t\t\tresolve( maxDepth, deferred, Identity, special ),\n\t\t\t\t\t\t\t\t\t\t\t\tresolve( maxDepth, deferred, Thrower, special ),\n\t\t\t\t\t\t\t\t\t\t\t\tresolve( maxDepth, deferred, Identity,\n\t\t\t\t\t\t\t\t\t\t\t\t\tdeferred.notifyWith )\n\t\t\t\t\t\t\t\t\t\t\t);\n\t\t\t\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\t\t\t// Handle all other returned values\n\t\t\t\t\t\t\t\t\t} else {\n\n\t\t\t\t\t\t\t\t\t\t// Only substitute handlers pass on context\n\t\t\t\t\t\t\t\t\t\t// and multiple values (non-spec behavior)\n\t\t\t\t\t\t\t\t\t\tif ( handler !== Identity ) {\n\t\t\t\t\t\t\t\t\t\t\tthat = undefined;\n\t\t\t\t\t\t\t\t\t\t\targs = [ returned ];\n\t\t\t\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\t\t\t\t// Process the value(s)\n\t\t\t\t\t\t\t\t\t\t// Default process is resolve\n\t\t\t\t\t\t\t\t\t\t( special || deferred.resolveWith )( that, args );\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t},\n\n\t\t\t\t\t\t\t\t// Only normal processors (resolve) catch and reject exceptions\n\t\t\t\t\t\t\t\tprocess = special ?\n\t\t\t\t\t\t\t\t\tmightThrow :\n\t\t\t\t\t\t\t\t\tfunction() {\n\t\t\t\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\t\t\t\tmightThrow();\n\t\t\t\t\t\t\t\t\t\t} catch ( e ) {\n\n\t\t\t\t\t\t\t\t\t\t\tif ( jQuery.Deferred.exceptionHook ) {\n\t\t\t\t\t\t\t\t\t\t\t\tjQuery.Deferred.exceptionHook( e,\n\t\t\t\t\t\t\t\t\t\t\t\t\tprocess.stackTrace );\n\t\t\t\t\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\t\t\t\t\t// Support: Promises/A+ section 2.3.3.3.4.1\n\t\t\t\t\t\t\t\t\t\t\t// https://promisesaplus.com/#point-61\n\t\t\t\t\t\t\t\t\t\t\t// Ignore post-resolution exceptions\n\t\t\t\t\t\t\t\t\t\t\tif ( depth + 1 >= maxDepth ) {\n\n\t\t\t\t\t\t\t\t\t\t\t\t// Only substitute handlers pass on context\n\t\t\t\t\t\t\t\t\t\t\t\t// and multiple values (non-spec behavior)\n\t\t\t\t\t\t\t\t\t\t\t\tif ( handler !== Thrower ) {\n\t\t\t\t\t\t\t\t\t\t\t\t\tthat = undefined;\n\t\t\t\t\t\t\t\t\t\t\t\t\targs = [ e ];\n\t\t\t\t\t\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\t\t\t\t\t\tdeferred.rejectWith( that, args );\n\t\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t};\n\n\t\t\t\t\t\t\t// Support: Promises/A+ section 2.3.3.3.1\n\t\t\t\t\t\t\t// https://promisesaplus.com/#point-57\n\t\t\t\t\t\t\t// Re-resolve promises immediately to dodge false rejection from\n\t\t\t\t\t\t\t// subsequent errors\n\t\t\t\t\t\t\tif ( depth ) {\n\t\t\t\t\t\t\t\tprocess();\n\t\t\t\t\t\t\t} else {\n\n\t\t\t\t\t\t\t\t// Call an optional hook to record the stack, in case of exception\n\t\t\t\t\t\t\t\t// since it's otherwise lost when execution goes async\n\t\t\t\t\t\t\t\tif ( jQuery.Deferred.getStackHook ) {\n\t\t\t\t\t\t\t\t\tprocess.stackTrace = jQuery.Deferred.getStackHook();\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\twindow.setTimeout( process );\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t};\n\t\t\t\t\t}\n\n\t\t\t\t\treturn jQuery.Deferred( function( newDefer ) {\n\n\t\t\t\t\t\t// progress_handlers.add( ... )\n\t\t\t\t\t\ttuples[ 0 ][ 3 ].add(\n\t\t\t\t\t\t\tresolve(\n\t\t\t\t\t\t\t\t0,\n\t\t\t\t\t\t\t\tnewDefer,\n\t\t\t\t\t\t\t\tjQuery.isFunction( onProgress ) ?\n\t\t\t\t\t\t\t\t\tonProgress :\n\t\t\t\t\t\t\t\t\tIdentity,\n\t\t\t\t\t\t\t\tnewDefer.notifyWith\n\t\t\t\t\t\t\t)\n\t\t\t\t\t\t);\n\n\t\t\t\t\t\t// fulfilled_handlers.add( ... )\n\t\t\t\t\t\ttuples[ 1 ][ 3 ].add(\n\t\t\t\t\t\t\tresolve(\n\t\t\t\t\t\t\t\t0,\n\t\t\t\t\t\t\t\tnewDefer,\n\t\t\t\t\t\t\t\tjQuery.isFunction( onFulfilled ) ?\n\t\t\t\t\t\t\t\t\tonFulfilled :\n\t\t\t\t\t\t\t\t\tIdentity\n\t\t\t\t\t\t\t)\n\t\t\t\t\t\t);\n\n\t\t\t\t\t\t// rejected_handlers.add( ... )\n\t\t\t\t\t\ttuples[ 2 ][ 3 ].add(\n\t\t\t\t\t\t\tresolve(\n\t\t\t\t\t\t\t\t0,\n\t\t\t\t\t\t\t\tnewDefer,\n\t\t\t\t\t\t\t\tjQuery.isFunction( onRejected ) ?\n\t\t\t\t\t\t\t\t\tonRejected :\n\t\t\t\t\t\t\t\t\tThrower\n\t\t\t\t\t\t\t)\n\t\t\t\t\t\t);\n\t\t\t\t\t} ).promise();\n\t\t\t\t},\n\n\t\t\t\t// Get a promise for this deferred\n\t\t\t\t// If obj is provided, the promise aspect is added to the object\n\t\t\t\tpromise: function( obj ) {\n\t\t\t\t\treturn obj != null ? jQuery.extend( obj, promise ) : promise;\n\t\t\t\t}\n\t\t\t},\n\t\t\tdeferred = {};\n\n\t\t// Add list-specific methods\n\t\tjQuery.each( tuples, function( i, tuple ) {\n\t\t\tvar list = tuple[ 2 ],\n\t\t\t\tstateString = tuple[ 5 ];\n\n\t\t\t// promise.progress = list.add\n\t\t\t// promise.done = list.add\n\t\t\t// promise.fail = list.add\n\t\t\tpromise[ tuple[ 1 ] ] = list.add;\n\n\t\t\t// Handle state\n\t\t\tif ( stateString ) {\n\t\t\t\tlist.add(\n\t\t\t\t\tfunction() {\n\n\t\t\t\t\t\t// state = \"resolved\" (i.e., fulfilled)\n\t\t\t\t\t\t// state = \"rejected\"\n\t\t\t\t\t\tstate = stateString;\n\t\t\t\t\t},\n\n\t\t\t\t\t// rejected_callbacks.disable\n\t\t\t\t\t// fulfilled_callbacks.disable\n\t\t\t\t\ttuples[ 3 - i ][ 2 ].disable,\n\n\t\t\t\t\t// progress_callbacks.lock\n\t\t\t\t\ttuples[ 0 ][ 2 ].lock\n\t\t\t\t);\n\t\t\t}\n\n\t\t\t// progress_handlers.fire\n\t\t\t// fulfilled_handlers.fire\n\t\t\t// rejected_handlers.fire\n\t\t\tlist.add( tuple[ 3 ].fire );\n\n\t\t\t// deferred.notify = function() { deferred.notifyWith(...) }\n\t\t\t// deferred.resolve = function() { deferred.resolveWith(...) }\n\t\t\t// deferred.reject = function() { deferred.rejectWith(...) }\n\t\t\tdeferred[ tuple[ 0 ] ] = function() {\n\t\t\t\tdeferred[ tuple[ 0 ] + \"With\" ]( this === deferred ? undefined : this, arguments );\n\t\t\t\treturn this;\n\t\t\t};\n\n\t\t\t// deferred.notifyWith = list.fireWith\n\t\t\t// deferred.resolveWith = list.fireWith\n\t\t\t// deferred.rejectWith = list.fireWith\n\t\t\tdeferred[ tuple[ 0 ] + \"With\" ] = list.fireWith;\n\t\t} );\n\n\t\t// Make the deferred a promise\n\t\tpromise.promise( deferred );\n\n\t\t// Call given func if any\n\t\tif ( func ) {\n\t\t\tfunc.call( deferred, deferred );\n\t\t}\n\n\t\t// All done!\n\t\treturn deferred;\n\t},\n\n\t// Deferred helper\n\twhen: function( singleValue ) {\n\t\tvar\n\n\t\t\t// count of uncompleted subordinates\n\t\t\tremaining = arguments.length,\n\n\t\t\t// count of unprocessed arguments\n\t\t\ti = remaining,\n\n\t\t\t// subordinate fulfillment data\n\t\t\tresolveContexts = Array( i ),\n\t\t\tresolveValues = slice.call( arguments ),\n\n\t\t\t// the master Deferred\n\t\t\tmaster = jQuery.Deferred(),\n\n\t\t\t// subordinate callback factory\n\t\t\tupdateFunc = function( i ) {\n\t\t\t\treturn function( value ) {\n\t\t\t\t\tresolveContexts[ i ] = this;\n\t\t\t\t\tresolveValues[ i ] = arguments.length > 1 ? slice.call( arguments ) : value;\n\t\t\t\t\tif ( !( --remaining ) ) {\n\t\t\t\t\t\tmaster.resolveWith( resolveContexts, resolveValues );\n\t\t\t\t\t}\n\t\t\t\t};\n\t\t\t};\n\n\t\t// Single- and empty arguments are adopted like Promise.resolve\n\t\tif ( remaining <= 1 ) {\n\t\t\tadoptValue( singleValue, master.done( updateFunc( i ) ).resolve, master.reject );\n\n\t\t\t// Use .then() to unwrap secondary thenables (cf. gh-3000)\n\t\t\tif ( master.state() === \"pending\" ||\n\t\t\t\tjQuery.isFunction( resolveValues[ i ] && resolveValues[ i ].then ) ) {\n\n\t\t\t\treturn master.then();\n\t\t\t}\n\t\t}\n\n\t\t// Multiple arguments are aggregated like Promise.all array elements\n\t\twhile ( i-- ) {\n\t\t\tadoptValue( resolveValues[ i ], updateFunc( i ), master.reject );\n\t\t}\n\n\t\treturn master.promise();\n\t}\n} );\n\n\n// These usually indicate a programmer mistake during development,\n// warn about them ASAP rather than swallowing them by default.\nvar rerrorNames = /^(Eval|Internal|Range|Reference|Syntax|Type|URI)Error$/;\n\njQuery.Deferred.exceptionHook = function( error, stack ) {\n\n\t// Support: IE 8 - 9 only\n\t// Console exists when dev tools are open, which can happen at any time\n\tif ( window.console && window.console.warn && error && rerrorNames.test( error.name ) ) {\n\t\twindow.console.warn( \"jQuery.Deferred exception: \" + error.message, error.stack, stack );\n\t}\n};\n\n\n\n\njQuery.readyException = function( error ) {\n\twindow.setTimeout( function() {\n\t\tthrow error;\n\t} );\n};\n\n\n\n\n// The deferred used on DOM ready\nvar readyList = jQuery.Deferred();\n\njQuery.fn.ready = function( fn ) {\n\n\treadyList\n\t\t.then( fn )\n\n\t\t// Wrap jQuery.readyException in a function so that the lookup\n\t\t// happens at the time of error handling instead of callback\n\t\t// registration.\n\t\t.catch( function( error ) {\n\t\t\tjQuery.readyException( error );\n\t\t} );\n\n\treturn this;\n};\n\njQuery.extend( {\n\n\t// Is the DOM ready to be used? Set to true once it occurs.\n\tisReady: false,\n\n\t// A counter to track how many items to wait for before\n\t// the ready event fires. See #6781\n\treadyWait: 1,\n\n\t// Hold (or release) the ready event\n\tholdReady: function( hold ) {\n\t\tif ( hold ) {\n\t\t\tjQuery.readyWait++;\n\t\t} else {\n\t\t\tjQuery.ready( true );\n\t\t}\n\t},\n\n\t// Handle when the DOM is ready\n\tready: function( wait ) {\n\n\t\t// Abort if there are pending holds or we're already ready\n\t\tif ( wait === true ? --jQuery.readyWait : jQuery.isReady ) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Remember that the DOM is ready\n\t\tjQuery.isReady = true;\n\n\t\t// If a normal DOM Ready event fired, decrement, and wait if need be\n\t\tif ( wait !== true && --jQuery.readyWait > 0 ) {\n\t\t\treturn;\n\t\t}\n\n\t\t// If there are functions bound, to execute\n\t\treadyList.resolveWith( document, [ jQuery ] );\n\t}\n} );\n\njQuery.ready.then = readyList.then;\n\n// The ready event handler and self cleanup method\nfunction completed() {\n\tdocument.removeEventListener( \"DOMContentLoaded\", completed );\n\twindow.removeEventListener( \"load\", completed );\n\tjQuery.ready();\n}\n\n// Catch cases where $(document).ready() is called\n// after the browser event has already occurred.\n// Support: IE <=9 - 10 only\n// Older IE sometimes signals \"interactive\" too soon\nif ( document.readyState === \"complete\" ||\n\t( document.readyState !== \"loading\" && !document.documentElement.doScroll ) ) {\n\n\t// Handle it asynchronously to allow scripts the opportunity to delay ready\n\twindow.setTimeout( jQuery.ready );\n\n} else {\n\n\t// Use the handy event callback\n\tdocument.addEventListener( \"DOMContentLoaded\", completed );\n\n\t// A fallback to window.onload, that will always work\n\twindow.addEventListener( \"load\", completed );\n}\n\n\n\n\n// Multifunctional method to get and set values of a collection\n// The value/s can optionally be executed if it's a function\nvar access = function( elems, fn, key, value, chainable, emptyGet, raw ) {\n\tvar i = 0,\n\t\tlen = elems.length,\n\t\tbulk = key == null;\n\n\t// Sets many values\n\tif ( jQuery.type( key ) === \"object\" ) {\n\t\tchainable = true;\n\t\tfor ( i in key ) {\n\t\t\taccess( elems, fn, i, key[ i ], true, emptyGet, raw );\n\t\t}\n\n\t// Sets one value\n\t} else if ( value !== undefined ) {\n\t\tchainable = true;\n\n\t\tif ( !jQuery.isFunction( value ) ) {\n\t\t\traw = true;\n\t\t}\n\n\t\tif ( bulk ) {\n\n\t\t\t// Bulk operations run against the entire set\n\t\t\tif ( raw ) {\n\t\t\t\tfn.call( elems, value );\n\t\t\t\tfn = null;\n\n\t\t\t// ...except when executing function values\n\t\t\t} else {\n\t\t\t\tbulk = fn;\n\t\t\t\tfn = function( elem, key, value ) {\n\t\t\t\t\treturn bulk.call( jQuery( elem ), value );\n\t\t\t\t};\n\t\t\t}\n\t\t}\n\n\t\tif ( fn ) {\n\t\t\tfor ( ; i < len; i++ ) {\n\t\t\t\tfn(\n\t\t\t\t\telems[ i ], key, raw ?\n\t\t\t\t\tvalue :\n\t\t\t\t\tvalue.call( elems[ i ], i, fn( elems[ i ], key ) )\n\t\t\t\t);\n\t\t\t}\n\t\t}\n\t}\n\n\tif ( chainable ) {\n\t\treturn elems;\n\t}\n\n\t// Gets\n\tif ( bulk ) {\n\t\treturn fn.call( elems );\n\t}\n\n\treturn len ? fn( elems[ 0 ], key ) : emptyGet;\n};\nvar acceptData = function( owner ) {\n\n\t// Accepts only:\n\t//  - Node\n\t//    - Node.ELEMENT_NODE\n\t//    - Node.DOCUMENT_NODE\n\t//  - Object\n\t//    - Any\n\treturn owner.nodeType === 1 || owner.nodeType === 9 || !( +owner.nodeType );\n};\n\n\n\n\nfunction Data() {\n\tthis.expando = jQuery.expando + Data.uid++;\n}\n\nData.uid = 1;\n\nData.prototype = {\n\n\tcache: function( owner ) {\n\n\t\t// Check if the owner object already has a cache\n\t\tvar value = owner[ this.expando ];\n\n\t\t// If not, create one\n\t\tif ( !value ) {\n\t\t\tvalue = {};\n\n\t\t\t// We can accept data for non-element nodes in modern browsers,\n\t\t\t// but we should not, see #8335.\n\t\t\t// Always return an empty object.\n\t\t\tif ( acceptData( owner ) ) {\n\n\t\t\t\t// If it is a node unlikely to be stringify-ed or looped over\n\t\t\t\t// use plain assignment\n\t\t\t\tif ( owner.nodeType ) {\n\t\t\t\t\towner[ this.expando ] = value;\n\n\t\t\t\t// Otherwise secure it in a non-enumerable property\n\t\t\t\t// configurable must be true to allow the property to be\n\t\t\t\t// deleted when data is removed\n\t\t\t\t} else {\n\t\t\t\t\tObject.defineProperty( owner, this.expando, {\n\t\t\t\t\t\tvalue: value,\n\t\t\t\t\t\tconfigurable: true\n\t\t\t\t\t} );\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn value;\n\t},\n\tset: function( owner, data, value ) {\n\t\tvar prop,\n\t\t\tcache = this.cache( owner );\n\n\t\t// Handle: [ owner, key, value ] args\n\t\t// Always use camelCase key (gh-2257)\n\t\tif ( typeof data === \"string\" ) {\n\t\t\tcache[ jQuery.camelCase( data ) ] = value;\n\n\t\t// Handle: [ owner, { properties } ] args\n\t\t} else {\n\n\t\t\t// Copy the properties one-by-one to the cache object\n\t\t\tfor ( prop in data ) {\n\t\t\t\tcache[ jQuery.camelCase( prop ) ] = data[ prop ];\n\t\t\t}\n\t\t}\n\t\treturn cache;\n\t},\n\tget: function( owner, key ) {\n\t\treturn key === undefined ?\n\t\t\tthis.cache( owner ) :\n\n\t\t\t// Always use camelCase key (gh-2257)\n\t\t\towner[ this.expando ] && owner[ this.expando ][ jQuery.camelCase( key ) ];\n\t},\n\taccess: function( owner, key, value ) {\n\n\t\t// In cases where either:\n\t\t//\n\t\t//   1. No key was specified\n\t\t//   2. A string key was specified, but no value provided\n\t\t//\n\t\t// Take the \"read\" path and allow the get method to determine\n\t\t// which value to return, respectively either:\n\t\t//\n\t\t//   1. The entire cache object\n\t\t//   2. The data stored at the key\n\t\t//\n\t\tif ( key === undefined ||\n\t\t\t\t( ( key && typeof key === \"string\" ) && value === undefined ) ) {\n\n\t\t\treturn this.get( owner, key );\n\t\t}\n\n\t\t// When the key is not a string, or both a key and value\n\t\t// are specified, set or extend (existing objects) with either:\n\t\t//\n\t\t//   1. An object of properties\n\t\t//   2. A key and value\n\t\t//\n\t\tthis.set( owner, key, value );\n\n\t\t// Since the \"set\" path can have two possible entry points\n\t\t// return the expected data based on which path was taken[*]\n\t\treturn value !== undefined ? value : key;\n\t},\n\tremove: function( owner, key ) {\n\t\tvar i,\n\t\t\tcache = owner[ this.expando ];\n\n\t\tif ( cache === undefined ) {\n\t\t\treturn;\n\t\t}\n\n\t\tif ( key !== undefined ) {\n\n\t\t\t// Support array or space separated string of keys\n\t\t\tif ( jQuery.isArray( key ) ) {\n\n\t\t\t\t// If key is an array of keys...\n\t\t\t\t// We always set camelCase keys, so remove that.\n\t\t\t\tkey = key.map( jQuery.camelCase );\n\t\t\t} else {\n\t\t\t\tkey = jQuery.camelCase( key );\n\n\t\t\t\t// If a key with the spaces exists, use it.\n\t\t\t\t// Otherwise, create an array by matching non-whitespace\n\t\t\t\tkey = key in cache ?\n\t\t\t\t\t[ key ] :\n\t\t\t\t\t( key.match( rnothtmlwhite ) || [] );\n\t\t\t}\n\n\t\t\ti = key.length;\n\n\t\t\twhile ( i-- ) {\n\t\t\t\tdelete cache[ key[ i ] ];\n\t\t\t}\n\t\t}\n\n\t\t// Remove the expando if there's no more data\n\t\tif ( key === undefined || jQuery.isEmptyObject( cache ) ) {\n\n\t\t\t// Support: Chrome <=35 - 45\n\t\t\t// Webkit & Blink performance suffers when deleting properties\n\t\t\t// from DOM nodes, so set to undefined instead\n\t\t\t// https://bugs.chromium.org/p/chromium/issues/detail?id=378607 (bug restricted)\n\t\t\tif ( owner.nodeType ) {\n\t\t\t\towner[ this.expando ] = undefined;\n\t\t\t} else {\n\t\t\t\tdelete owner[ this.expando ];\n\t\t\t}\n\t\t}\n\t},\n\thasData: function( owner ) {\n\t\tvar cache = owner[ this.expando ];\n\t\treturn cache !== undefined && !jQuery.isEmptyObject( cache );\n\t}\n};\nvar dataPriv = new Data();\n\nvar dataUser = new Data();\n\n\n\n//\tImplementation Summary\n//\n//\t1. Enforce API surface and semantic compatibility with 1.9.x branch\n//\t2. Improve the module's maintainability by reducing the storage\n//\t\tpaths to a single mechanism.\n//\t3. Use the same single mechanism to support \"private\" and \"user\" data.\n//\t4. _Never_ expose \"private\" data to user code (TODO: Drop _data, _removeData)\n//\t5. Avoid exposing implementation details on user objects (eg. expando properties)\n//\t6. Provide a clear path for implementation upgrade to WeakMap in 2014\n\nvar rbrace = /^(?:\\{[\\w\\W]*\\}|\\[[\\w\\W]*\\])$/,\n\trmultiDash = /[A-Z]/g;\n\nfunction getData( data ) {\n\tif ( data === \"true\" ) {\n\t\treturn true;\n\t}\n\n\tif ( data === \"false\" ) {\n\t\treturn false;\n\t}\n\n\tif ( data === \"null\" ) {\n\t\treturn null;\n\t}\n\n\t// Only convert to a number if it doesn't change the string\n\tif ( data === +data + \"\" ) {\n\t\treturn +data;\n\t}\n\n\tif ( rbrace.test( data ) ) {\n\t\treturn JSON.parse( data );\n\t}\n\n\treturn data;\n}\n\nfunction dataAttr( elem, key, data ) {\n\tvar name;\n\n\t// If nothing was found internally, try to fetch any\n\t// data from the HTML5 data-* attribute\n\tif ( data === undefined && elem.nodeType === 1 ) {\n\t\tname = \"data-\" + key.replace( rmultiDash, \"-$&\" ).toLowerCase();\n\t\tdata = elem.getAttribute( name );\n\n\t\tif ( typeof data === \"string\" ) {\n\t\t\ttry {\n\t\t\t\tdata = getData( data );\n\t\t\t} catch ( e ) {}\n\n\t\t\t// Make sure we set the data so it isn't changed later\n\t\t\tdataUser.set( elem, key, data );\n\t\t} else {\n\t\t\tdata = undefined;\n\t\t}\n\t}\n\treturn data;\n}\n\njQuery.extend( {\n\thasData: function( elem ) {\n\t\treturn dataUser.hasData( elem ) || dataPriv.hasData( elem );\n\t},\n\n\tdata: function( elem, name, data ) {\n\t\treturn dataUser.access( elem, name, data );\n\t},\n\n\tremoveData: function( elem, name ) {\n\t\tdataUser.remove( elem, name );\n\t},\n\n\t// TODO: Now that all calls to _data and _removeData have been replaced\n\t// with direct calls to dataPriv methods, these can be deprecated.\n\t_data: function( elem, name, data ) {\n\t\treturn dataPriv.access( elem, name, data );\n\t},\n\n\t_removeData: function( elem, name ) {\n\t\tdataPriv.remove( elem, name );\n\t}\n} );\n\njQuery.fn.extend( {\n\tdata: function( key, value ) {\n\t\tvar i, name, data,\n\t\t\telem = this[ 0 ],\n\t\t\tattrs = elem && elem.attributes;\n\n\t\t// Gets all values\n\t\tif ( key === undefined ) {\n\t\t\tif ( this.length ) {\n\t\t\t\tdata = dataUser.get( elem );\n\n\t\t\t\tif ( elem.nodeType === 1 && !dataPriv.get( elem, \"hasDataAttrs\" ) ) {\n\t\t\t\t\ti = attrs.length;\n\t\t\t\t\twhile ( i-- ) {\n\n\t\t\t\t\t\t// Support: IE 11 only\n\t\t\t\t\t\t// The attrs elements can be null (#14894)\n\t\t\t\t\t\tif ( attrs[ i ] ) {\n\t\t\t\t\t\t\tname = attrs[ i ].name;\n\t\t\t\t\t\t\tif ( name.indexOf( \"data-\" ) === 0 ) {\n\t\t\t\t\t\t\t\tname = jQuery.camelCase( name.slice( 5 ) );\n\t\t\t\t\t\t\t\tdataAttr( elem, name, data[ name ] );\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tdataPriv.set( elem, \"hasDataAttrs\", true );\n\t\t\t\t}\n\t\t\t}\n\n\t\t\treturn data;\n\t\t}\n\n\t\t// Sets multiple values\n\t\tif ( typeof key === \"object\" ) {\n\t\t\treturn this.each( function() {\n\t\t\t\tdataUser.set( this, key );\n\t\t\t} );\n\t\t}\n\n\t\treturn access( this, function( value ) {\n\t\t\tvar data;\n\n\t\t\t// The calling jQuery object (element matches) is not empty\n\t\t\t// (and therefore has an element appears at this[ 0 ]) and the\n\t\t\t// `value` parameter was not undefined. An empty jQuery object\n\t\t\t// will result in `undefined` for elem = this[ 0 ] which will\n\t\t\t// throw an exception if an attempt to read a data cache is made.\n\t\t\tif ( elem && value === undefined ) {\n\n\t\t\t\t// Attempt to get data from the cache\n\t\t\t\t// The key will always be camelCased in Data\n\t\t\t\tdata = dataUser.get( elem, key );\n\t\t\t\tif ( data !== undefined ) {\n\t\t\t\t\treturn data;\n\t\t\t\t}\n\n\t\t\t\t// Attempt to \"discover\" the data in\n\t\t\t\t// HTML5 custom data-* attrs\n\t\t\t\tdata = dataAttr( elem, key );\n\t\t\t\tif ( data !== undefined ) {\n\t\t\t\t\treturn data;\n\t\t\t\t}\n\n\t\t\t\t// We tried really hard, but the data doesn't exist.\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t// Set the data...\n\t\t\tthis.each( function() {\n\n\t\t\t\t// We always store the camelCased key\n\t\t\t\tdataUser.set( this, key, value );\n\t\t\t} );\n\t\t}, null, value, arguments.length > 1, null, true );\n\t},\n\n\tremoveData: function( key ) {\n\t\treturn this.each( function() {\n\t\t\tdataUser.remove( this, key );\n\t\t} );\n\t}\n} );\n\n\njQuery.extend( {\n\tqueue: function( elem, type, data ) {\n\t\tvar queue;\n\n\t\tif ( elem ) {\n\t\t\ttype = ( type || \"fx\" ) + \"queue\";\n\t\t\tqueue = dataPriv.get( elem, type );\n\n\t\t\t// Speed up dequeue by getting out quickly if this is just a lookup\n\t\t\tif ( data ) {\n\t\t\t\tif ( !queue || jQuery.isArray( data ) ) {\n\t\t\t\t\tqueue = dataPriv.access( elem, type, jQuery.makeArray( data ) );\n\t\t\t\t} else {\n\t\t\t\t\tqueue.push( data );\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn queue || [];\n\t\t}\n\t},\n\n\tdequeue: function( elem, type ) {\n\t\ttype = type || \"fx\";\n\n\t\tvar queue = jQuery.queue( elem, type ),\n\t\t\tstartLength = queue.length,\n\t\t\tfn = queue.shift(),\n\t\t\thooks = jQuery._queueHooks( elem, type ),\n\t\t\tnext = function() {\n\t\t\t\tjQuery.dequeue( elem, type );\n\t\t\t};\n\n\t\t// If the fx queue is dequeued, always remove the progress sentinel\n\t\tif ( fn === \"inprogress\" ) {\n\t\t\tfn = queue.shift();\n\t\t\tstartLength--;\n\t\t}\n\n\t\tif ( fn ) {\n\n\t\t\t// Add a progress sentinel to prevent the fx queue from being\n\t\t\t// automatically dequeued\n\t\t\tif ( type === \"fx\" ) {\n\t\t\t\tqueue.unshift( \"inprogress\" );\n\t\t\t}\n\n\t\t\t// Clear up the last queue stop function\n\t\t\tdelete hooks.stop;\n\t\t\tfn.call( elem, next, hooks );\n\t\t}\n\n\t\tif ( !startLength && hooks ) {\n\t\t\thooks.empty.fire();\n\t\t}\n\t},\n\n\t// Not public - generate a queueHooks object, or return the current one\n\t_queueHooks: function( elem, type ) {\n\t\tvar key = type + \"queueHooks\";\n\t\treturn dataPriv.get( elem, key ) || dataPriv.access( elem, key, {\n\t\t\tempty: jQuery.Callbacks( \"once memory\" ).add( function() {\n\t\t\t\tdataPriv.remove( elem, [ type + \"queue\", key ] );\n\t\t\t} )\n\t\t} );\n\t}\n} );\n\njQuery.fn.extend( {\n\tqueue: function( type, data ) {\n\t\tvar setter = 2;\n\n\t\tif ( typeof type !== \"string\" ) {\n\t\t\tdata = type;\n\t\t\ttype = \"fx\";\n\t\t\tsetter--;\n\t\t}\n\n\t\tif ( arguments.length < setter ) {\n\t\t\treturn jQuery.queue( this[ 0 ], type );\n\t\t}\n\n\t\treturn data === undefined ?\n\t\t\tthis :\n\t\t\tthis.each( function() {\n\t\t\t\tvar queue = jQuery.queue( this, type, data );\n\n\t\t\t\t// Ensure a hooks for this queue\n\t\t\t\tjQuery._queueHooks( this, type );\n\n\t\t\t\tif ( type === \"fx\" && queue[ 0 ] !== \"inprogress\" ) {\n\t\t\t\t\tjQuery.dequeue( this, type );\n\t\t\t\t}\n\t\t\t} );\n\t},\n\tdequeue: function( type ) {\n\t\treturn this.each( function() {\n\t\t\tjQuery.dequeue( this, type );\n\t\t} );\n\t},\n\tclearQueue: function( type ) {\n\t\treturn this.queue( type || \"fx\", [] );\n\t},\n\n\t// Get a promise resolved when queues of a certain type\n\t// are emptied (fx is the type by default)\n\tpromise: function( type, obj ) {\n\t\tvar tmp,\n\t\t\tcount = 1,\n\t\t\tdefer = jQuery.Deferred(),\n\t\t\telements = this,\n\t\t\ti = this.length,\n\t\t\tresolve = function() {\n\t\t\t\tif ( !( --count ) ) {\n\t\t\t\t\tdefer.resolveWith( elements, [ elements ] );\n\t\t\t\t}\n\t\t\t};\n\n\t\tif ( typeof type !== \"string\" ) {\n\t\t\tobj = type;\n\t\t\ttype = undefined;\n\t\t}\n\t\ttype = type || \"fx\";\n\n\t\twhile ( i-- ) {\n\t\t\ttmp = dataPriv.get( elements[ i ], type + \"queueHooks\" );\n\t\t\tif ( tmp && tmp.empty ) {\n\t\t\t\tcount++;\n\t\t\t\ttmp.empty.add( resolve );\n\t\t\t}\n\t\t}\n\t\tresolve();\n\t\treturn defer.promise( obj );\n\t}\n} );\nvar pnum = ( /[+-]?(?:\\d*\\.|)\\d+(?:[eE][+-]?\\d+|)/ ).source;\n\nvar rcssNum = new RegExp( \"^(?:([+-])=|)(\" + pnum + \")([a-z%]*)$\", \"i\" );\n\n\nvar cssExpand = [ \"Top\", \"Right\", \"Bottom\", \"Left\" ];\n\nvar isHiddenWithinTree = function( elem, el ) {\n\n\t\t// isHiddenWithinTree might be called from jQuery#filter function;\n\t\t// in that case, element will be second argument\n\t\telem = el || elem;\n\n\t\t// Inline style trumps all\n\t\treturn elem.style.display === \"none\" ||\n\t\t\telem.style.display === \"\" &&\n\n\t\t\t// Otherwise, check computed style\n\t\t\t// Support: Firefox <=43 - 45\n\t\t\t// Disconnected elements can have computed display: none, so first confirm that elem is\n\t\t\t// in the document.\n\t\t\tjQuery.contains( elem.ownerDocument, elem ) &&\n\n\t\t\tjQuery.css( elem, \"display\" ) === \"none\";\n\t};\n\nvar swap = function( elem, options, callback, args ) {\n\tvar ret, name,\n\t\told = {};\n\n\t// Remember the old values, and insert the new ones\n\tfor ( name in options ) {\n\t\told[ name ] = elem.style[ name ];\n\t\telem.style[ name ] = options[ name ];\n\t}\n\n\tret = callback.apply( elem, args || [] );\n\n\t// Revert the old values\n\tfor ( name in options ) {\n\t\telem.style[ name ] = old[ name ];\n\t}\n\n\treturn ret;\n};\n\n\n\n\nfunction adjustCSS( elem, prop, valueParts, tween ) {\n\tvar adjusted,\n\t\tscale = 1,\n\t\tmaxIterations = 20,\n\t\tcurrentValue = tween ?\n\t\t\tfunction() {\n\t\t\t\treturn tween.cur();\n\t\t\t} :\n\t\t\tfunction() {\n\t\t\t\treturn jQuery.css( elem, prop, \"\" );\n\t\t\t},\n\t\tinitial = currentValue(),\n\t\tunit = valueParts && valueParts[ 3 ] || ( jQuery.cssNumber[ prop ] ? \"\" : \"px\" ),\n\n\t\t// Starting value computation is required for potential unit mismatches\n\t\tinitialInUnit = ( jQuery.cssNumber[ prop ] || unit !== \"px\" && +initial ) &&\n\t\t\trcssNum.exec( jQuery.css( elem, prop ) );\n\n\tif ( initialInUnit && initialInUnit[ 3 ] !== unit ) {\n\n\t\t// Trust units reported by jQuery.css\n\t\tunit = unit || initialInUnit[ 3 ];\n\n\t\t// Make sure we update the tween properties later on\n\t\tvalueParts = valueParts || [];\n\n\t\t// Iteratively approximate from a nonzero starting point\n\t\tinitialInUnit = +initial || 1;\n\n\t\tdo {\n\n\t\t\t// If previous iteration zeroed out, double until we get *something*.\n\t\t\t// Use string for doubling so we don't accidentally see scale as unchanged below\n\t\t\tscale = scale || \".5\";\n\n\t\t\t// Adjust and apply\n\t\t\tinitialInUnit = initialInUnit / scale;\n\t\t\tjQuery.style( elem, prop, initialInUnit + unit );\n\n\t\t// Update scale, tolerating zero or NaN from tween.cur()\n\t\t// Break the loop if scale is unchanged or perfect, or if we've just had enough.\n\t\t} while (\n\t\t\tscale !== ( scale = currentValue() / initial ) && scale !== 1 && --maxIterations\n\t\t);\n\t}\n\n\tif ( valueParts ) {\n\t\tinitialInUnit = +initialInUnit || +initial || 0;\n\n\t\t// Apply relative offset (+=/-=) if specified\n\t\tadjusted = valueParts[ 1 ] ?\n\t\t\tinitialInUnit + ( valueParts[ 1 ] + 1 ) * valueParts[ 2 ] :\n\t\t\t+valueParts[ 2 ];\n\t\tif ( tween ) {\n\t\t\ttween.unit = unit;\n\t\t\ttween.start = initialInUnit;\n\t\t\ttween.end = adjusted;\n\t\t}\n\t}\n\treturn adjusted;\n}\n\n\nvar defaultDisplayMap = {};\n\nfunction getDefaultDisplay( elem ) {\n\tvar temp,\n\t\tdoc = elem.ownerDocument,\n\t\tnodeName = elem.nodeName,\n\t\tdisplay = defaultDisplayMap[ nodeName ];\n\n\tif ( display ) {\n\t\treturn display;\n\t}\n\n\ttemp = doc.body.appendChild( doc.createElement( nodeName ) );\n\tdisplay = jQuery.css( temp, \"display\" );\n\n\ttemp.parentNode.removeChild( temp );\n\n\tif ( display === \"none\" ) {\n\t\tdisplay = \"block\";\n\t}\n\tdefaultDisplayMap[ nodeName ] = display;\n\n\treturn display;\n}\n\nfunction showHide( elements, show ) {\n\tvar display, elem,\n\t\tvalues = [],\n\t\tindex = 0,\n\t\tlength = elements.length;\n\n\t// Determine new display value for elements that need to change\n\tfor ( ; index < length; index++ ) {\n\t\telem = elements[ index ];\n\t\tif ( !elem.style ) {\n\t\t\tcontinue;\n\t\t}\n\n\t\tdisplay = elem.style.display;\n\t\tif ( show ) {\n\n\t\t\t// Since we force visibility upon cascade-hidden elements, an immediate (and slow)\n\t\t\t// check is required in this first loop unless we have a nonempty display value (either\n\t\t\t// inline or about-to-be-restored)\n\t\t\tif ( display === \"none\" ) {\n\t\t\t\tvalues[ index ] = dataPriv.get( elem, \"display\" ) || null;\n\t\t\t\tif ( !values[ index ] ) {\n\t\t\t\t\telem.style.display = \"\";\n\t\t\t\t}\n\t\t\t}\n\t\t\tif ( elem.style.display === \"\" && isHiddenWithinTree( elem ) ) {\n\t\t\t\tvalues[ index ] = getDefaultDisplay( elem );\n\t\t\t}\n\t\t} else {\n\t\t\tif ( display !== \"none\" ) {\n\t\t\t\tvalues[ index ] = \"none\";\n\n\t\t\t\t// Remember what we're overwriting\n\t\t\t\tdataPriv.set( elem, \"display\", display );\n\t\t\t}\n\t\t}\n\t}\n\n\t// Set the display of the elements in a second loop to avoid constant reflow\n\tfor ( index = 0; index < length; index++ ) {\n\t\tif ( values[ index ] != null ) {\n\t\t\telements[ index ].style.display = values[ index ];\n\t\t}\n\t}\n\n\treturn elements;\n}\n\njQuery.fn.extend( {\n\tshow: function() {\n\t\treturn showHide( this, true );\n\t},\n\thide: function() {\n\t\treturn showHide( this );\n\t},\n\ttoggle: function( state ) {\n\t\tif ( typeof state === \"boolean\" ) {\n\t\t\treturn state ? this.show() : this.hide();\n\t\t}\n\n\t\treturn this.each( function() {\n\t\t\tif ( isHiddenWithinTree( this ) ) {\n\t\t\t\tjQuery( this ).show();\n\t\t\t} else {\n\t\t\t\tjQuery( this ).hide();\n\t\t\t}\n\t\t} );\n\t}\n} );\nvar rcheckableType = ( /^(?:checkbox|radio)$/i );\n\nvar rtagName = ( /<([a-z][^\\/\\0>\\x20\\t\\r\\n\\f]+)/i );\n\nvar rscriptType = ( /^$|\\/(?:java|ecma)script/i );\n\n\n\n// We have to close these tags to support XHTML (#13200)\nvar wrapMap = {\n\n\t// Support: IE <=9 only\n\toption: [ 1, \"<select multiple='multiple'>\", \"</select>\" ],\n\n\t// XHTML parsers do not magically insert elements in the\n\t// same way that tag soup parsers do. So we cannot shorten\n\t// this by omitting <tbody> or other required elements.\n\tthead: [ 1, \"<table>\", \"</table>\" ],\n\tcol: [ 2, \"<table><colgroup>\", \"</colgroup></table>\" ],\n\ttr: [ 2, \"<table><tbody>\", \"</tbody></table>\" ],\n\ttd: [ 3, \"<table><tbody><tr>\", \"</tr></tbody></table>\" ],\n\n\t_default: [ 0, \"\", \"\" ]\n};\n\n// Support: IE <=9 only\nwrapMap.optgroup = wrapMap.option;\n\nwrapMap.tbody = wrapMap.tfoot = wrapMap.colgroup = wrapMap.caption = wrapMap.thead;\nwrapMap.th = wrapMap.td;\n\n\nfunction getAll( context, tag ) {\n\n\t// Support: IE <=9 - 11 only\n\t// Use typeof to avoid zero-argument method invocation on host objects (#15151)\n\tvar ret;\n\n\tif ( typeof context.getElementsByTagName !== \"undefined\" ) {\n\t\tret = context.getElementsByTagName( tag || \"*\" );\n\n\t} else if ( typeof context.querySelectorAll !== \"undefined\" ) {\n\t\tret = context.querySelectorAll( tag || \"*\" );\n\n\t} else {\n\t\tret = [];\n\t}\n\n\tif ( tag === undefined || tag && jQuery.nodeName( context, tag ) ) {\n\t\treturn jQuery.merge( [ context ], ret );\n\t}\n\n\treturn ret;\n}\n\n\n// Mark scripts as having already been evaluated\nfunction setGlobalEval( elems, refElements ) {\n\tvar i = 0,\n\t\tl = elems.length;\n\n\tfor ( ; i < l; i++ ) {\n\t\tdataPriv.set(\n\t\t\telems[ i ],\n\t\t\t\"globalEval\",\n\t\t\t!refElements || dataPriv.get( refElements[ i ], \"globalEval\" )\n\t\t);\n\t}\n}\n\n\nvar rhtml = /<|&#?\\w+;/;\n\nfunction buildFragment( elems, context, scripts, selection, ignored ) {\n\tvar elem, tmp, tag, wrap, contains, j,\n\t\tfragment = context.createDocumentFragment(),\n\t\tnodes = [],\n\t\ti = 0,\n\t\tl = elems.length;\n\n\tfor ( ; i < l; i++ ) {\n\t\telem = elems[ i ];\n\n\t\tif ( elem || elem === 0 ) {\n\n\t\t\t// Add nodes directly\n\t\t\tif ( jQuery.type( elem ) === \"object\" ) {\n\n\t\t\t\t// Support: Android <=4.0 only, PhantomJS 1 only\n\t\t\t\t// push.apply(_, arraylike) throws on ancient WebKit\n\t\t\t\tjQuery.merge( nodes, elem.nodeType ? [ elem ] : elem );\n\n\t\t\t// Convert non-html into a text node\n\t\t\t} else if ( !rhtml.test( elem ) ) {\n\t\t\t\tnodes.push( context.createTextNode( elem ) );\n\n\t\t\t// Convert html into DOM nodes\n\t\t\t} else {\n\t\t\t\ttmp = tmp || fragment.appendChild( context.createElement( \"div\" ) );\n\n\t\t\t\t// Deserialize a standard representation\n\t\t\t\ttag = ( rtagName.exec( elem ) || [ \"\", \"\" ] )[ 1 ].toLowerCase();\n\t\t\t\twrap = wrapMap[ tag ] || wrapMap._default;\n\t\t\t\ttmp.innerHTML = wrap[ 1 ] + jQuery.htmlPrefilter( elem ) + wrap[ 2 ];\n\n\t\t\t\t// Descend through wrappers to the right content\n\t\t\t\tj = wrap[ 0 ];\n\t\t\t\twhile ( j-- ) {\n\t\t\t\t\ttmp = tmp.lastChild;\n\t\t\t\t}\n\n\t\t\t\t// Support: Android <=4.0 only, PhantomJS 1 only\n\t\t\t\t// push.apply(_, arraylike) throws on ancient WebKit\n\t\t\t\tjQuery.merge( nodes, tmp.childNodes );\n\n\t\t\t\t// Remember the top-level container\n\t\t\t\ttmp = fragment.firstChild;\n\n\t\t\t\t// Ensure the created nodes are orphaned (#12392)\n\t\t\t\ttmp.textContent = \"\";\n\t\t\t}\n\t\t}\n\t}\n\n\t// Remove wrapper from fragment\n\tfragment.textContent = \"\";\n\n\ti = 0;\n\twhile ( ( elem = nodes[ i++ ] ) ) {\n\n\t\t// Skip elements already in the context collection (trac-4087)\n\t\tif ( selection && jQuery.inArray( elem, selection ) > -1 ) {\n\t\t\tif ( ignored ) {\n\t\t\t\tignored.push( elem );\n\t\t\t}\n\t\t\tcontinue;\n\t\t}\n\n\t\tcontains = jQuery.contains( elem.ownerDocument, elem );\n\n\t\t// Append to fragment\n\t\ttmp = getAll( fragment.appendChild( elem ), \"script\" );\n\n\t\t// Preserve script evaluation history\n\t\tif ( contains ) {\n\t\t\tsetGlobalEval( tmp );\n\t\t}\n\n\t\t// Capture executables\n\t\tif ( scripts ) {\n\t\t\tj = 0;\n\t\t\twhile ( ( elem = tmp[ j++ ] ) ) {\n\t\t\t\tif ( rscriptType.test( elem.type || \"\" ) ) {\n\t\t\t\t\tscripts.push( elem );\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\treturn fragment;\n}\n\n\n( function() {\n\tvar fragment = document.createDocumentFragment(),\n\t\tdiv = fragment.appendChild( document.createElement( \"div\" ) ),\n\t\tinput = document.createElement( \"input\" );\n\n\t// Support: Android 4.0 - 4.3 only\n\t// Check state lost if the name is set (#11217)\n\t// Support: Windows Web Apps (WWA)\n\t// `name` and `type` must use .setAttribute for WWA (#14901)\n\tinput.setAttribute( \"type\", \"radio\" );\n\tinput.setAttribute( \"checked\", \"checked\" );\n\tinput.setAttribute( \"name\", \"t\" );\n\n\tdiv.appendChild( input );\n\n\t// Support: Android <=4.1 only\n\t// Older WebKit doesn't clone checked state correctly in fragments\n\tsupport.checkClone = div.cloneNode( true ).cloneNode( true ).lastChild.checked;\n\n\t// Support: IE <=11 only\n\t// Make sure textarea (and checkbox) defaultValue is properly cloned\n\tdiv.innerHTML = \"<textarea>x</textarea>\";\n\tsupport.noCloneChecked = !!div.cloneNode( true ).lastChild.defaultValue;\n} )();\nvar documentElement = document.documentElement;\n\n\n\nvar\n\trkeyEvent = /^key/,\n\trmouseEvent = /^(?:mouse|pointer|contextmenu|drag|drop)|click/,\n\trtypenamespace = /^([^.]*)(?:\\.(.+)|)/;\n\nfunction returnTrue() {\n\treturn true;\n}\n\nfunction returnFalse() {\n\treturn false;\n}\n\n// Support: IE <=9 only\n// See #13393 for more info\nfunction safeActiveElement() {\n\ttry {\n\t\treturn document.activeElement;\n\t} catch ( err ) { }\n}\n\nfunction on( elem, types, selector, data, fn, one ) {\n\tvar origFn, type;\n\n\t// Types can be a map of types/handlers\n\tif ( typeof types === \"object\" ) {\n\n\t\t// ( types-Object, selector, data )\n\t\tif ( typeof selector !== \"string\" ) {\n\n\t\t\t// ( types-Object, data )\n\t\t\tdata = data || selector;\n\t\t\tselector = undefined;\n\t\t}\n\t\tfor ( type in types ) {\n\t\t\ton( elem, type, selector, data, types[ type ], one );\n\t\t}\n\t\treturn elem;\n\t}\n\n\tif ( data == null && fn == null ) {\n\n\t\t// ( types, fn )\n\t\tfn = selector;\n\t\tdata = selector = undefined;\n\t} else if ( fn == null ) {\n\t\tif ( typeof selector === \"string\" ) {\n\n\t\t\t// ( types, selector, fn )\n\t\t\tfn = data;\n\t\t\tdata = undefined;\n\t\t} else {\n\n\t\t\t// ( types, data, fn )\n\t\t\tfn = data;\n\t\t\tdata = selector;\n\t\t\tselector = undefined;\n\t\t}\n\t}\n\tif ( fn === false ) {\n\t\tfn = returnFalse;\n\t} else if ( !fn ) {\n\t\treturn elem;\n\t}\n\n\tif ( one === 1 ) {\n\t\torigFn = fn;\n\t\tfn = function( event ) {\n\n\t\t\t// Can use an empty set, since event contains the info\n\t\t\tjQuery().off( event );\n\t\t\treturn origFn.apply( this, arguments );\n\t\t};\n\n\t\t// Use same guid so caller can remove using origFn\n\t\tfn.guid = origFn.guid || ( origFn.guid = jQuery.guid++ );\n\t}\n\treturn elem.each( function() {\n\t\tjQuery.event.add( this, types, fn, data, selector );\n\t} );\n}\n\n/*\n * Helper functions for managing events -- not part of the public interface.\n * Props to Dean Edwards' addEvent library for many of the ideas.\n */\njQuery.event = {\n\n\tglobal: {},\n\n\tadd: function( elem, types, handler, data, selector ) {\n\n\t\tvar handleObjIn, eventHandle, tmp,\n\t\t\tevents, t, handleObj,\n\t\t\tspecial, handlers, type, namespaces, origType,\n\t\t\telemData = dataPriv.get( elem );\n\n\t\t// Don't attach events to noData or text/comment nodes (but allow plain objects)\n\t\tif ( !elemData ) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Caller can pass in an object of custom data in lieu of the handler\n\t\tif ( handler.handler ) {\n\t\t\thandleObjIn = handler;\n\t\t\thandler = handleObjIn.handler;\n\t\t\tselector = handleObjIn.selector;\n\t\t}\n\n\t\t// Ensure that invalid selectors throw exceptions at attach time\n\t\t// Evaluate against documentElement in case elem is a non-element node (e.g., document)\n\t\tif ( selector ) {\n\t\t\tjQuery.find.matchesSelector( documentElement, selector );\n\t\t}\n\n\t\t// Make sure that the handler has a unique ID, used to find/remove it later\n\t\tif ( !handler.guid ) {\n\t\t\thandler.guid = jQuery.guid++;\n\t\t}\n\n\t\t// Init the element's event structure and main handler, if this is the first\n\t\tif ( !( events = elemData.events ) ) {\n\t\t\tevents = elemData.events = {};\n\t\t}\n\t\tif ( !( eventHandle = elemData.handle ) ) {\n\t\t\teventHandle = elemData.handle = function( e ) {\n\n\t\t\t\t// Discard the second event of a jQuery.event.trigger() and\n\t\t\t\t// when an event is called after a page has unloaded\n\t\t\t\treturn typeof jQuery !== \"undefined\" && jQuery.event.triggered !== e.type ?\n\t\t\t\t\tjQuery.event.dispatch.apply( elem, arguments ) : undefined;\n\t\t\t};\n\t\t}\n\n\t\t// Handle multiple events separated by a space\n\t\ttypes = ( types || \"\" ).match( rnothtmlwhite ) || [ \"\" ];\n\t\tt = types.length;\n\t\twhile ( t-- ) {\n\t\t\ttmp = rtypenamespace.exec( types[ t ] ) || [];\n\t\t\ttype = origType = tmp[ 1 ];\n\t\t\tnamespaces = ( tmp[ 2 ] || \"\" ).split( \".\" ).sort();\n\n\t\t\t// There *must* be a type, no attaching namespace-only handlers\n\t\t\tif ( !type ) {\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\t// If event changes its type, use the special event handlers for the changed type\n\t\t\tspecial = jQuery.event.special[ type ] || {};\n\n\t\t\t// If selector defined, determine special event api type, otherwise given type\n\t\t\ttype = ( selector ? special.delegateType : special.bindType ) || type;\n\n\t\t\t// Update special based on newly reset type\n\t\t\tspecial = jQuery.event.special[ type ] || {};\n\n\t\t\t// handleObj is passed to all event handlers\n\t\t\thandleObj = jQuery.extend( {\n\t\t\t\ttype: type,\n\t\t\t\torigType: origType,\n\t\t\t\tdata: data,\n\t\t\t\thandler: handler,\n\t\t\t\tguid: handler.guid,\n\t\t\t\tselector: selector,\n\t\t\t\tneedsContext: selector && jQuery.expr.match.needsContext.test( selector ),\n\t\t\t\tnamespace: namespaces.join( \".\" )\n\t\t\t}, handleObjIn );\n\n\t\t\t// Init the event handler queue if we're the first\n\t\t\tif ( !( handlers = events[ type ] ) ) {\n\t\t\t\thandlers = events[ type ] = [];\n\t\t\t\thandlers.delegateCount = 0;\n\n\t\t\t\t// Only use addEventListener if the special events handler returns false\n\t\t\t\tif ( !special.setup ||\n\t\t\t\t\tspecial.setup.call( elem, data, namespaces, eventHandle ) === false ) {\n\n\t\t\t\t\tif ( elem.addEventListener ) {\n\t\t\t\t\t\telem.addEventListener( type, eventHandle );\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif ( special.add ) {\n\t\t\t\tspecial.add.call( elem, handleObj );\n\n\t\t\t\tif ( !handleObj.handler.guid ) {\n\t\t\t\t\thandleObj.handler.guid = handler.guid;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Add to the element's handler list, delegates in front\n\t\t\tif ( selector ) {\n\t\t\t\thandlers.splice( handlers.delegateCount++, 0, handleObj );\n\t\t\t} else {\n\t\t\t\thandlers.push( handleObj );\n\t\t\t}\n\n\t\t\t// Keep track of which events have ever been used, for event optimization\n\t\t\tjQuery.event.global[ type ] = true;\n\t\t}\n\n\t},\n\n\t// Detach an event or set of events from an element\n\tremove: function( elem, types, handler, selector, mappedTypes ) {\n\n\t\tvar j, origCount, tmp,\n\t\t\tevents, t, handleObj,\n\t\t\tspecial, handlers, type, namespaces, origType,\n\t\t\telemData = dataPriv.hasData( elem ) && dataPriv.get( elem );\n\n\t\tif ( !elemData || !( events = elemData.events ) ) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Once for each type.namespace in types; type may be omitted\n\t\ttypes = ( types || \"\" ).match( rnothtmlwhite ) || [ \"\" ];\n\t\tt = types.length;\n\t\twhile ( t-- ) {\n\t\t\ttmp = rtypenamespace.exec( types[ t ] ) || [];\n\t\t\ttype = origType = tmp[ 1 ];\n\t\t\tnamespaces = ( tmp[ 2 ] || \"\" ).split( \".\" ).sort();\n\n\t\t\t// Unbind all events (on this namespace, if provided) for the element\n\t\t\tif ( !type ) {\n\t\t\t\tfor ( type in events ) {\n\t\t\t\t\tjQuery.event.remove( elem, type + types[ t ], handler, selector, true );\n\t\t\t\t}\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tspecial = jQuery.event.special[ type ] || {};\n\t\t\ttype = ( selector ? special.delegateType : special.bindType ) || type;\n\t\t\thandlers = events[ type ] || [];\n\t\t\ttmp = tmp[ 2 ] &&\n\t\t\t\tnew RegExp( \"(^|\\\\.)\" + namespaces.join( \"\\\\.(?:.*\\\\.|)\" ) + \"(\\\\.|$)\" );\n\n\t\t\t// Remove matching events\n\t\t\torigCount = j = handlers.length;\n\t\t\twhile ( j-- ) {\n\t\t\t\thandleObj = handlers[ j ];\n\n\t\t\t\tif ( ( mappedTypes || origType === handleObj.origType ) &&\n\t\t\t\t\t( !handler || handler.guid === handleObj.guid ) &&\n\t\t\t\t\t( !tmp || tmp.test( handleObj.namespace ) ) &&\n\t\t\t\t\t( !selector || selector === handleObj.selector ||\n\t\t\t\t\t\tselector === \"**\" && handleObj.selector ) ) {\n\t\t\t\t\thandlers.splice( j, 1 );\n\n\t\t\t\t\tif ( handleObj.selector ) {\n\t\t\t\t\t\thandlers.delegateCount--;\n\t\t\t\t\t}\n\t\t\t\t\tif ( special.remove ) {\n\t\t\t\t\t\tspecial.remove.call( elem, handleObj );\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Remove generic event handler if we removed something and no more handlers exist\n\t\t\t// (avoids potential for endless recursion during removal of special event handlers)\n\t\t\tif ( origCount && !handlers.length ) {\n\t\t\t\tif ( !special.teardown ||\n\t\t\t\t\tspecial.teardown.call( elem, namespaces, elemData.handle ) === false ) {\n\n\t\t\t\t\tjQuery.removeEvent( elem, type, elemData.handle );\n\t\t\t\t}\n\n\t\t\t\tdelete events[ type ];\n\t\t\t}\n\t\t}\n\n\t\t// Remove data and the expando if it's no longer used\n\t\tif ( jQuery.isEmptyObject( events ) ) {\n\t\t\tdataPriv.remove( elem, \"handle events\" );\n\t\t}\n\t},\n\n\tdispatch: function( nativeEvent ) {\n\n\t\t// Make a writable jQuery.Event from the native event object\n\t\tvar event = jQuery.event.fix( nativeEvent );\n\n\t\tvar i, j, ret, matched, handleObj, handlerQueue,\n\t\t\targs = new Array( arguments.length ),\n\t\t\thandlers = ( dataPriv.get( this, \"events\" ) || {} )[ event.type ] || [],\n\t\t\tspecial = jQuery.event.special[ event.type ] || {};\n\n\t\t// Use the fix-ed jQuery.Event rather than the (read-only) native event\n\t\targs[ 0 ] = event;\n\n\t\tfor ( i = 1; i < arguments.length; i++ ) {\n\t\t\targs[ i ] = arguments[ i ];\n\t\t}\n\n\t\tevent.delegateTarget = this;\n\n\t\t// Call the preDispatch hook for the mapped type, and let it bail if desired\n\t\tif ( special.preDispatch && special.preDispatch.call( this, event ) === false ) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Determine handlers\n\t\thandlerQueue = jQuery.event.handlers.call( this, event, handlers );\n\n\t\t// Run delegates first; they may want to stop propagation beneath us\n\t\ti = 0;\n\t\twhile ( ( matched = handlerQueue[ i++ ] ) && !event.isPropagationStopped() ) {\n\t\t\tevent.currentTarget = matched.elem;\n\n\t\t\tj = 0;\n\t\t\twhile ( ( handleObj = matched.handlers[ j++ ] ) &&\n\t\t\t\t!event.isImmediatePropagationStopped() ) {\n\n\t\t\t\t// Triggered event must either 1) have no namespace, or 2) have namespace(s)\n\t\t\t\t// a subset or equal to those in the bound event (both can have no namespace).\n\t\t\t\tif ( !event.rnamespace || event.rnamespace.test( handleObj.namespace ) ) {\n\n\t\t\t\t\tevent.handleObj = handleObj;\n\t\t\t\t\tevent.data = handleObj.data;\n\n\t\t\t\t\tret = ( ( jQuery.event.special[ handleObj.origType ] || {} ).handle ||\n\t\t\t\t\t\thandleObj.handler ).apply( matched.elem, args );\n\n\t\t\t\t\tif ( ret !== undefined ) {\n\t\t\t\t\t\tif ( ( event.result = ret ) === false ) {\n\t\t\t\t\t\t\tevent.preventDefault();\n\t\t\t\t\t\t\tevent.stopPropagation();\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Call the postDispatch hook for the mapped type\n\t\tif ( special.postDispatch ) {\n\t\t\tspecial.postDispatch.call( this, event );\n\t\t}\n\n\t\treturn event.result;\n\t},\n\n\thandlers: function( event, handlers ) {\n\t\tvar i, handleObj, sel, matchedHandlers, matchedSelectors,\n\t\t\thandlerQueue = [],\n\t\t\tdelegateCount = handlers.delegateCount,\n\t\t\tcur = event.target;\n\n\t\t// Find delegate handlers\n\t\tif ( delegateCount &&\n\n\t\t\t// Support: IE <=9\n\t\t\t// Black-hole SVG <use> instance trees (trac-13180)\n\t\t\tcur.nodeType &&\n\n\t\t\t// Support: Firefox <=42\n\t\t\t// Suppress spec-violating clicks indicating a non-primary pointer button (trac-3861)\n\t\t\t// https://www.w3.org/TR/DOM-Level-3-Events/#event-type-click\n\t\t\t// Support: IE 11 only\n\t\t\t// ...but not arrow key \"clicks\" of radio inputs, which can have `button` -1 (gh-2343)\n\t\t\t!( event.type === \"click\" && event.button >= 1 ) ) {\n\n\t\t\tfor ( ; cur !== this; cur = cur.parentNode || this ) {\n\n\t\t\t\t// Don't check non-elements (#13208)\n\t\t\t\t// Don't process clicks on disabled elements (#6911, #8165, #11382, #11764)\n\t\t\t\tif ( cur.nodeType === 1 && !( event.type === \"click\" && cur.disabled === true ) ) {\n\t\t\t\t\tmatchedHandlers = [];\n\t\t\t\t\tmatchedSelectors = {};\n\t\t\t\t\tfor ( i = 0; i < delegateCount; i++ ) {\n\t\t\t\t\t\thandleObj = handlers[ i ];\n\n\t\t\t\t\t\t// Don't conflict with Object.prototype properties (#13203)\n\t\t\t\t\t\tsel = handleObj.selector + \" \";\n\n\t\t\t\t\t\tif ( matchedSelectors[ sel ] === undefined ) {\n\t\t\t\t\t\t\tmatchedSelectors[ sel ] = handleObj.needsContext ?\n\t\t\t\t\t\t\t\tjQuery( sel, this ).index( cur ) > -1 :\n\t\t\t\t\t\t\t\tjQuery.find( sel, this, null, [ cur ] ).length;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif ( matchedSelectors[ sel ] ) {\n\t\t\t\t\t\t\tmatchedHandlers.push( handleObj );\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif ( matchedHandlers.length ) {\n\t\t\t\t\t\thandlerQueue.push( { elem: cur, handlers: matchedHandlers } );\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Add the remaining (directly-bound) handlers\n\t\tcur = this;\n\t\tif ( delegateCount < handlers.length ) {\n\t\t\thandlerQueue.push( { elem: cur, handlers: handlers.slice( delegateCount ) } );\n\t\t}\n\n\t\treturn handlerQueue;\n\t},\n\n\taddProp: function( name, hook ) {\n\t\tObject.defineProperty( jQuery.Event.prototype, name, {\n\t\t\tenumerable: true,\n\t\t\tconfigurable: true,\n\n\t\t\tget: jQuery.isFunction( hook ) ?\n\t\t\t\tfunction() {\n\t\t\t\t\tif ( this.originalEvent ) {\n\t\t\t\t\t\t\treturn hook( this.originalEvent );\n\t\t\t\t\t}\n\t\t\t\t} :\n\t\t\t\tfunction() {\n\t\t\t\t\tif ( this.originalEvent ) {\n\t\t\t\t\t\t\treturn this.originalEvent[ name ];\n\t\t\t\t\t}\n\t\t\t\t},\n\n\t\t\tset: function( value ) {\n\t\t\t\tObject.defineProperty( this, name, {\n\t\t\t\t\tenumerable: true,\n\t\t\t\t\tconfigurable: true,\n\t\t\t\t\twritable: true,\n\t\t\t\t\tvalue: value\n\t\t\t\t} );\n\t\t\t}\n\t\t} );\n\t},\n\n\tfix: function( originalEvent ) {\n\t\treturn originalEvent[ jQuery.expando ] ?\n\t\t\toriginalEvent :\n\t\t\tnew jQuery.Event( originalEvent );\n\t},\n\n\tspecial: {\n\t\tload: {\n\n\t\t\t// Prevent triggered image.load events from bubbling to window.load\n\t\t\tnoBubble: true\n\t\t},\n\t\tfocus: {\n\n\t\t\t// Fire native event if possible so blur/focus sequence is correct\n\t\t\ttrigger: function() {\n\t\t\t\tif ( this !== safeActiveElement() && this.focus ) {\n\t\t\t\t\tthis.focus();\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t},\n\t\t\tdelegateType: \"focusin\"\n\t\t},\n\t\tblur: {\n\t\t\ttrigger: function() {\n\t\t\t\tif ( this === safeActiveElement() && this.blur ) {\n\t\t\t\t\tthis.blur();\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t},\n\t\t\tdelegateType: \"focusout\"\n\t\t},\n\t\tclick: {\n\n\t\t\t// For checkbox, fire native event so checked state will be right\n\t\t\ttrigger: function() {\n\t\t\t\tif ( this.type === \"checkbox\" && this.click && jQuery.nodeName( this, \"input\" ) ) {\n\t\t\t\t\tthis.click();\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t},\n\n\t\t\t// For cross-browser consistency, don't fire native .click() on links\n\t\t\t_default: function( event ) {\n\t\t\t\treturn jQuery.nodeName( event.target, \"a\" );\n\t\t\t}\n\t\t},\n\n\t\tbeforeunload: {\n\t\t\tpostDispatch: function( event ) {\n\n\t\t\t\t// Support: Firefox 20+\n\t\t\t\t// Firefox doesn't alert if the returnValue field is not set.\n\t\t\t\tif ( event.result !== undefined && event.originalEvent ) {\n\t\t\t\t\tevent.originalEvent.returnValue = event.result;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n};\n\njQuery.removeEvent = function( elem, type, handle ) {\n\n\t// This \"if\" is needed for plain objects\n\tif ( elem.removeEventListener ) {\n\t\telem.removeEventListener( type, handle );\n\t}\n};\n\njQuery.Event = function( src, props ) {\n\n\t// Allow instantiation without the 'new' keyword\n\tif ( !( this instanceof jQuery.Event ) ) {\n\t\treturn new jQuery.Event( src, props );\n\t}\n\n\t// Event object\n\tif ( src && src.type ) {\n\t\tthis.originalEvent = src;\n\t\tthis.type = src.type;\n\n\t\t// Events bubbling up the document may have been marked as prevented\n\t\t// by a handler lower down the tree; reflect the correct value.\n\t\tthis.isDefaultPrevented = src.defaultPrevented ||\n\t\t\t\tsrc.defaultPrevented === undefined &&\n\n\t\t\t\t// Support: Android <=2.3 only\n\t\t\t\tsrc.returnValue === false ?\n\t\t\treturnTrue :\n\t\t\treturnFalse;\n\n\t\t// Create target properties\n\t\t// Support: Safari <=6 - 7 only\n\t\t// Target should not be a text node (#504, #13143)\n\t\tthis.target = ( src.target && src.target.nodeType === 3 ) ?\n\t\t\tsrc.target.parentNode :\n\t\t\tsrc.target;\n\n\t\tthis.currentTarget = src.currentTarget;\n\t\tthis.relatedTarget = src.relatedTarget;\n\n\t// Event type\n\t} else {\n\t\tthis.type = src;\n\t}\n\n\t// Put explicitly provided properties onto the event object\n\tif ( props ) {\n\t\tjQuery.extend( this, props );\n\t}\n\n\t// Create a timestamp if incoming event doesn't have one\n\tthis.timeStamp = src && src.timeStamp || jQuery.now();\n\n\t// Mark it as fixed\n\tthis[ jQuery.expando ] = true;\n};\n\n// jQuery.Event is based on DOM3 Events as specified by the ECMAScript Language Binding\n// https://www.w3.org/TR/2003/WD-DOM-Level-3-Events-20030331/ecma-script-binding.html\njQuery.Event.prototype = {\n\tconstructor: jQuery.Event,\n\tisDefaultPrevented: returnFalse,\n\tisPropagationStopped: returnFalse,\n\tisImmediatePropagationStopped: returnFalse,\n\tisSimulated: false,\n\n\tpreventDefault: function() {\n\t\tvar e = this.originalEvent;\n\n\t\tthis.isDefaultPrevented = returnTrue;\n\n\t\tif ( e && !this.isSimulated ) {\n\t\t\te.preventDefault();\n\t\t}\n\t},\n\tstopPropagation: function() {\n\t\tvar e = this.originalEvent;\n\n\t\tthis.isPropagationStopped = returnTrue;\n\n\t\tif ( e && !this.isSimulated ) {\n\t\t\te.stopPropagation();\n\t\t}\n\t},\n\tstopImmediatePropagation: function() {\n\t\tvar e = this.originalEvent;\n\n\t\tthis.isImmediatePropagationStopped = returnTrue;\n\n\t\tif ( e && !this.isSimulated ) {\n\t\t\te.stopImmediatePropagation();\n\t\t}\n\n\t\tthis.stopPropagation();\n\t}\n};\n\n// Includes all common event props including KeyEvent and MouseEvent specific props\njQuery.each( {\n\taltKey: true,\n\tbubbles: true,\n\tcancelable: true,\n\tchangedTouches: true,\n\tctrlKey: true,\n\tdetail: true,\n\teventPhase: true,\n\tmetaKey: true,\n\tpageX: true,\n\tpageY: true,\n\tshiftKey: true,\n\tview: true,\n\t\"char\": true,\n\tcharCode: true,\n\tkey: true,\n\tkeyCode: true,\n\tbutton: true,\n\tbuttons: true,\n\tclientX: true,\n\tclientY: true,\n\toffsetX: true,\n\toffsetY: true,\n\tpointerId: true,\n\tpointerType: true,\n\tscreenX: true,\n\tscreenY: true,\n\ttargetTouches: true,\n\ttoElement: true,\n\ttouches: true,\n\n\twhich: function( event ) {\n\t\tvar button = event.button;\n\n\t\t// Add which for key events\n\t\tif ( event.which == null && rkeyEvent.test( event.type ) ) {\n\t\t\treturn event.charCode != null ? event.charCode : event.keyCode;\n\t\t}\n\n\t\t// Add which for click: 1 === left; 2 === middle; 3 === right\n\t\tif ( !event.which && button !== undefined && rmouseEvent.test( event.type ) ) {\n\t\t\tif ( button & 1 ) {\n\t\t\t\treturn 1;\n\t\t\t}\n\n\t\t\tif ( button & 2 ) {\n\t\t\t\treturn 3;\n\t\t\t}\n\n\t\t\tif ( button & 4 ) {\n\t\t\t\treturn 2;\n\t\t\t}\n\n\t\t\treturn 0;\n\t\t}\n\n\t\treturn event.which;\n\t}\n}, jQuery.event.addProp );\n\n// Create mouseenter/leave events using mouseover/out and event-time checks\n// so that event delegation works in jQuery.\n// Do the same for pointerenter/pointerleave and pointerover/pointerout\n//\n// Support: Safari 7 only\n// Safari sends mouseenter too often; see:\n// https://bugs.chromium.org/p/chromium/issues/detail?id=470258\n// for the description of the bug (it existed in older Chrome versions as well).\njQuery.each( {\n\tmouseenter: \"mouseover\",\n\tmouseleave: \"mouseout\",\n\tpointerenter: \"pointerover\",\n\tpointerleave: \"pointerout\"\n}, function( orig, fix ) {\n\tjQuery.event.special[ orig ] = {\n\t\tdelegateType: fix,\n\t\tbindType: fix,\n\n\t\thandle: function( event ) {\n\t\t\tvar ret,\n\t\t\t\ttarget = this,\n\t\t\t\trelated = event.relatedTarget,\n\t\t\t\thandleObj = event.handleObj;\n\n\t\t\t// For mouseenter/leave call the handler if related is outside the target.\n\t\t\t// NB: No relatedTarget if the mouse left/entered the browser window\n\t\t\tif ( !related || ( related !== target && !jQuery.contains( target, related ) ) ) {\n\t\t\t\tevent.type = handleObj.origType;\n\t\t\t\tret = handleObj.handler.apply( this, arguments );\n\t\t\t\tevent.type = fix;\n\t\t\t}\n\t\t\treturn ret;\n\t\t}\n\t};\n} );\n\njQuery.fn.extend( {\n\n\ton: function( types, selector, data, fn ) {\n\t\treturn on( this, types, selector, data, fn );\n\t},\n\tone: function( types, selector, data, fn ) {\n\t\treturn on( this, types, selector, data, fn, 1 );\n\t},\n\toff: function( types, selector, fn ) {\n\t\tvar handleObj, type;\n\t\tif ( types && types.preventDefault && types.handleObj ) {\n\n\t\t\t// ( event )  dispatched jQuery.Event\n\t\t\thandleObj = types.handleObj;\n\t\t\tjQuery( types.delegateTarget ).off(\n\t\t\t\thandleObj.namespace ?\n\t\t\t\t\thandleObj.origType + \".\" + handleObj.namespace :\n\t\t\t\t\thandleObj.origType,\n\t\t\t\thandleObj.selector,\n\t\t\t\thandleObj.handler\n\t\t\t);\n\t\t\treturn this;\n\t\t}\n\t\tif ( typeof types === \"object\" ) {\n\n\t\t\t// ( types-object [, selector] )\n\t\t\tfor ( type in types ) {\n\t\t\t\tthis.off( type, selector, types[ type ] );\n\t\t\t}\n\t\t\treturn this;\n\t\t}\n\t\tif ( selector === false || typeof selector === \"function\" ) {\n\n\t\t\t// ( types [, fn] )\n\t\t\tfn = selector;\n\t\t\tselector = undefined;\n\t\t}\n\t\tif ( fn === false ) {\n\t\t\tfn = returnFalse;\n\t\t}\n\t\treturn this.each( function() {\n\t\t\tjQuery.event.remove( this, types, fn, selector );\n\t\t} );\n\t}\n} );\n\n\nvar\n\n\t/* eslint-disable max-len */\n\n\t// See https://github.com/eslint/eslint/issues/3229\n\trxhtmlTag = /<(?!area|br|col|embed|hr|img|input|link|meta|param)(([a-z][^\\/\\0>\\x20\\t\\r\\n\\f]*)[^>]*)\\/>/gi,\n\n\t/* eslint-enable */\n\n\t// Support: IE <=10 - 11, Edge 12 - 13\n\t// In IE/Edge using regex groups here causes severe slowdowns.\n\t// See https://connect.microsoft.com/IE/feedback/details/1736512/\n\trnoInnerhtml = /<script|<style|<link/i,\n\n\t// checked=\"checked\" or checked\n\trchecked = /checked\\s*(?:[^=]|=\\s*.checked.)/i,\n\trscriptTypeMasked = /^true\\/(.*)/,\n\trcleanScript = /^\\s*<!(?:\\[CDATA\\[|--)|(?:\\]\\]|--)>\\s*$/g;\n\nfunction manipulationTarget( elem, content ) {\n\tif ( jQuery.nodeName( elem, \"table\" ) &&\n\t\tjQuery.nodeName( content.nodeType !== 11 ? content : content.firstChild, \"tr\" ) ) {\n\n\t\treturn elem.getElementsByTagName( \"tbody\" )[ 0 ] || elem;\n\t}\n\n\treturn elem;\n}\n\n// Replace/restore the type attribute of script elements for safe DOM manipulation\nfunction disableScript( elem ) {\n\telem.type = ( elem.getAttribute( \"type\" ) !== null ) + \"/\" + elem.type;\n\treturn elem;\n}\nfunction restoreScript( elem ) {\n\tvar match = rscriptTypeMasked.exec( elem.type );\n\n\tif ( match ) {\n\t\telem.type = match[ 1 ];\n\t} else {\n\t\telem.removeAttribute( \"type\" );\n\t}\n\n\treturn elem;\n}\n\nfunction cloneCopyEvent( src, dest ) {\n\tvar i, l, type, pdataOld, pdataCur, udataOld, udataCur, events;\n\n\tif ( dest.nodeType !== 1 ) {\n\t\treturn;\n\t}\n\n\t// 1. Copy private data: events, handlers, etc.\n\tif ( dataPriv.hasData( src ) ) {\n\t\tpdataOld = dataPriv.access( src );\n\t\tpdataCur = dataPriv.set( dest, pdataOld );\n\t\tevents = pdataOld.events;\n\n\t\tif ( events ) {\n\t\t\tdelete pdataCur.handle;\n\t\t\tpdataCur.events = {};\n\n\t\t\tfor ( type in events ) {\n\t\t\t\tfor ( i = 0, l = events[ type ].length; i < l; i++ ) {\n\t\t\t\t\tjQuery.event.add( dest, type, events[ type ][ i ] );\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// 2. Copy user data\n\tif ( dataUser.hasData( src ) ) {\n\t\tudataOld = dataUser.access( src );\n\t\tudataCur = jQuery.extend( {}, udataOld );\n\n\t\tdataUser.set( dest, udataCur );\n\t}\n}\n\n// Fix IE bugs, see support tests\nfunction fixInput( src, dest ) {\n\tvar nodeName = dest.nodeName.toLowerCase();\n\n\t// Fails to persist the checked state of a cloned checkbox or radio button.\n\tif ( nodeName === \"input\" && rcheckableType.test( src.type ) ) {\n\t\tdest.checked = src.checked;\n\n\t// Fails to return the selected option to the default selected state when cloning options\n\t} else if ( nodeName === \"input\" || nodeName === \"textarea\" ) {\n\t\tdest.defaultValue = src.defaultValue;\n\t}\n}\n\nfunction domManip( collection, args, callback, ignored ) {\n\n\t// Flatten any nested arrays\n\targs = concat.apply( [], args );\n\n\tvar fragment, first, scripts, hasScripts, node, doc,\n\t\ti = 0,\n\t\tl = collection.length,\n\t\tiNoClone = l - 1,\n\t\tvalue = args[ 0 ],\n\t\tisFunction = jQuery.isFunction( value );\n\n\t// We can't cloneNode fragments that contain checked, in WebKit\n\tif ( isFunction ||\n\t\t\t( l > 1 && typeof value === \"string\" &&\n\t\t\t\t!support.checkClone && rchecked.test( value ) ) ) {\n\t\treturn collection.each( function( index ) {\n\t\t\tvar self = collection.eq( index );\n\t\t\tif ( isFunction ) {\n\t\t\t\targs[ 0 ] = value.call( this, index, self.html() );\n\t\t\t}\n\t\t\tdomManip( self, args, callback, ignored );\n\t\t} );\n\t}\n\n\tif ( l ) {\n\t\tfragment = buildFragment( args, collection[ 0 ].ownerDocument, false, collection, ignored );\n\t\tfirst = fragment.firstChild;\n\n\t\tif ( fragment.childNodes.length === 1 ) {\n\t\t\tfragment = first;\n\t\t}\n\n\t\t// Require either new content or an interest in ignored elements to invoke the callback\n\t\tif ( first || ignored ) {\n\t\t\tscripts = jQuery.map( getAll( fragment, \"script\" ), disableScript );\n\t\t\thasScripts = scripts.length;\n\n\t\t\t// Use the original fragment for the last item\n\t\t\t// instead of the first because it can end up\n\t\t\t// being emptied incorrectly in certain situations (#8070).\n\t\t\tfor ( ; i < l; i++ ) {\n\t\t\t\tnode = fragment;\n\n\t\t\t\tif ( i !== iNoClone ) {\n\t\t\t\t\tnode = jQuery.clone( node, true, true );\n\n\t\t\t\t\t// Keep references to cloned scripts for later restoration\n\t\t\t\t\tif ( hasScripts ) {\n\n\t\t\t\t\t\t// Support: Android <=4.0 only, PhantomJS 1 only\n\t\t\t\t\t\t// push.apply(_, arraylike) throws on ancient WebKit\n\t\t\t\t\t\tjQuery.merge( scripts, getAll( node, \"script\" ) );\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tcallback.call( collection[ i ], node, i );\n\t\t\t}\n\n\t\t\tif ( hasScripts ) {\n\t\t\t\tdoc = scripts[ scripts.length - 1 ].ownerDocument;\n\n\t\t\t\t// Reenable scripts\n\t\t\t\tjQuery.map( scripts, restoreScript );\n\n\t\t\t\t// Evaluate executable scripts on first document insertion\n\t\t\t\tfor ( i = 0; i < hasScripts; i++ ) {\n\t\t\t\t\tnode = scripts[ i ];\n\t\t\t\t\tif ( rscriptType.test( node.type || \"\" ) &&\n\t\t\t\t\t\t!dataPriv.access( node, \"globalEval\" ) &&\n\t\t\t\t\t\tjQuery.contains( doc, node ) ) {\n\n\t\t\t\t\t\tif ( node.src ) {\n\n\t\t\t\t\t\t\t// Optional AJAX dependency, but won't run scripts if not present\n\t\t\t\t\t\t\tif ( jQuery._evalUrl ) {\n\t\t\t\t\t\t\t\tjQuery._evalUrl( node.src );\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tDOMEval( node.textContent.replace( rcleanScript, \"\" ), doc );\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\treturn collection;\n}\n\nfunction remove( elem, selector, keepData ) {\n\tvar node,\n\t\tnodes = selector ? jQuery.filter( selector, elem ) : elem,\n\t\ti = 0;\n\n\tfor ( ; ( node = nodes[ i ] ) != null; i++ ) {\n\t\tif ( !keepData && node.nodeType === 1 ) {\n\t\t\tjQuery.cleanData( getAll( node ) );\n\t\t}\n\n\t\tif ( node.parentNode ) {\n\t\t\tif ( keepData && jQuery.contains( node.ownerDocument, node ) ) {\n\t\t\t\tsetGlobalEval( getAll( node, \"script\" ) );\n\t\t\t}\n\t\t\tnode.parentNode.removeChild( node );\n\t\t}\n\t}\n\n\treturn elem;\n}\n\njQuery.extend( {\n\thtmlPrefilter: function( html ) {\n\t\treturn html.replace( rxhtmlTag, \"<$1></$2>\" );\n\t},\n\n\tclone: function( elem, dataAndEvents, deepDataAndEvents ) {\n\t\tvar i, l, srcElements, destElements,\n\t\t\tclone = elem.cloneNode( true ),\n\t\t\tinPage = jQuery.contains( elem.ownerDocument, elem );\n\n\t\t// Fix IE cloning issues\n\t\tif ( !support.noCloneChecked && ( elem.nodeType === 1 || elem.nodeType === 11 ) &&\n\t\t\t\t!jQuery.isXMLDoc( elem ) ) {\n\n\t\t\t// We eschew Sizzle here for performance reasons: https://jsperf.com/getall-vs-sizzle/2\n\t\t\tdestElements = getAll( clone );\n\t\t\tsrcElements = getAll( elem );\n\n\t\t\tfor ( i = 0, l = srcElements.length; i < l; i++ ) {\n\t\t\t\tfixInput( srcElements[ i ], destElements[ i ] );\n\t\t\t}\n\t\t}\n\n\t\t// Copy the events from the original to the clone\n\t\tif ( dataAndEvents ) {\n\t\t\tif ( deepDataAndEvents ) {\n\t\t\t\tsrcElements = srcElements || getAll( elem );\n\t\t\t\tdestElements = destElements || getAll( clone );\n\n\t\t\t\tfor ( i = 0, l = srcElements.length; i < l; i++ ) {\n\t\t\t\t\tcloneCopyEvent( srcElements[ i ], destElements[ i ] );\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tcloneCopyEvent( elem, clone );\n\t\t\t}\n\t\t}\n\n\t\t// Preserve script evaluation history\n\t\tdestElements = getAll( clone, \"script\" );\n\t\tif ( destElements.length > 0 ) {\n\t\t\tsetGlobalEval( destElements, !inPage && getAll( elem, \"script\" ) );\n\t\t}\n\n\t\t// Return the cloned set\n\t\treturn clone;\n\t},\n\n\tcleanData: function( elems ) {\n\t\tvar data, elem, type,\n\t\t\tspecial = jQuery.event.special,\n\t\t\ti = 0;\n\n\t\tfor ( ; ( elem = elems[ i ] ) !== undefined; i++ ) {\n\t\t\tif ( acceptData( elem ) ) {\n\t\t\t\tif ( ( data = elem[ dataPriv.expando ] ) ) {\n\t\t\t\t\tif ( data.events ) {\n\t\t\t\t\t\tfor ( type in data.events ) {\n\t\t\t\t\t\t\tif ( special[ type ] ) {\n\t\t\t\t\t\t\t\tjQuery.event.remove( elem, type );\n\n\t\t\t\t\t\t\t// This is a shortcut to avoid jQuery.event.remove's overhead\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tjQuery.removeEvent( elem, type, data.handle );\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\t// Support: Chrome <=35 - 45+\n\t\t\t\t\t// Assign undefined instead of using delete, see Data#remove\n\t\t\t\t\telem[ dataPriv.expando ] = undefined;\n\t\t\t\t}\n\t\t\t\tif ( elem[ dataUser.expando ] ) {\n\n\t\t\t\t\t// Support: Chrome <=35 - 45+\n\t\t\t\t\t// Assign undefined instead of using delete, see Data#remove\n\t\t\t\t\telem[ dataUser.expando ] = undefined;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n} );\n\njQuery.fn.extend( {\n\tdetach: function( selector ) {\n\t\treturn remove( this, selector, true );\n\t},\n\n\tremove: function( selector ) {\n\t\treturn remove( this, selector );\n\t},\n\n\ttext: function( value ) {\n\t\treturn access( this, function( value ) {\n\t\t\treturn value === undefined ?\n\t\t\t\tjQuery.text( this ) :\n\t\t\t\tthis.empty().each( function() {\n\t\t\t\t\tif ( this.nodeType === 1 || this.nodeType === 11 || this.nodeType === 9 ) {\n\t\t\t\t\t\tthis.textContent = value;\n\t\t\t\t\t}\n\t\t\t\t} );\n\t\t}, null, value, arguments.length );\n\t},\n\n\tappend: function() {\n\t\treturn domManip( this, arguments, function( elem ) {\n\t\t\tif ( this.nodeType === 1 || this.nodeType === 11 || this.nodeType === 9 ) {\n\t\t\t\tvar target = manipulationTarget( this, elem );\n\t\t\t\ttarget.appendChild( elem );\n\t\t\t}\n\t\t} );\n\t},\n\n\tprepend: function() {\n\t\treturn domManip( this, arguments, function( elem ) {\n\t\t\tif ( this.nodeType === 1 || this.nodeType === 11 || this.nodeType === 9 ) {\n\t\t\t\tvar target = manipulationTarget( this, elem );\n\t\t\t\ttarget.insertBefore( elem, target.firstChild );\n\t\t\t}\n\t\t} );\n\t},\n\n\tbefore: function() {\n\t\treturn domManip( this, arguments, function( elem ) {\n\t\t\tif ( this.parentNode ) {\n\t\t\t\tthis.parentNode.insertBefore( elem, this );\n\t\t\t}\n\t\t} );\n\t},\n\n\tafter: function() {\n\t\treturn domManip( this, arguments, function( elem ) {\n\t\t\tif ( this.parentNode ) {\n\t\t\t\tthis.parentNode.insertBefore( elem, this.nextSibling );\n\t\t\t}\n\t\t} );\n\t},\n\n\tempty: function() {\n\t\tvar elem,\n\t\t\ti = 0;\n\n\t\tfor ( ; ( elem = this[ i ] ) != null; i++ ) {\n\t\t\tif ( elem.nodeType === 1 ) {\n\n\t\t\t\t// Prevent memory leaks\n\t\t\t\tjQuery.cleanData( getAll( elem, false ) );\n\n\t\t\t\t// Remove any remaining nodes\n\t\t\t\telem.textContent = \"\";\n\t\t\t}\n\t\t}\n\n\t\treturn this;\n\t},\n\n\tclone: function( dataAndEvents, deepDataAndEvents ) {\n\t\tdataAndEvents = dataAndEvents == null ? false : dataAndEvents;\n\t\tdeepDataAndEvents = deepDataAndEvents == null ? dataAndEvents : deepDataAndEvents;\n\n\t\treturn this.map( function() {\n\t\t\treturn jQuery.clone( this, dataAndEvents, deepDataAndEvents );\n\t\t} );\n\t},\n\n\thtml: function( value ) {\n\t\treturn access( this, function( value ) {\n\t\t\tvar elem = this[ 0 ] || {},\n\t\t\t\ti = 0,\n\t\t\t\tl = this.length;\n\n\t\t\tif ( value === undefined && elem.nodeType === 1 ) {\n\t\t\t\treturn elem.innerHTML;\n\t\t\t}\n\n\t\t\t// See if we can take a shortcut and just use innerHTML\n\t\t\tif ( typeof value === \"string\" && !rnoInnerhtml.test( value ) &&\n\t\t\t\t!wrapMap[ ( rtagName.exec( value ) || [ \"\", \"\" ] )[ 1 ].toLowerCase() ] ) {\n\n\t\t\t\tvalue = jQuery.htmlPrefilter( value );\n\n\t\t\t\ttry {\n\t\t\t\t\tfor ( ; i < l; i++ ) {\n\t\t\t\t\t\telem = this[ i ] || {};\n\n\t\t\t\t\t\t// Remove element nodes and prevent memory leaks\n\t\t\t\t\t\tif ( elem.nodeType === 1 ) {\n\t\t\t\t\t\t\tjQuery.cleanData( getAll( elem, false ) );\n\t\t\t\t\t\t\telem.innerHTML = value;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\telem = 0;\n\n\t\t\t\t// If using innerHTML throws an exception, use the fallback method\n\t\t\t\t} catch ( e ) {}\n\t\t\t}\n\n\t\t\tif ( elem ) {\n\t\t\t\tthis.empty().append( value );\n\t\t\t}\n\t\t}, null, value, arguments.length );\n\t},\n\n\treplaceWith: function() {\n\t\tvar ignored = [];\n\n\t\t// Make the changes, replacing each non-ignored context element with the new content\n\t\treturn domManip( this, arguments, function( elem ) {\n\t\t\tvar parent = this.parentNode;\n\n\t\t\tif ( jQuery.inArray( this, ignored ) < 0 ) {\n\t\t\t\tjQuery.cleanData( getAll( this ) );\n\t\t\t\tif ( parent ) {\n\t\t\t\t\tparent.replaceChild( elem, this );\n\t\t\t\t}\n\t\t\t}\n\n\t\t// Force callback invocation\n\t\t}, ignored );\n\t}\n} );\n\njQuery.each( {\n\tappendTo: \"append\",\n\tprependTo: \"prepend\",\n\tinsertBefore: \"before\",\n\tinsertAfter: \"after\",\n\treplaceAll: \"replaceWith\"\n}, function( name, original ) {\n\tjQuery.fn[ name ] = function( selector ) {\n\t\tvar elems,\n\t\t\tret = [],\n\t\t\tinsert = jQuery( selector ),\n\t\t\tlast = insert.length - 1,\n\t\t\ti = 0;\n\n\t\tfor ( ; i <= last; i++ ) {\n\t\t\telems = i === last ? this : this.clone( true );\n\t\t\tjQuery( insert[ i ] )[ original ]( elems );\n\n\t\t\t// Support: Android <=4.0 only, PhantomJS 1 only\n\t\t\t// .get() because push.apply(_, arraylike) throws on ancient WebKit\n\t\t\tpush.apply( ret, elems.get() );\n\t\t}\n\n\t\treturn this.pushStack( ret );\n\t};\n} );\nvar rmargin = ( /^margin/ );\n\nvar rnumnonpx = new RegExp( \"^(\" + pnum + \")(?!px)[a-z%]+$\", \"i\" );\n\nvar getStyles = function( elem ) {\n\n\t\t// Support: IE <=11 only, Firefox <=30 (#15098, #14150)\n\t\t// IE throws on elements created in popups\n\t\t// FF meanwhile throws on frame elements through \"defaultView.getComputedStyle\"\n\t\tvar view = elem.ownerDocument.defaultView;\n\n\t\tif ( !view || !view.opener ) {\n\t\t\tview = window;\n\t\t}\n\n\t\treturn view.getComputedStyle( elem );\n\t};\n\n\n\n( function() {\n\n\t// Executing both pixelPosition & boxSizingReliable tests require only one layout\n\t// so they're executed at the same time to save the second computation.\n\tfunction computeStyleTests() {\n\n\t\t// This is a singleton, we need to execute it only once\n\t\tif ( !div ) {\n\t\t\treturn;\n\t\t}\n\n\t\tdiv.style.cssText =\n\t\t\t\"box-sizing:border-box;\" +\n\t\t\t\"position:relative;display:block;\" +\n\t\t\t\"margin:auto;border:1px;padding:1px;\" +\n\t\t\t\"top:1%;width:50%\";\n\t\tdiv.innerHTML = \"\";\n\t\tdocumentElement.appendChild( container );\n\n\t\tvar divStyle = window.getComputedStyle( div );\n\t\tpixelPositionVal = divStyle.top !== \"1%\";\n\n\t\t// Support: Android 4.0 - 4.3 only, Firefox <=3 - 44\n\t\treliableMarginLeftVal = divStyle.marginLeft === \"2px\";\n\t\tboxSizingReliableVal = divStyle.width === \"4px\";\n\n\t\t// Support: Android 4.0 - 4.3 only\n\t\t// Some styles come back with percentage values, even though they shouldn't\n\t\tdiv.style.marginRight = \"50%\";\n\t\tpixelMarginRightVal = divStyle.marginRight === \"4px\";\n\n\t\tdocumentElement.removeChild( container );\n\n\t\t// Nullify the div so it wouldn't be stored in the memory and\n\t\t// it will also be a sign that checks already performed\n\t\tdiv = null;\n\t}\n\n\tvar pixelPositionVal, boxSizingReliableVal, pixelMarginRightVal, reliableMarginLeftVal,\n\t\tcontainer = document.createElement( \"div\" ),\n\t\tdiv = document.createElement( \"div\" );\n\n\t// Finish early in limited (non-browser) environments\n\tif ( !div.style ) {\n\t\treturn;\n\t}\n\n\t// Support: IE <=9 - 11 only\n\t// Style of cloned element affects source element cloned (#8908)\n\tdiv.style.backgroundClip = \"content-box\";\n\tdiv.cloneNode( true ).style.backgroundClip = \"\";\n\tsupport.clearCloneStyle = div.style.backgroundClip === \"content-box\";\n\n\tcontainer.style.cssText = \"border:0;width:8px;height:0;top:0;left:-9999px;\" +\n\t\t\"padding:0;margin-top:1px;position:absolute\";\n\tcontainer.appendChild( div );\n\n\tjQuery.extend( support, {\n\t\tpixelPosition: function() {\n\t\t\tcomputeStyleTests();\n\t\t\treturn pixelPositionVal;\n\t\t},\n\t\tboxSizingReliable: function() {\n\t\t\tcomputeStyleTests();\n\t\t\treturn boxSizingReliableVal;\n\t\t},\n\t\tpixelMarginRight: function() {\n\t\t\tcomputeStyleTests();\n\t\t\treturn pixelMarginRightVal;\n\t\t},\n\t\treliableMarginLeft: function() {\n\t\t\tcomputeStyleTests();\n\t\t\treturn reliableMarginLeftVal;\n\t\t}\n\t} );\n} )();\n\n\nfunction curCSS( elem, name, computed ) {\n\tvar width, minWidth, maxWidth, ret,\n\t\tstyle = elem.style;\n\n\tcomputed = computed || getStyles( elem );\n\n\t// Support: IE <=9 only\n\t// getPropertyValue is only needed for .css('filter') (#12537)\n\tif ( computed ) {\n\t\tret = computed.getPropertyValue( name ) || computed[ name ];\n\n\t\tif ( ret === \"\" && !jQuery.contains( elem.ownerDocument, elem ) ) {\n\t\t\tret = jQuery.style( elem, name );\n\t\t}\n\n\t\t// A tribute to the \"awesome hack by Dean Edwards\"\n\t\t// Android Browser returns percentage for some values,\n\t\t// but width seems to be reliably pixels.\n\t\t// This is against the CSSOM draft spec:\n\t\t// https://drafts.csswg.org/cssom/#resolved-values\n\t\tif ( !support.pixelMarginRight() && rnumnonpx.test( ret ) && rmargin.test( name ) ) {\n\n\t\t\t// Remember the original values\n\t\t\twidth = style.width;\n\t\t\tminWidth = style.minWidth;\n\t\t\tmaxWidth = style.maxWidth;\n\n\t\t\t// Put in the new values to get a computed value out\n\t\t\tstyle.minWidth = style.maxWidth = style.width = ret;\n\t\t\tret = computed.width;\n\n\t\t\t// Revert the changed values\n\t\t\tstyle.width = width;\n\t\t\tstyle.minWidth = minWidth;\n\t\t\tstyle.maxWidth = maxWidth;\n\t\t}\n\t}\n\n\treturn ret !== undefined ?\n\n\t\t// Support: IE <=9 - 11 only\n\t\t// IE returns zIndex value as an integer.\n\t\tret + \"\" :\n\t\tret;\n}\n\n\nfunction addGetHookIf( conditionFn, hookFn ) {\n\n\t// Define the hook, we'll check on the first run if it's really needed.\n\treturn {\n\t\tget: function() {\n\t\t\tif ( conditionFn() ) {\n\n\t\t\t\t// Hook not needed (or it's not possible to use it due\n\t\t\t\t// to missing dependency), remove it.\n\t\t\t\tdelete this.get;\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t// Hook needed; redefine it so that the support test is not executed again.\n\t\t\treturn ( this.get = hookFn ).apply( this, arguments );\n\t\t}\n\t};\n}\n\n\nvar\n\n\t// Swappable if display is none or starts with table\n\t// except \"table\", \"table-cell\", or \"table-caption\"\n\t// See here for display values: https://developer.mozilla.org/en-US/docs/CSS/display\n\trdisplayswap = /^(none|table(?!-c[ea]).+)/,\n\tcssShow = { position: \"absolute\", visibility: \"hidden\", display: \"block\" },\n\tcssNormalTransform = {\n\t\tletterSpacing: \"0\",\n\t\tfontWeight: \"400\"\n\t},\n\n\tcssPrefixes = [ \"Webkit\", \"Moz\", \"ms\" ],\n\temptyStyle = document.createElement( \"div\" ).style;\n\n// Return a css property mapped to a potentially vendor prefixed property\nfunction vendorPropName( name ) {\n\n\t// Shortcut for names that are not vendor prefixed\n\tif ( name in emptyStyle ) {\n\t\treturn name;\n\t}\n\n\t// Check for vendor prefixed names\n\tvar capName = name[ 0 ].toUpperCase() + name.slice( 1 ),\n\t\ti = cssPrefixes.length;\n\n\twhile ( i-- ) {\n\t\tname = cssPrefixes[ i ] + capName;\n\t\tif ( name in emptyStyle ) {\n\t\t\treturn name;\n\t\t}\n\t}\n}\n\nfunction setPositiveNumber( elem, value, subtract ) {\n\n\t// Any relative (+/-) values have already been\n\t// normalized at this point\n\tvar matches = rcssNum.exec( value );\n\treturn matches ?\n\n\t\t// Guard against undefined \"subtract\", e.g., when used as in cssHooks\n\t\tMath.max( 0, matches[ 2 ] - ( subtract || 0 ) ) + ( matches[ 3 ] || \"px\" ) :\n\t\tvalue;\n}\n\nfunction augmentWidthOrHeight( elem, name, extra, isBorderBox, styles ) {\n\tvar i,\n\t\tval = 0;\n\n\t// If we already have the right measurement, avoid augmentation\n\tif ( extra === ( isBorderBox ? \"border\" : \"content\" ) ) {\n\t\ti = 4;\n\n\t// Otherwise initialize for horizontal or vertical properties\n\t} else {\n\t\ti = name === \"width\" ? 1 : 0;\n\t}\n\n\tfor ( ; i < 4; i += 2 ) {\n\n\t\t// Both box models exclude margin, so add it if we want it\n\t\tif ( extra === \"margin\" ) {\n\t\t\tval += jQuery.css( elem, extra + cssExpand[ i ], true, styles );\n\t\t}\n\n\t\tif ( isBorderBox ) {\n\n\t\t\t// border-box includes padding, so remove it if we want content\n\t\t\tif ( extra === \"content\" ) {\n\t\t\t\tval -= jQuery.css( elem, \"padding\" + cssExpand[ i ], true, styles );\n\t\t\t}\n\n\t\t\t// At this point, extra isn't border nor margin, so remove border\n\t\t\tif ( extra !== \"margin\" ) {\n\t\t\t\tval -= jQuery.css( elem, \"border\" + cssExpand[ i ] + \"Width\", true, styles );\n\t\t\t}\n\t\t} else {\n\n\t\t\t// At this point, extra isn't content, so add padding\n\t\t\tval += jQuery.css( elem, \"padding\" + cssExpand[ i ], true, styles );\n\n\t\t\t// At this point, extra isn't content nor padding, so add border\n\t\t\tif ( extra !== \"padding\" ) {\n\t\t\t\tval += jQuery.css( elem, \"border\" + cssExpand[ i ] + \"Width\", true, styles );\n\t\t\t}\n\t\t}\n\t}\n\n\treturn val;\n}\n\nfunction getWidthOrHeight( elem, name, extra ) {\n\n\t// Start with offset property, which is equivalent to the border-box value\n\tvar val,\n\t\tvalueIsBorderBox = true,\n\t\tstyles = getStyles( elem ),\n\t\tisBorderBox = jQuery.css( elem, \"boxSizing\", false, styles ) === \"border-box\";\n\n\t// Support: IE <=11 only\n\t// Running getBoundingClientRect on a disconnected node\n\t// in IE throws an error.\n\tif ( elem.getClientRects().length ) {\n\t\tval = elem.getBoundingClientRect()[ name ];\n\t}\n\n\t// Some non-html elements return undefined for offsetWidth, so check for null/undefined\n\t// svg - https://bugzilla.mozilla.org/show_bug.cgi?id=649285\n\t// MathML - https://bugzilla.mozilla.org/show_bug.cgi?id=491668\n\tif ( val <= 0 || val == null ) {\n\n\t\t// Fall back to computed then uncomputed css if necessary\n\t\tval = curCSS( elem, name, styles );\n\t\tif ( val < 0 || val == null ) {\n\t\t\tval = elem.style[ name ];\n\t\t}\n\n\t\t// Computed unit is not pixels. Stop here and return.\n\t\tif ( rnumnonpx.test( val ) ) {\n\t\t\treturn val;\n\t\t}\n\n\t\t// Check for style in case a browser which returns unreliable values\n\t\t// for getComputedStyle silently falls back to the reliable elem.style\n\t\tvalueIsBorderBox = isBorderBox &&\n\t\t\t( support.boxSizingReliable() || val === elem.style[ name ] );\n\n\t\t// Normalize \"\", auto, and prepare for extra\n\t\tval = parseFloat( val ) || 0;\n\t}\n\n\t// Use the active box-sizing model to add/subtract irrelevant styles\n\treturn ( val +\n\t\taugmentWidthOrHeight(\n\t\t\telem,\n\t\t\tname,\n\t\t\textra || ( isBorderBox ? \"border\" : \"content\" ),\n\t\t\tvalueIsBorderBox,\n\t\t\tstyles\n\t\t)\n\t) + \"px\";\n}\n\njQuery.extend( {\n\n\t// Add in style property hooks for overriding the default\n\t// behavior of getting and setting a style property\n\tcssHooks: {\n\t\topacity: {\n\t\t\tget: function( elem, computed ) {\n\t\t\t\tif ( computed ) {\n\n\t\t\t\t\t// We should always get a number back from opacity\n\t\t\t\t\tvar ret = curCSS( elem, \"opacity\" );\n\t\t\t\t\treturn ret === \"\" ? \"1\" : ret;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t},\n\n\t// Don't automatically add \"px\" to these possibly-unitless properties\n\tcssNumber: {\n\t\t\"animationIterationCount\": true,\n\t\t\"columnCount\": true,\n\t\t\"fillOpacity\": true,\n\t\t\"flexGrow\": true,\n\t\t\"flexShrink\": true,\n\t\t\"fontWeight\": true,\n\t\t\"lineHeight\": true,\n\t\t\"opacity\": true,\n\t\t\"order\": true,\n\t\t\"orphans\": true,\n\t\t\"widows\": true,\n\t\t\"zIndex\": true,\n\t\t\"zoom\": true\n\t},\n\n\t// Add in properties whose names you wish to fix before\n\t// setting or getting the value\n\tcssProps: {\n\t\t\"float\": \"cssFloat\"\n\t},\n\n\t// Get and set the style property on a DOM Node\n\tstyle: function( elem, name, value, extra ) {\n\n\t\t// Don't set styles on text and comment nodes\n\t\tif ( !elem || elem.nodeType === 3 || elem.nodeType === 8 || !elem.style ) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Make sure that we're working with the right name\n\t\tvar ret, type, hooks,\n\t\t\torigName = jQuery.camelCase( name ),\n\t\t\tstyle = elem.style;\n\n\t\tname = jQuery.cssProps[ origName ] ||\n\t\t\t( jQuery.cssProps[ origName ] = vendorPropName( origName ) || origName );\n\n\t\t// Gets hook for the prefixed version, then unprefixed version\n\t\thooks = jQuery.cssHooks[ name ] || jQuery.cssHooks[ origName ];\n\n\t\t// Check if we're setting a value\n\t\tif ( value !== undefined ) {\n\t\t\ttype = typeof value;\n\n\t\t\t// Convert \"+=\" or \"-=\" to relative numbers (#7345)\n\t\t\tif ( type === \"string\" && ( ret = rcssNum.exec( value ) ) && ret[ 1 ] ) {\n\t\t\t\tvalue = adjustCSS( elem, name, ret );\n\n\t\t\t\t// Fixes bug #9237\n\t\t\t\ttype = \"number\";\n\t\t\t}\n\n\t\t\t// Make sure that null and NaN values aren't set (#7116)\n\t\t\tif ( value == null || value !== value ) {\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t// If a number was passed in, add the unit (except for certain CSS properties)\n\t\t\tif ( type === \"number\" ) {\n\t\t\t\tvalue += ret && ret[ 3 ] || ( jQuery.cssNumber[ origName ] ? \"\" : \"px\" );\n\t\t\t}\n\n\t\t\t// background-* props affect original clone's values\n\t\t\tif ( !support.clearCloneStyle && value === \"\" && name.indexOf( \"background\" ) === 0 ) {\n\t\t\t\tstyle[ name ] = \"inherit\";\n\t\t\t}\n\n\t\t\t// If a hook was provided, use that value, otherwise just set the specified value\n\t\t\tif ( !hooks || !( \"set\" in hooks ) ||\n\t\t\t\t( value = hooks.set( elem, value, extra ) ) !== undefined ) {\n\n\t\t\t\tstyle[ name ] = value;\n\t\t\t}\n\n\t\t} else {\n\n\t\t\t// If a hook was provided get the non-computed value from there\n\t\t\tif ( hooks && \"get\" in hooks &&\n\t\t\t\t( ret = hooks.get( elem, false, extra ) ) !== undefined ) {\n\n\t\t\t\treturn ret;\n\t\t\t}\n\n\t\t\t// Otherwise just get the value from the style object\n\t\t\treturn style[ name ];\n\t\t}\n\t},\n\n\tcss: function( elem, name, extra, styles ) {\n\t\tvar val, num, hooks,\n\t\t\torigName = jQuery.camelCase( name );\n\n\t\t// Make sure that we're working with the right name\n\t\tname = jQuery.cssProps[ origName ] ||\n\t\t\t( jQuery.cssProps[ origName ] = vendorPropName( origName ) || origName );\n\n\t\t// Try prefixed name followed by the unprefixed name\n\t\thooks = jQuery.cssHooks[ name ] || jQuery.cssHooks[ origName ];\n\n\t\t// If a hook was provided get the computed value from there\n\t\tif ( hooks && \"get\" in hooks ) {\n\t\t\tval = hooks.get( elem, true, extra );\n\t\t}\n\n\t\t// Otherwise, if a way to get the computed value exists, use that\n\t\tif ( val === undefined ) {\n\t\t\tval = curCSS( elem, name, styles );\n\t\t}\n\n\t\t// Convert \"normal\" to computed value\n\t\tif ( val === \"normal\" && name in cssNormalTransform ) {\n\t\t\tval = cssNormalTransform[ name ];\n\t\t}\n\n\t\t// Make numeric if forced or a qualifier was provided and val looks numeric\n\t\tif ( extra === \"\" || extra ) {\n\t\t\tnum = parseFloat( val );\n\t\t\treturn extra === true || isFinite( num ) ? num || 0 : val;\n\t\t}\n\t\treturn val;\n\t}\n} );\n\njQuery.each( [ \"height\", \"width\" ], function( i, name ) {\n\tjQuery.cssHooks[ name ] = {\n\t\tget: function( elem, computed, extra ) {\n\t\t\tif ( computed ) {\n\n\t\t\t\t// Certain elements can have dimension info if we invisibly show them\n\t\t\t\t// but it must have a current display style that would benefit\n\t\t\t\treturn rdisplayswap.test( jQuery.css( elem, \"display\" ) ) &&\n\n\t\t\t\t\t// Support: Safari 8+\n\t\t\t\t\t// Table columns in Safari have non-zero offsetWidth & zero\n\t\t\t\t\t// getBoundingClientRect().width unless display is changed.\n\t\t\t\t\t// Support: IE <=11 only\n\t\t\t\t\t// Running getBoundingClientRect on a disconnected node\n\t\t\t\t\t// in IE throws an error.\n\t\t\t\t\t( !elem.getClientRects().length || !elem.getBoundingClientRect().width ) ?\n\t\t\t\t\t\tswap( elem, cssShow, function() {\n\t\t\t\t\t\t\treturn getWidthOrHeight( elem, name, extra );\n\t\t\t\t\t\t} ) :\n\t\t\t\t\t\tgetWidthOrHeight( elem, name, extra );\n\t\t\t}\n\t\t},\n\n\t\tset: function( elem, value, extra ) {\n\t\t\tvar matches,\n\t\t\t\tstyles = extra && getStyles( elem ),\n\t\t\t\tsubtract = extra && augmentWidthOrHeight(\n\t\t\t\t\telem,\n\t\t\t\t\tname,\n\t\t\t\t\textra,\n\t\t\t\t\tjQuery.css( elem, \"boxSizing\", false, styles ) === \"border-box\",\n\t\t\t\t\tstyles\n\t\t\t\t);\n\n\t\t\t// Convert to pixels if value adjustment is needed\n\t\t\tif ( subtract && ( matches = rcssNum.exec( value ) ) &&\n\t\t\t\t( matches[ 3 ] || \"px\" ) !== \"px\" ) {\n\n\t\t\t\telem.style[ name ] = value;\n\t\t\t\tvalue = jQuery.css( elem, name );\n\t\t\t}\n\n\t\t\treturn setPositiveNumber( elem, value, subtract );\n\t\t}\n\t};\n} );\n\njQuery.cssHooks.marginLeft = addGetHookIf( support.reliableMarginLeft,\n\tfunction( elem, computed ) {\n\t\tif ( computed ) {\n\t\t\treturn ( parseFloat( curCSS( elem, \"marginLeft\" ) ) ||\n\t\t\t\telem.getBoundingClientRect().left -\n\t\t\t\t\tswap( elem, { marginLeft: 0 }, function() {\n\t\t\t\t\t\treturn elem.getBoundingClientRect().left;\n\t\t\t\t\t} )\n\t\t\t\t) + \"px\";\n\t\t}\n\t}\n);\n\n// These hooks are used by animate to expand properties\njQuery.each( {\n\tmargin: \"\",\n\tpadding: \"\",\n\tborder: \"Width\"\n}, function( prefix, suffix ) {\n\tjQuery.cssHooks[ prefix + suffix ] = {\n\t\texpand: function( value ) {\n\t\t\tvar i = 0,\n\t\t\t\texpanded = {},\n\n\t\t\t\t// Assumes a single number if not a string\n\t\t\t\tparts = typeof value === \"string\" ? value.split( \" \" ) : [ value ];\n\n\t\t\tfor ( ; i < 4; i++ ) {\n\t\t\t\texpanded[ prefix + cssExpand[ i ] + suffix ] =\n\t\t\t\t\tparts[ i ] || parts[ i - 2 ] || parts[ 0 ];\n\t\t\t}\n\n\t\t\treturn expanded;\n\t\t}\n\t};\n\n\tif ( !rmargin.test( prefix ) ) {\n\t\tjQuery.cssHooks[ prefix + suffix ].set = setPositiveNumber;\n\t}\n} );\n\njQuery.fn.extend( {\n\tcss: function( name, value ) {\n\t\treturn access( this, function( elem, name, value ) {\n\t\t\tvar styles, len,\n\t\t\t\tmap = {},\n\t\t\t\ti = 0;\n\n\t\t\tif ( jQuery.isArray( name ) ) {\n\t\t\t\tstyles = getStyles( elem );\n\t\t\t\tlen = name.length;\n\n\t\t\t\tfor ( ; i < len; i++ ) {\n\t\t\t\t\tmap[ name[ i ] ] = jQuery.css( elem, name[ i ], false, styles );\n\t\t\t\t}\n\n\t\t\t\treturn map;\n\t\t\t}\n\n\t\t\treturn value !== undefined ?\n\t\t\t\tjQuery.style( elem, name, value ) :\n\t\t\t\tjQuery.css( elem, name );\n\t\t}, name, value, arguments.length > 1 );\n\t}\n} );\n\n\nfunction Tween( elem, options, prop, end, easing ) {\n\treturn new Tween.prototype.init( elem, options, prop, end, easing );\n}\njQuery.Tween = Tween;\n\nTween.prototype = {\n\tconstructor: Tween,\n\tinit: function( elem, options, prop, end, easing, unit ) {\n\t\tthis.elem = elem;\n\t\tthis.prop = prop;\n\t\tthis.easing = easing || jQuery.easing._default;\n\t\tthis.options = options;\n\t\tthis.start = this.now = this.cur();\n\t\tthis.end = end;\n\t\tthis.unit = unit || ( jQuery.cssNumber[ prop ] ? \"\" : \"px\" );\n\t},\n\tcur: function() {\n\t\tvar hooks = Tween.propHooks[ this.prop ];\n\n\t\treturn hooks && hooks.get ?\n\t\t\thooks.get( this ) :\n\t\t\tTween.propHooks._default.get( this );\n\t},\n\trun: function( percent ) {\n\t\tvar eased,\n\t\t\thooks = Tween.propHooks[ this.prop ];\n\n\t\tif ( this.options.duration ) {\n\t\t\tthis.pos = eased = jQuery.easing[ this.easing ](\n\t\t\t\tpercent, this.options.duration * percent, 0, 1, this.options.duration\n\t\t\t);\n\t\t} else {\n\t\t\tthis.pos = eased = percent;\n\t\t}\n\t\tthis.now = ( this.end - this.start ) * eased + this.start;\n\n\t\tif ( this.options.step ) {\n\t\t\tthis.options.step.call( this.elem, this.now, this );\n\t\t}\n\n\t\tif ( hooks && hooks.set ) {\n\t\t\thooks.set( this );\n\t\t} else {\n\t\t\tTween.propHooks._default.set( this );\n\t\t}\n\t\treturn this;\n\t}\n};\n\nTween.prototype.init.prototype = Tween.prototype;\n\nTween.propHooks = {\n\t_default: {\n\t\tget: function( tween ) {\n\t\t\tvar result;\n\n\t\t\t// Use a property on the element directly when it is not a DOM element,\n\t\t\t// or when there is no matching style property that exists.\n\t\t\tif ( tween.elem.nodeType !== 1 ||\n\t\t\t\ttween.elem[ tween.prop ] != null && tween.elem.style[ tween.prop ] == null ) {\n\t\t\t\treturn tween.elem[ tween.prop ];\n\t\t\t}\n\n\t\t\t// Passing an empty string as a 3rd parameter to .css will automatically\n\t\t\t// attempt a parseFloat and fallback to a string if the parse fails.\n\t\t\t// Simple values such as \"10px\" are parsed to Float;\n\t\t\t// complex values such as \"rotate(1rad)\" are returned as-is.\n\t\t\tresult = jQuery.css( tween.elem, tween.prop, \"\" );\n\n\t\t\t// Empty strings, null, undefined and \"auto\" are converted to 0.\n\t\t\treturn !result || result === \"auto\" ? 0 : result;\n\t\t},\n\t\tset: function( tween ) {\n\n\t\t\t// Use step hook for back compat.\n\t\t\t// Use cssHook if its there.\n\t\t\t// Use .style if available and use plain properties where available.\n\t\t\tif ( jQuery.fx.step[ tween.prop ] ) {\n\t\t\t\tjQuery.fx.step[ tween.prop ]( tween );\n\t\t\t} else if ( tween.elem.nodeType === 1 &&\n\t\t\t\t( tween.elem.style[ jQuery.cssProps[ tween.prop ] ] != null ||\n\t\t\t\t\tjQuery.cssHooks[ tween.prop ] ) ) {\n\t\t\t\tjQuery.style( tween.elem, tween.prop, tween.now + tween.unit );\n\t\t\t} else {\n\t\t\t\ttween.elem[ tween.prop ] = tween.now;\n\t\t\t}\n\t\t}\n\t}\n};\n\n// Support: IE <=9 only\n// Panic based approach to setting things on disconnected nodes\nTween.propHooks.scrollTop = Tween.propHooks.scrollLeft = {\n\tset: function( tween ) {\n\t\tif ( tween.elem.nodeType && tween.elem.parentNode ) {\n\t\t\ttween.elem[ tween.prop ] = tween.now;\n\t\t}\n\t}\n};\n\njQuery.easing = {\n\tlinear: function( p ) {\n\t\treturn p;\n\t},\n\tswing: function( p ) {\n\t\treturn 0.5 - Math.cos( p * Math.PI ) / 2;\n\t},\n\t_default: \"swing\"\n};\n\njQuery.fx = Tween.prototype.init;\n\n// Back compat <1.8 extension point\njQuery.fx.step = {};\n\n\n\n\nvar\n\tfxNow, timerId,\n\trfxtypes = /^(?:toggle|show|hide)$/,\n\trrun = /queueHooks$/;\n\nfunction raf() {\n\tif ( timerId ) {\n\t\twindow.requestAnimationFrame( raf );\n\t\tjQuery.fx.tick();\n\t}\n}\n\n// Animations created synchronously will run synchronously\nfunction createFxNow() {\n\twindow.setTimeout( function() {\n\t\tfxNow = undefined;\n\t} );\n\treturn ( fxNow = jQuery.now() );\n}\n\n// Generate parameters to create a standard animation\nfunction genFx( type, includeWidth ) {\n\tvar which,\n\t\ti = 0,\n\t\tattrs = { height: type };\n\n\t// If we include width, step value is 1 to do all cssExpand values,\n\t// otherwise step value is 2 to skip over Left and Right\n\tincludeWidth = includeWidth ? 1 : 0;\n\tfor ( ; i < 4; i += 2 - includeWidth ) {\n\t\twhich = cssExpand[ i ];\n\t\tattrs[ \"margin\" + which ] = attrs[ \"padding\" + which ] = type;\n\t}\n\n\tif ( includeWidth ) {\n\t\tattrs.opacity = attrs.width = type;\n\t}\n\n\treturn attrs;\n}\n\nfunction createTween( value, prop, animation ) {\n\tvar tween,\n\t\tcollection = ( Animation.tweeners[ prop ] || [] ).concat( Animation.tweeners[ \"*\" ] ),\n\t\tindex = 0,\n\t\tlength = collection.length;\n\tfor ( ; index < length; index++ ) {\n\t\tif ( ( tween = collection[ index ].call( animation, prop, value ) ) ) {\n\n\t\t\t// We're done with this property\n\t\t\treturn tween;\n\t\t}\n\t}\n}\n\nfunction defaultPrefilter( elem, props, opts ) {\n\tvar prop, value, toggle, hooks, oldfire, propTween, restoreDisplay, display,\n\t\tisBox = \"width\" in props || \"height\" in props,\n\t\tanim = this,\n\t\torig = {},\n\t\tstyle = elem.style,\n\t\thidden = elem.nodeType && isHiddenWithinTree( elem ),\n\t\tdataShow = dataPriv.get( elem, \"fxshow\" );\n\n\t// Queue-skipping animations hijack the fx hooks\n\tif ( !opts.queue ) {\n\t\thooks = jQuery._queueHooks( elem, \"fx\" );\n\t\tif ( hooks.unqueued == null ) {\n\t\t\thooks.unqueued = 0;\n\t\t\toldfire = hooks.empty.fire;\n\t\t\thooks.empty.fire = function() {\n\t\t\t\tif ( !hooks.unqueued ) {\n\t\t\t\t\toldfire();\n\t\t\t\t}\n\t\t\t};\n\t\t}\n\t\thooks.unqueued++;\n\n\t\tanim.always( function() {\n\n\t\t\t// Ensure the complete handler is called before this completes\n\t\t\tanim.always( function() {\n\t\t\t\thooks.unqueued--;\n\t\t\t\tif ( !jQuery.queue( elem, \"fx\" ).length ) {\n\t\t\t\t\thooks.empty.fire();\n\t\t\t\t}\n\t\t\t} );\n\t\t} );\n\t}\n\n\t// Detect show/hide animations\n\tfor ( prop in props ) {\n\t\tvalue = props[ prop ];\n\t\tif ( rfxtypes.test( value ) ) {\n\t\t\tdelete props[ prop ];\n\t\t\ttoggle = toggle || value === \"toggle\";\n\t\t\tif ( value === ( hidden ? \"hide\" : \"show\" ) ) {\n\n\t\t\t\t// Pretend to be hidden if this is a \"show\" and\n\t\t\t\t// there is still data from a stopped show/hide\n\t\t\t\tif ( value === \"show\" && dataShow && dataShow[ prop ] !== undefined ) {\n\t\t\t\t\thidden = true;\n\n\t\t\t\t// Ignore all other no-op show/hide data\n\t\t\t\t} else {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t}\n\t\t\torig[ prop ] = dataShow && dataShow[ prop ] || jQuery.style( elem, prop );\n\t\t}\n\t}\n\n\t// Bail out if this is a no-op like .hide().hide()\n\tpropTween = !jQuery.isEmptyObject( props );\n\tif ( !propTween && jQuery.isEmptyObject( orig ) ) {\n\t\treturn;\n\t}\n\n\t// Restrict \"overflow\" and \"display\" styles during box animations\n\tif ( isBox && elem.nodeType === 1 ) {\n\n\t\t// Support: IE <=9 - 11, Edge 12 - 13\n\t\t// Record all 3 overflow attributes because IE does not infer the shorthand\n\t\t// from identically-valued overflowX and overflowY\n\t\topts.overflow = [ style.overflow, style.overflowX, style.overflowY ];\n\n\t\t// Identify a display type, preferring old show/hide data over the CSS cascade\n\t\trestoreDisplay = dataShow && dataShow.display;\n\t\tif ( restoreDisplay == null ) {\n\t\t\trestoreDisplay = dataPriv.get( elem, \"display\" );\n\t\t}\n\t\tdisplay = jQuery.css( elem, \"display\" );\n\t\tif ( display === \"none\" ) {\n\t\t\tif ( restoreDisplay ) {\n\t\t\t\tdisplay = restoreDisplay;\n\t\t\t} else {\n\n\t\t\t\t// Get nonempty value(s) by temporarily forcing visibility\n\t\t\t\tshowHide( [ elem ], true );\n\t\t\t\trestoreDisplay = elem.style.display || restoreDisplay;\n\t\t\t\tdisplay = jQuery.css( elem, \"display\" );\n\t\t\t\tshowHide( [ elem ] );\n\t\t\t}\n\t\t}\n\n\t\t// Animate inline elements as inline-block\n\t\tif ( display === \"inline\" || display === \"inline-block\" && restoreDisplay != null ) {\n\t\t\tif ( jQuery.css( elem, \"float\" ) === \"none\" ) {\n\n\t\t\t\t// Restore the original display value at the end of pure show/hide animations\n\t\t\t\tif ( !propTween ) {\n\t\t\t\t\tanim.done( function() {\n\t\t\t\t\t\tstyle.display = restoreDisplay;\n\t\t\t\t\t} );\n\t\t\t\t\tif ( restoreDisplay == null ) {\n\t\t\t\t\t\tdisplay = style.display;\n\t\t\t\t\t\trestoreDisplay = display === \"none\" ? \"\" : display;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tstyle.display = \"inline-block\";\n\t\t\t}\n\t\t}\n\t}\n\n\tif ( opts.overflow ) {\n\t\tstyle.overflow = \"hidden\";\n\t\tanim.always( function() {\n\t\t\tstyle.overflow = opts.overflow[ 0 ];\n\t\t\tstyle.overflowX = opts.overflow[ 1 ];\n\t\t\tstyle.overflowY = opts.overflow[ 2 ];\n\t\t} );\n\t}\n\n\t// Implement show/hide animations\n\tpropTween = false;\n\tfor ( prop in orig ) {\n\n\t\t// General show/hide setup for this element animation\n\t\tif ( !propTween ) {\n\t\t\tif ( dataShow ) {\n\t\t\t\tif ( \"hidden\" in dataShow ) {\n\t\t\t\t\thidden = dataShow.hidden;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tdataShow = dataPriv.access( elem, \"fxshow\", { display: restoreDisplay } );\n\t\t\t}\n\n\t\t\t// Store hidden/visible for toggle so `.stop().toggle()` \"reverses\"\n\t\t\tif ( toggle ) {\n\t\t\t\tdataShow.hidden = !hidden;\n\t\t\t}\n\n\t\t\t// Show elements before animating them\n\t\t\tif ( hidden ) {\n\t\t\t\tshowHide( [ elem ], true );\n\t\t\t}\n\n\t\t\t/* eslint-disable no-loop-func */\n\n\t\t\tanim.done( function() {\n\n\t\t\t/* eslint-enable no-loop-func */\n\n\t\t\t\t// The final step of a \"hide\" animation is actually hiding the element\n\t\t\t\tif ( !hidden ) {\n\t\t\t\t\tshowHide( [ elem ] );\n\t\t\t\t}\n\t\t\t\tdataPriv.remove( elem, \"fxshow\" );\n\t\t\t\tfor ( prop in orig ) {\n\t\t\t\t\tjQuery.style( elem, prop, orig[ prop ] );\n\t\t\t\t}\n\t\t\t} );\n\t\t}\n\n\t\t// Per-property setup\n\t\tpropTween = createTween( hidden ? dataShow[ prop ] : 0, prop, anim );\n\t\tif ( !( prop in dataShow ) ) {\n\t\t\tdataShow[ prop ] = propTween.start;\n\t\t\tif ( hidden ) {\n\t\t\t\tpropTween.end = propTween.start;\n\t\t\t\tpropTween.start = 0;\n\t\t\t}\n\t\t}\n\t}\n}\n\nfunction propFilter( props, specialEasing ) {\n\tvar index, name, easing, value, hooks;\n\n\t// camelCase, specialEasing and expand cssHook pass\n\tfor ( index in props ) {\n\t\tname = jQuery.camelCase( index );\n\t\teasing = specialEasing[ name ];\n\t\tvalue = props[ index ];\n\t\tif ( jQuery.isArray( value ) ) {\n\t\t\teasing = value[ 1 ];\n\t\t\tvalue = props[ index ] = value[ 0 ];\n\t\t}\n\n\t\tif ( index !== name ) {\n\t\t\tprops[ name ] = value;\n\t\t\tdelete props[ index ];\n\t\t}\n\n\t\thooks = jQuery.cssHooks[ name ];\n\t\tif ( hooks && \"expand\" in hooks ) {\n\t\t\tvalue = hooks.expand( value );\n\t\t\tdelete props[ name ];\n\n\t\t\t// Not quite $.extend, this won't overwrite existing keys.\n\t\t\t// Reusing 'index' because we have the correct \"name\"\n\t\t\tfor ( index in value ) {\n\t\t\t\tif ( !( index in props ) ) {\n\t\t\t\t\tprops[ index ] = value[ index ];\n\t\t\t\t\tspecialEasing[ index ] = easing;\n\t\t\t\t}\n\t\t\t}\n\t\t} else {\n\t\t\tspecialEasing[ name ] = easing;\n\t\t}\n\t}\n}\n\nfunction Animation( elem, properties, options ) {\n\tvar result,\n\t\tstopped,\n\t\tindex = 0,\n\t\tlength = Animation.prefilters.length,\n\t\tdeferred = jQuery.Deferred().always( function() {\n\n\t\t\t// Don't match elem in the :animated selector\n\t\t\tdelete tick.elem;\n\t\t} ),\n\t\ttick = function() {\n\t\t\tif ( stopped ) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tvar currentTime = fxNow || createFxNow(),\n\t\t\t\tremaining = Math.max( 0, animation.startTime + animation.duration - currentTime ),\n\n\t\t\t\t// Support: Android 2.3 only\n\t\t\t\t// Archaic crash bug won't allow us to use `1 - ( 0.5 || 0 )` (#12497)\n\t\t\t\ttemp = remaining / animation.duration || 0,\n\t\t\t\tpercent = 1 - temp,\n\t\t\t\tindex = 0,\n\t\t\t\tlength = animation.tweens.length;\n\n\t\t\tfor ( ; index < length; index++ ) {\n\t\t\t\tanimation.tweens[ index ].run( percent );\n\t\t\t}\n\n\t\t\tdeferred.notifyWith( elem, [ animation, percent, remaining ] );\n\n\t\t\tif ( percent < 1 && length ) {\n\t\t\t\treturn remaining;\n\t\t\t} else {\n\t\t\t\tdeferred.resolveWith( elem, [ animation ] );\n\t\t\t\treturn false;\n\t\t\t}\n\t\t},\n\t\tanimation = deferred.promise( {\n\t\t\telem: elem,\n\t\t\tprops: jQuery.extend( {}, properties ),\n\t\t\topts: jQuery.extend( true, {\n\t\t\t\tspecialEasing: {},\n\t\t\t\teasing: jQuery.easing._default\n\t\t\t}, options ),\n\t\t\toriginalProperties: properties,\n\t\t\toriginalOptions: options,\n\t\t\tstartTime: fxNow || createFxNow(),\n\t\t\tduration: options.duration,\n\t\t\ttweens: [],\n\t\t\tcreateTween: function( prop, end ) {\n\t\t\t\tvar tween = jQuery.Tween( elem, animation.opts, prop, end,\n\t\t\t\t\t\tanimation.opts.specialEasing[ prop ] || animation.opts.easing );\n\t\t\t\tanimation.tweens.push( tween );\n\t\t\t\treturn tween;\n\t\t\t},\n\t\t\tstop: function( gotoEnd ) {\n\t\t\t\tvar index = 0,\n\n\t\t\t\t\t// If we are going to the end, we want to run all the tweens\n\t\t\t\t\t// otherwise we skip this part\n\t\t\t\t\tlength = gotoEnd ? animation.tweens.length : 0;\n\t\t\t\tif ( stopped ) {\n\t\t\t\t\treturn this;\n\t\t\t\t}\n\t\t\t\tstopped = true;\n\t\t\t\tfor ( ; index < length; index++ ) {\n\t\t\t\t\tanimation.tweens[ index ].run( 1 );\n\t\t\t\t}\n\n\t\t\t\t// Resolve when we played the last frame; otherwise, reject\n\t\t\t\tif ( gotoEnd ) {\n\t\t\t\t\tdeferred.notifyWith( elem, [ animation, 1, 0 ] );\n\t\t\t\t\tdeferred.resolveWith( elem, [ animation, gotoEnd ] );\n\t\t\t\t} else {\n\t\t\t\t\tdeferred.rejectWith( elem, [ animation, gotoEnd ] );\n\t\t\t\t}\n\t\t\t\treturn this;\n\t\t\t}\n\t\t} ),\n\t\tprops = animation.props;\n\n\tpropFilter( props, animation.opts.specialEasing );\n\n\tfor ( ; index < length; index++ ) {\n\t\tresult = Animation.prefilters[ index ].call( animation, elem, props, animation.opts );\n\t\tif ( result ) {\n\t\t\tif ( jQuery.isFunction( result.stop ) ) {\n\t\t\t\tjQuery._queueHooks( animation.elem, animation.opts.queue ).stop =\n\t\t\t\t\tjQuery.proxy( result.stop, result );\n\t\t\t}\n\t\t\treturn result;\n\t\t}\n\t}\n\n\tjQuery.map( props, createTween, animation );\n\n\tif ( jQuery.isFunction( animation.opts.start ) ) {\n\t\tanimation.opts.start.call( elem, animation );\n\t}\n\n\tjQuery.fx.timer(\n\t\tjQuery.extend( tick, {\n\t\t\telem: elem,\n\t\t\tanim: animation,\n\t\t\tqueue: animation.opts.queue\n\t\t} )\n\t);\n\n\t// attach callbacks from options\n\treturn animation.progress( animation.opts.progress )\n\t\t.done( animation.opts.done, animation.opts.complete )\n\t\t.fail( animation.opts.fail )\n\t\t.always( animation.opts.always );\n}\n\njQuery.Animation = jQuery.extend( Animation, {\n\n\ttweeners: {\n\t\t\"*\": [ function( prop, value ) {\n\t\t\tvar tween = this.createTween( prop, value );\n\t\t\tadjustCSS( tween.elem, prop, rcssNum.exec( value ), tween );\n\t\t\treturn tween;\n\t\t} ]\n\t},\n\n\ttweener: function( props, callback ) {\n\t\tif ( jQuery.isFunction( props ) ) {\n\t\t\tcallback = props;\n\t\t\tprops = [ \"*\" ];\n\t\t} else {\n\t\t\tprops = props.match( rnothtmlwhite );\n\t\t}\n\n\t\tvar prop,\n\t\t\tindex = 0,\n\t\t\tlength = props.length;\n\n\t\tfor ( ; index < length; index++ ) {\n\t\t\tprop = props[ index ];\n\t\t\tAnimation.tweeners[ prop ] = Animation.tweeners[ prop ] || [];\n\t\t\tAnimation.tweeners[ prop ].unshift( callback );\n\t\t}\n\t},\n\n\tprefilters: [ defaultPrefilter ],\n\n\tprefilter: function( callback, prepend ) {\n\t\tif ( prepend ) {\n\t\t\tAnimation.prefilters.unshift( callback );\n\t\t} else {\n\t\t\tAnimation.prefilters.push( callback );\n\t\t}\n\t}\n} );\n\njQuery.speed = function( speed, easing, fn ) {\n\tvar opt = speed && typeof speed === \"object\" ? jQuery.extend( {}, speed ) : {\n\t\tcomplete: fn || !fn && easing ||\n\t\t\tjQuery.isFunction( speed ) && speed,\n\t\tduration: speed,\n\t\teasing: fn && easing || easing && !jQuery.isFunction( easing ) && easing\n\t};\n\n\t// Go to the end state if fx are off or if document is hidden\n\tif ( jQuery.fx.off || document.hidden ) {\n\t\topt.duration = 0;\n\n\t} else {\n\t\tif ( typeof opt.duration !== \"number\" ) {\n\t\t\tif ( opt.duration in jQuery.fx.speeds ) {\n\t\t\t\topt.duration = jQuery.fx.speeds[ opt.duration ];\n\n\t\t\t} else {\n\t\t\t\topt.duration = jQuery.fx.speeds._default;\n\t\t\t}\n\t\t}\n\t}\n\n\t// Normalize opt.queue - true/undefined/null -> \"fx\"\n\tif ( opt.queue == null || opt.queue === true ) {\n\t\topt.queue = \"fx\";\n\t}\n\n\t// Queueing\n\topt.old = opt.complete;\n\n\topt.complete = function() {\n\t\tif ( jQuery.isFunction( opt.old ) ) {\n\t\t\topt.old.call( this );\n\t\t}\n\n\t\tif ( opt.queue ) {\n\t\t\tjQuery.dequeue( this, opt.queue );\n\t\t}\n\t};\n\n\treturn opt;\n};\n\njQuery.fn.extend( {\n\tfadeTo: function( speed, to, easing, callback ) {\n\n\t\t// Show any hidden elements after setting opacity to 0\n\t\treturn this.filter( isHiddenWithinTree ).css( \"opacity\", 0 ).show()\n\n\t\t\t// Animate to the value specified\n\t\t\t.end().animate( { opacity: to }, speed, easing, callback );\n\t},\n\tanimate: function( prop, speed, easing, callback ) {\n\t\tvar empty = jQuery.isEmptyObject( prop ),\n\t\t\toptall = jQuery.speed( speed, easing, callback ),\n\t\t\tdoAnimation = function() {\n\n\t\t\t\t// Operate on a copy of prop so per-property easing won't be lost\n\t\t\t\tvar anim = Animation( this, jQuery.extend( {}, prop ), optall );\n\n\t\t\t\t// Empty animations, or finishing resolves immediately\n\t\t\t\tif ( empty || dataPriv.get( this, \"finish\" ) ) {\n\t\t\t\t\tanim.stop( true );\n\t\t\t\t}\n\t\t\t};\n\t\t\tdoAnimation.finish = doAnimation;\n\n\t\treturn empty || optall.queue === false ?\n\t\t\tthis.each( doAnimation ) :\n\t\t\tthis.queue( optall.queue, doAnimation );\n\t},\n\tstop: function( type, clearQueue, gotoEnd ) {\n\t\tvar stopQueue = function( hooks ) {\n\t\t\tvar stop = hooks.stop;\n\t\t\tdelete hooks.stop;\n\t\t\tstop( gotoEnd );\n\t\t};\n\n\t\tif ( typeof type !== \"string\" ) {\n\t\t\tgotoEnd = clearQueue;\n\t\t\tclearQueue = type;\n\t\t\ttype = undefined;\n\t\t}\n\t\tif ( clearQueue && type !== false ) {\n\t\t\tthis.queue( type || \"fx\", [] );\n\t\t}\n\n\t\treturn this.each( function() {\n\t\t\tvar dequeue = true,\n\t\t\t\tindex = type != null && type + \"queueHooks\",\n\t\t\t\ttimers = jQuery.timers,\n\t\t\t\tdata = dataPriv.get( this );\n\n\t\t\tif ( index ) {\n\t\t\t\tif ( data[ index ] && data[ index ].stop ) {\n\t\t\t\t\tstopQueue( data[ index ] );\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tfor ( index in data ) {\n\t\t\t\t\tif ( data[ index ] && data[ index ].stop && rrun.test( index ) ) {\n\t\t\t\t\t\tstopQueue( data[ index ] );\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tfor ( index = timers.length; index--; ) {\n\t\t\t\tif ( timers[ index ].elem === this &&\n\t\t\t\t\t( type == null || timers[ index ].queue === type ) ) {\n\n\t\t\t\t\ttimers[ index ].anim.stop( gotoEnd );\n\t\t\t\t\tdequeue = false;\n\t\t\t\t\ttimers.splice( index, 1 );\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Start the next in the queue if the last step wasn't forced.\n\t\t\t// Timers currently will call their complete callbacks, which\n\t\t\t// will dequeue but only if they were gotoEnd.\n\t\t\tif ( dequeue || !gotoEnd ) {\n\t\t\t\tjQuery.dequeue( this, type );\n\t\t\t}\n\t\t} );\n\t},\n\tfinish: function( type ) {\n\t\tif ( type !== false ) {\n\t\t\ttype = type || \"fx\";\n\t\t}\n\t\treturn this.each( function() {\n\t\t\tvar index,\n\t\t\t\tdata = dataPriv.get( this ),\n\t\t\t\tqueue = data[ type + \"queue\" ],\n\t\t\t\thooks = data[ type + \"queueHooks\" ],\n\t\t\t\ttimers = jQuery.timers,\n\t\t\t\tlength = queue ? queue.length : 0;\n\n\t\t\t// Enable finishing flag on private data\n\t\t\tdata.finish = true;\n\n\t\t\t// Empty the queue first\n\t\t\tjQuery.queue( this, type, [] );\n\n\t\t\tif ( hooks && hooks.stop ) {\n\t\t\t\thooks.stop.call( this, true );\n\t\t\t}\n\n\t\t\t// Look for any active animations, and finish them\n\t\t\tfor ( index = timers.length; index--; ) {\n\t\t\t\tif ( timers[ index ].elem === this && timers[ index ].queue === type ) {\n\t\t\t\t\ttimers[ index ].anim.stop( true );\n\t\t\t\t\ttimers.splice( index, 1 );\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Look for any animations in the old queue and finish them\n\t\t\tfor ( index = 0; index < length; index++ ) {\n\t\t\t\tif ( queue[ index ] && queue[ index ].finish ) {\n\t\t\t\t\tqueue[ index ].finish.call( this );\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Turn off finishing flag\n\t\t\tdelete data.finish;\n\t\t} );\n\t}\n} );\n\njQuery.each( [ \"toggle\", \"show\", \"hide\" ], function( i, name ) {\n\tvar cssFn = jQuery.fn[ name ];\n\tjQuery.fn[ name ] = function( speed, easing, callback ) {\n\t\treturn speed == null || typeof speed === \"boolean\" ?\n\t\t\tcssFn.apply( this, arguments ) :\n\t\t\tthis.animate( genFx( name, true ), speed, easing, callback );\n\t};\n} );\n\n// Generate shortcuts for custom animations\njQuery.each( {\n\tslideDown: genFx( \"show\" ),\n\tslideUp: genFx( \"hide\" ),\n\tslideToggle: genFx( \"toggle\" ),\n\tfadeIn: { opacity: \"show\" },\n\tfadeOut: { opacity: \"hide\" },\n\tfadeToggle: { opacity: \"toggle\" }\n}, function( name, props ) {\n\tjQuery.fn[ name ] = function( speed, easing, callback ) {\n\t\treturn this.animate( props, speed, easing, callback );\n\t};\n} );\n\njQuery.timers = [];\njQuery.fx.tick = function() {\n\tvar timer,\n\t\ti = 0,\n\t\ttimers = jQuery.timers;\n\n\tfxNow = jQuery.now();\n\n\tfor ( ; i < timers.length; i++ ) {\n\t\ttimer = timers[ i ];\n\n\t\t// Checks the timer has not already been removed\n\t\tif ( !timer() && timers[ i ] === timer ) {\n\t\t\ttimers.splice( i--, 1 );\n\t\t}\n\t}\n\n\tif ( !timers.length ) {\n\t\tjQuery.fx.stop();\n\t}\n\tfxNow = undefined;\n};\n\njQuery.fx.timer = function( timer ) {\n\tjQuery.timers.push( timer );\n\tif ( timer() ) {\n\t\tjQuery.fx.start();\n\t} else {\n\t\tjQuery.timers.pop();\n\t}\n};\n\njQuery.fx.interval = 13;\njQuery.fx.start = function() {\n\tif ( !timerId ) {\n\t\ttimerId = window.requestAnimationFrame ?\n\t\t\twindow.requestAnimationFrame( raf ) :\n\t\t\twindow.setInterval( jQuery.fx.tick, jQuery.fx.interval );\n\t}\n};\n\njQuery.fx.stop = function() {\n\tif ( window.cancelAnimationFrame ) {\n\t\twindow.cancelAnimationFrame( timerId );\n\t} else {\n\t\twindow.clearInterval( timerId );\n\t}\n\n\ttimerId = null;\n};\n\njQuery.fx.speeds = {\n\tslow: 600,\n\tfast: 200,\n\n\t// Default speed\n\t_default: 400\n};\n\n\n// Based off of the plugin by Clint Helfers, with permission.\n// https://web.archive.org/web/20100324014747/http://blindsignals.com/index.php/2009/07/jquery-delay/\njQuery.fn.delay = function( time, type ) {\n\ttime = jQuery.fx ? jQuery.fx.speeds[ time ] || time : time;\n\ttype = type || \"fx\";\n\n\treturn this.queue( type, function( next, hooks ) {\n\t\tvar timeout = window.setTimeout( next, time );\n\t\thooks.stop = function() {\n\t\t\twindow.clearTimeout( timeout );\n\t\t};\n\t} );\n};\n\n\n( function() {\n\tvar input = document.createElement( \"input\" ),\n\t\tselect = document.createElement( \"select\" ),\n\t\topt = select.appendChild( document.createElement( \"option\" ) );\n\n\tinput.type = \"checkbox\";\n\n\t// Support: Android <=4.3 only\n\t// Default value for a checkbox should be \"on\"\n\tsupport.checkOn = input.value !== \"\";\n\n\t// Support: IE <=11 only\n\t// Must access selectedIndex to make default options select\n\tsupport.optSelected = opt.selected;\n\n\t// Support: IE <=11 only\n\t// An input loses its value after becoming a radio\n\tinput = document.createElement( \"input\" );\n\tinput.value = \"t\";\n\tinput.type = \"radio\";\n\tsupport.radioValue = input.value === \"t\";\n} )();\n\n\nvar boolHook,\n\tattrHandle = jQuery.expr.attrHandle;\n\njQuery.fn.extend( {\n\tattr: function( name, value ) {\n\t\treturn access( this, jQuery.attr, name, value, arguments.length > 1 );\n\t},\n\n\tremoveAttr: function( name ) {\n\t\treturn this.each( function() {\n\t\t\tjQuery.removeAttr( this, name );\n\t\t} );\n\t}\n} );\n\njQuery.extend( {\n\tattr: function( elem, name, value ) {\n\t\tvar ret, hooks,\n\t\t\tnType = elem.nodeType;\n\n\t\t// Don't get/set attributes on text, comment and attribute nodes\n\t\tif ( nType === 3 || nType === 8 || nType === 2 ) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Fallback to prop when attributes are not supported\n\t\tif ( typeof elem.getAttribute === \"undefined\" ) {\n\t\t\treturn jQuery.prop( elem, name, value );\n\t\t}\n\n\t\t// Attribute hooks are determined by the lowercase version\n\t\t// Grab necessary hook if one is defined\n\t\tif ( nType !== 1 || !jQuery.isXMLDoc( elem ) ) {\n\t\t\thooks = jQuery.attrHooks[ name.toLowerCase() ] ||\n\t\t\t\t( jQuery.expr.match.bool.test( name ) ? boolHook : undefined );\n\t\t}\n\n\t\tif ( value !== undefined ) {\n\t\t\tif ( value === null ) {\n\t\t\t\tjQuery.removeAttr( elem, name );\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tif ( hooks && \"set\" in hooks &&\n\t\t\t\t( ret = hooks.set( elem, value, name ) ) !== undefined ) {\n\t\t\t\treturn ret;\n\t\t\t}\n\n\t\t\telem.setAttribute( name, value + \"\" );\n\t\t\treturn value;\n\t\t}\n\n\t\tif ( hooks && \"get\" in hooks && ( ret = hooks.get( elem, name ) ) !== null ) {\n\t\t\treturn ret;\n\t\t}\n\n\t\tret = jQuery.find.attr( elem, name );\n\n\t\t// Non-existent attributes return null, we normalize to undefined\n\t\treturn ret == null ? undefined : ret;\n\t},\n\n\tattrHooks: {\n\t\ttype: {\n\t\t\tset: function( elem, value ) {\n\t\t\t\tif ( !support.radioValue && value === \"radio\" &&\n\t\t\t\t\tjQuery.nodeName( elem, \"input\" ) ) {\n\t\t\t\t\tvar val = elem.value;\n\t\t\t\t\telem.setAttribute( \"type\", value );\n\t\t\t\t\tif ( val ) {\n\t\t\t\t\t\telem.value = val;\n\t\t\t\t\t}\n\t\t\t\t\treturn value;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t},\n\n\tremoveAttr: function( elem, value ) {\n\t\tvar name,\n\t\t\ti = 0,\n\n\t\t\t// Attribute names can contain non-HTML whitespace characters\n\t\t\t// https://html.spec.whatwg.org/multipage/syntax.html#attributes-2\n\t\t\tattrNames = value && value.match( rnothtmlwhite );\n\n\t\tif ( attrNames && elem.nodeType === 1 ) {\n\t\t\twhile ( ( name = attrNames[ i++ ] ) ) {\n\t\t\t\telem.removeAttribute( name );\n\t\t\t}\n\t\t}\n\t}\n} );\n\n// Hooks for boolean attributes\nboolHook = {\n\tset: function( elem, value, name ) {\n\t\tif ( value === false ) {\n\n\t\t\t// Remove boolean attributes when set to false\n\t\t\tjQuery.removeAttr( elem, name );\n\t\t} else {\n\t\t\telem.setAttribute( name, name );\n\t\t}\n\t\treturn name;\n\t}\n};\n\njQuery.each( jQuery.expr.match.bool.source.match( /\\w+/g ), function( i, name ) {\n\tvar getter = attrHandle[ name ] || jQuery.find.attr;\n\n\tattrHandle[ name ] = function( elem, name, isXML ) {\n\t\tvar ret, handle,\n\t\t\tlowercaseName = name.toLowerCase();\n\n\t\tif ( !isXML ) {\n\n\t\t\t// Avoid an infinite loop by temporarily removing this function from the getter\n\t\t\thandle = attrHandle[ lowercaseName ];\n\t\t\tattrHandle[ lowercaseName ] = ret;\n\t\t\tret = getter( elem, name, isXML ) != null ?\n\t\t\t\tlowercaseName :\n\t\t\t\tnull;\n\t\t\tattrHandle[ lowercaseName ] = handle;\n\t\t}\n\t\treturn ret;\n\t};\n} );\n\n\n\n\nvar rfocusable = /^(?:input|select|textarea|button)$/i,\n\trclickable = /^(?:a|area)$/i;\n\njQuery.fn.extend( {\n\tprop: function( name, value ) {\n\t\treturn access( this, jQuery.prop, name, value, arguments.length > 1 );\n\t},\n\n\tremoveProp: function( name ) {\n\t\treturn this.each( function() {\n\t\t\tdelete this[ jQuery.propFix[ name ] || name ];\n\t\t} );\n\t}\n} );\n\njQuery.extend( {\n\tprop: function( elem, name, value ) {\n\t\tvar ret, hooks,\n\t\t\tnType = elem.nodeType;\n\n\t\t// Don't get/set properties on text, comment and attribute nodes\n\t\tif ( nType === 3 || nType === 8 || nType === 2 ) {\n\t\t\treturn;\n\t\t}\n\n\t\tif ( nType !== 1 || !jQuery.isXMLDoc( elem ) ) {\n\n\t\t\t// Fix name and attach hooks\n\t\t\tname = jQuery.propFix[ name ] || name;\n\t\t\thooks = jQuery.propHooks[ name ];\n\t\t}\n\n\t\tif ( value !== undefined ) {\n\t\t\tif ( hooks && \"set\" in hooks &&\n\t\t\t\t( ret = hooks.set( elem, value, name ) ) !== undefined ) {\n\t\t\t\treturn ret;\n\t\t\t}\n\n\t\t\treturn ( elem[ name ] = value );\n\t\t}\n\n\t\tif ( hooks && \"get\" in hooks && ( ret = hooks.get( elem, name ) ) !== null ) {\n\t\t\treturn ret;\n\t\t}\n\n\t\treturn elem[ name ];\n\t},\n\n\tpropHooks: {\n\t\ttabIndex: {\n\t\t\tget: function( elem ) {\n\n\t\t\t\t// Support: IE <=9 - 11 only\n\t\t\t\t// elem.tabIndex doesn't always return the\n\t\t\t\t// correct value when it hasn't been explicitly set\n\t\t\t\t// https://web.archive.org/web/20141116233347/http://fluidproject.org/blog/2008/01/09/getting-setting-and-removing-tabindex-values-with-javascript/\n\t\t\t\t// Use proper attribute retrieval(#12072)\n\t\t\t\tvar tabindex = jQuery.find.attr( elem, \"tabindex\" );\n\n\t\t\t\tif ( tabindex ) {\n\t\t\t\t\treturn parseInt( tabindex, 10 );\n\t\t\t\t}\n\n\t\t\t\tif (\n\t\t\t\t\trfocusable.test( elem.nodeName ) ||\n\t\t\t\t\trclickable.test( elem.nodeName ) &&\n\t\t\t\t\telem.href\n\t\t\t\t) {\n\t\t\t\t\treturn 0;\n\t\t\t\t}\n\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\t},\n\n\tpropFix: {\n\t\t\"for\": \"htmlFor\",\n\t\t\"class\": \"className\"\n\t}\n} );\n\n// Support: IE <=11 only\n// Accessing the selectedIndex property\n// forces the browser to respect setting selected\n// on the option\n// The getter ensures a default option is selected\n// when in an optgroup\n// eslint rule \"no-unused-expressions\" is disabled for this code\n// since it considers such accessions noop\nif ( !support.optSelected ) {\n\tjQuery.propHooks.selected = {\n\t\tget: function( elem ) {\n\n\t\t\t/* eslint no-unused-expressions: \"off\" */\n\n\t\t\tvar parent = elem.parentNode;\n\t\t\tif ( parent && parent.parentNode ) {\n\t\t\t\tparent.parentNode.selectedIndex;\n\t\t\t}\n\t\t\treturn null;\n\t\t},\n\t\tset: function( elem ) {\n\n\t\t\t/* eslint no-unused-expressions: \"off\" */\n\n\t\t\tvar parent = elem.parentNode;\n\t\t\tif ( parent ) {\n\t\t\t\tparent.selectedIndex;\n\n\t\t\t\tif ( parent.parentNode ) {\n\t\t\t\t\tparent.parentNode.selectedIndex;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t};\n}\n\njQuery.each( [\n\t\"tabIndex\",\n\t\"readOnly\",\n\t\"maxLength\",\n\t\"cellSpacing\",\n\t\"cellPadding\",\n\t\"rowSpan\",\n\t\"colSpan\",\n\t\"useMap\",\n\t\"frameBorder\",\n\t\"contentEditable\"\n], function() {\n\tjQuery.propFix[ this.toLowerCase() ] = this;\n} );\n\n\n\n\n\t// Strip and collapse whitespace according to HTML spec\n\t// https://html.spec.whatwg.org/multipage/infrastructure.html#strip-and-collapse-whitespace\n\tfunction stripAndCollapse( value ) {\n\t\tvar tokens = value.match( rnothtmlwhite ) || [];\n\t\treturn tokens.join( \" \" );\n\t}\n\n\nfunction getClass( elem ) {\n\treturn elem.getAttribute && elem.getAttribute( \"class\" ) || \"\";\n}\n\njQuery.fn.extend( {\n\taddClass: function( value ) {\n\t\tvar classes, elem, cur, curValue, clazz, j, finalValue,\n\t\t\ti = 0;\n\n\t\tif ( jQuery.isFunction( value ) ) {\n\t\t\treturn this.each( function( j ) {\n\t\t\t\tjQuery( this ).addClass( value.call( this, j, getClass( this ) ) );\n\t\t\t} );\n\t\t}\n\n\t\tif ( typeof value === \"string\" && value ) {\n\t\t\tclasses = value.match( rnothtmlwhite ) || [];\n\n\t\t\twhile ( ( elem = this[ i++ ] ) ) {\n\t\t\t\tcurValue = getClass( elem );\n\t\t\t\tcur = elem.nodeType === 1 && ( \" \" + stripAndCollapse( curValue ) + \" \" );\n\n\t\t\t\tif ( cur ) {\n\t\t\t\t\tj = 0;\n\t\t\t\t\twhile ( ( clazz = classes[ j++ ] ) ) {\n\t\t\t\t\t\tif ( cur.indexOf( \" \" + clazz + \" \" ) < 0 ) {\n\t\t\t\t\t\t\tcur += clazz + \" \";\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\t// Only assign if different to avoid unneeded rendering.\n\t\t\t\t\tfinalValue = stripAndCollapse( cur );\n\t\t\t\t\tif ( curValue !== finalValue ) {\n\t\t\t\t\t\telem.setAttribute( \"class\", finalValue );\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn this;\n\t},\n\n\tremoveClass: function( value ) {\n\t\tvar classes, elem, cur, curValue, clazz, j, finalValue,\n\t\t\ti = 0;\n\n\t\tif ( jQuery.isFunction( value ) ) {\n\t\t\treturn this.each( function( j ) {\n\t\t\t\tjQuery( this ).removeClass( value.call( this, j, getClass( this ) ) );\n\t\t\t} );\n\t\t}\n\n\t\tif ( !arguments.length ) {\n\t\t\treturn this.attr( \"class\", \"\" );\n\t\t}\n\n\t\tif ( typeof value === \"string\" && value ) {\n\t\t\tclasses = value.match( rnothtmlwhite ) || [];\n\n\t\t\twhile ( ( elem = this[ i++ ] ) ) {\n\t\t\t\tcurValue = getClass( elem );\n\n\t\t\t\t// This expression is here for better compressibility (see addClass)\n\t\t\t\tcur = elem.nodeType === 1 && ( \" \" + stripAndCollapse( curValue ) + \" \" );\n\n\t\t\t\tif ( cur ) {\n\t\t\t\t\tj = 0;\n\t\t\t\t\twhile ( ( clazz = classes[ j++ ] ) ) {\n\n\t\t\t\t\t\t// Remove *all* instances\n\t\t\t\t\t\twhile ( cur.indexOf( \" \" + clazz + \" \" ) > -1 ) {\n\t\t\t\t\t\t\tcur = cur.replace( \" \" + clazz + \" \", \" \" );\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\t// Only assign if different to avoid unneeded rendering.\n\t\t\t\t\tfinalValue = stripAndCollapse( cur );\n\t\t\t\t\tif ( curValue !== finalValue ) {\n\t\t\t\t\t\telem.setAttribute( \"class\", finalValue );\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn this;\n\t},\n\n\ttoggleClass: function( value, stateVal ) {\n\t\tvar type = typeof value;\n\n\t\tif ( typeof stateVal === \"boolean\" && type === \"string\" ) {\n\t\t\treturn stateVal ? this.addClass( value ) : this.removeClass( value );\n\t\t}\n\n\t\tif ( jQuery.isFunction( value ) ) {\n\t\t\treturn this.each( function( i ) {\n\t\t\t\tjQuery( this ).toggleClass(\n\t\t\t\t\tvalue.call( this, i, getClass( this ), stateVal ),\n\t\t\t\t\tstateVal\n\t\t\t\t);\n\t\t\t} );\n\t\t}\n\n\t\treturn this.each( function() {\n\t\t\tvar className, i, self, classNames;\n\n\t\t\tif ( type === \"string\" ) {\n\n\t\t\t\t// Toggle individual class names\n\t\t\t\ti = 0;\n\t\t\t\tself = jQuery( this );\n\t\t\t\tclassNames = value.match( rnothtmlwhite ) || [];\n\n\t\t\t\twhile ( ( className = classNames[ i++ ] ) ) {\n\n\t\t\t\t\t// Check each className given, space separated list\n\t\t\t\t\tif ( self.hasClass( className ) ) {\n\t\t\t\t\t\tself.removeClass( className );\n\t\t\t\t\t} else {\n\t\t\t\t\t\tself.addClass( className );\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t// Toggle whole class name\n\t\t\t} else if ( value === undefined || type === \"boolean\" ) {\n\t\t\t\tclassName = getClass( this );\n\t\t\t\tif ( className ) {\n\n\t\t\t\t\t// Store className if set\n\t\t\t\t\tdataPriv.set( this, \"__className__\", className );\n\t\t\t\t}\n\n\t\t\t\t// If the element has a class name or if we're passed `false`,\n\t\t\t\t// then remove the whole classname (if there was one, the above saved it).\n\t\t\t\t// Otherwise bring back whatever was previously saved (if anything),\n\t\t\t\t// falling back to the empty string if nothing was stored.\n\t\t\t\tif ( this.setAttribute ) {\n\t\t\t\t\tthis.setAttribute( \"class\",\n\t\t\t\t\t\tclassName || value === false ?\n\t\t\t\t\t\t\"\" :\n\t\t\t\t\t\tdataPriv.get( this, \"__className__\" ) || \"\"\n\t\t\t\t\t);\n\t\t\t\t}\n\t\t\t}\n\t\t} );\n\t},\n\n\thasClass: function( selector ) {\n\t\tvar className, elem,\n\t\t\ti = 0;\n\n\t\tclassName = \" \" + selector + \" \";\n\t\twhile ( ( elem = this[ i++ ] ) ) {\n\t\t\tif ( elem.nodeType === 1 &&\n\t\t\t\t( \" \" + stripAndCollapse( getClass( elem ) ) + \" \" ).indexOf( className ) > -1 ) {\n\t\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\n\t\treturn false;\n\t}\n} );\n\n\n\n\nvar rreturn = /\\r/g;\n\njQuery.fn.extend( {\n\tval: function( value ) {\n\t\tvar hooks, ret, isFunction,\n\t\t\telem = this[ 0 ];\n\n\t\tif ( !arguments.length ) {\n\t\t\tif ( elem ) {\n\t\t\t\thooks = jQuery.valHooks[ elem.type ] ||\n\t\t\t\t\tjQuery.valHooks[ elem.nodeName.toLowerCase() ];\n\n\t\t\t\tif ( hooks &&\n\t\t\t\t\t\"get\" in hooks &&\n\t\t\t\t\t( ret = hooks.get( elem, \"value\" ) ) !== undefined\n\t\t\t\t) {\n\t\t\t\t\treturn ret;\n\t\t\t\t}\n\n\t\t\t\tret = elem.value;\n\n\t\t\t\t// Handle most common string cases\n\t\t\t\tif ( typeof ret === \"string\" ) {\n\t\t\t\t\treturn ret.replace( rreturn, \"\" );\n\t\t\t\t}\n\n\t\t\t\t// Handle cases where value is null/undef or number\n\t\t\t\treturn ret == null ? \"\" : ret;\n\t\t\t}\n\n\t\t\treturn;\n\t\t}\n\n\t\tisFunction = jQuery.isFunction( value );\n\n\t\treturn this.each( function( i ) {\n\t\t\tvar val;\n\n\t\t\tif ( this.nodeType !== 1 ) {\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tif ( isFunction ) {\n\t\t\t\tval = value.call( this, i, jQuery( this ).val() );\n\t\t\t} else {\n\t\t\t\tval = value;\n\t\t\t}\n\n\t\t\t// Treat null/undefined as \"\"; convert numbers to string\n\t\t\tif ( val == null ) {\n\t\t\t\tval = \"\";\n\n\t\t\t} else if ( typeof val === \"number\" ) {\n\t\t\t\tval += \"\";\n\n\t\t\t} else if ( jQuery.isArray( val ) ) {\n\t\t\t\tval = jQuery.map( val, function( value ) {\n\t\t\t\t\treturn value == null ? \"\" : value + \"\";\n\t\t\t\t} );\n\t\t\t}\n\n\t\t\thooks = jQuery.valHooks[ this.type ] || jQuery.valHooks[ this.nodeName.toLowerCase() ];\n\n\t\t\t// If set returns undefined, fall back to normal setting\n\t\t\tif ( !hooks || !( \"set\" in hooks ) || hooks.set( this, val, \"value\" ) === undefined ) {\n\t\t\t\tthis.value = val;\n\t\t\t}\n\t\t} );\n\t}\n} );\n\njQuery.extend( {\n\tvalHooks: {\n\t\toption: {\n\t\t\tget: function( elem ) {\n\n\t\t\t\tvar val = jQuery.find.attr( elem, \"value\" );\n\t\t\t\treturn val != null ?\n\t\t\t\t\tval :\n\n\t\t\t\t\t// Support: IE <=10 - 11 only\n\t\t\t\t\t// option.text throws exceptions (#14686, #14858)\n\t\t\t\t\t// Strip and collapse whitespace\n\t\t\t\t\t// https://html.spec.whatwg.org/#strip-and-collapse-whitespace\n\t\t\t\t\tstripAndCollapse( jQuery.text( elem ) );\n\t\t\t}\n\t\t},\n\t\tselect: {\n\t\t\tget: function( elem ) {\n\t\t\t\tvar value, option, i,\n\t\t\t\t\toptions = elem.options,\n\t\t\t\t\tindex = elem.selectedIndex,\n\t\t\t\t\tone = elem.type === \"select-one\",\n\t\t\t\t\tvalues = one ? null : [],\n\t\t\t\t\tmax = one ? index + 1 : options.length;\n\n\t\t\t\tif ( index < 0 ) {\n\t\t\t\t\ti = max;\n\n\t\t\t\t} else {\n\t\t\t\t\ti = one ? index : 0;\n\t\t\t\t}\n\n\t\t\t\t// Loop through all the selected options\n\t\t\t\tfor ( ; i < max; i++ ) {\n\t\t\t\t\toption = options[ i ];\n\n\t\t\t\t\t// Support: IE <=9 only\n\t\t\t\t\t// IE8-9 doesn't update selected after form reset (#2551)\n\t\t\t\t\tif ( ( option.selected || i === index ) &&\n\n\t\t\t\t\t\t\t// Don't return options that are disabled or in a disabled optgroup\n\t\t\t\t\t\t\t!option.disabled &&\n\t\t\t\t\t\t\t( !option.parentNode.disabled ||\n\t\t\t\t\t\t\t\t!jQuery.nodeName( option.parentNode, \"optgroup\" ) ) ) {\n\n\t\t\t\t\t\t// Get the specific value for the option\n\t\t\t\t\t\tvalue = jQuery( option ).val();\n\n\t\t\t\t\t\t// We don't need an array for one selects\n\t\t\t\t\t\tif ( one ) {\n\t\t\t\t\t\t\treturn value;\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t// Multi-Selects return an array\n\t\t\t\t\t\tvalues.push( value );\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\treturn values;\n\t\t\t},\n\n\t\t\tset: function( elem, value ) {\n\t\t\t\tvar optionSet, option,\n\t\t\t\t\toptions = elem.options,\n\t\t\t\t\tvalues = jQuery.makeArray( value ),\n\t\t\t\t\ti = options.length;\n\n\t\t\t\twhile ( i-- ) {\n\t\t\t\t\toption = options[ i ];\n\n\t\t\t\t\t/* eslint-disable no-cond-assign */\n\n\t\t\t\t\tif ( option.selected =\n\t\t\t\t\t\tjQuery.inArray( jQuery.valHooks.option.get( option ), values ) > -1\n\t\t\t\t\t) {\n\t\t\t\t\t\toptionSet = true;\n\t\t\t\t\t}\n\n\t\t\t\t\t/* eslint-enable no-cond-assign */\n\t\t\t\t}\n\n\t\t\t\t// Force browsers to behave consistently when non-matching value is set\n\t\t\t\tif ( !optionSet ) {\n\t\t\t\t\telem.selectedIndex = -1;\n\t\t\t\t}\n\t\t\t\treturn values;\n\t\t\t}\n\t\t}\n\t}\n} );\n\n// Radios and checkboxes getter/setter\njQuery.each( [ \"radio\", \"checkbox\" ], function() {\n\tjQuery.valHooks[ this ] = {\n\t\tset: function( elem, value ) {\n\t\t\tif ( jQuery.isArray( value ) ) {\n\t\t\t\treturn ( elem.checked = jQuery.inArray( jQuery( elem ).val(), value ) > -1 );\n\t\t\t}\n\t\t}\n\t};\n\tif ( !support.checkOn ) {\n\t\tjQuery.valHooks[ this ].get = function( elem ) {\n\t\t\treturn elem.getAttribute( \"value\" ) === null ? \"on\" : elem.value;\n\t\t};\n\t}\n} );\n\n\n\n\n// Return jQuery for attributes-only inclusion\n\n\nvar rfocusMorph = /^(?:focusinfocus|focusoutblur)$/;\n\njQuery.extend( jQuery.event, {\n\n\ttrigger: function( event, data, elem, onlyHandlers ) {\n\n\t\tvar i, cur, tmp, bubbleType, ontype, handle, special,\n\t\t\teventPath = [ elem || document ],\n\t\t\ttype = hasOwn.call( event, \"type\" ) ? event.type : event,\n\t\t\tnamespaces = hasOwn.call( event, \"namespace\" ) ? event.namespace.split( \".\" ) : [];\n\n\t\tcur = tmp = elem = elem || document;\n\n\t\t// Don't do events on text and comment nodes\n\t\tif ( elem.nodeType === 3 || elem.nodeType === 8 ) {\n\t\t\treturn;\n\t\t}\n\n\t\t// focus/blur morphs to focusin/out; ensure we're not firing them right now\n\t\tif ( rfocusMorph.test( type + jQuery.event.triggered ) ) {\n\t\t\treturn;\n\t\t}\n\n\t\tif ( type.indexOf( \".\" ) > -1 ) {\n\n\t\t\t// Namespaced trigger; create a regexp to match event type in handle()\n\t\t\tnamespaces = type.split( \".\" );\n\t\t\ttype = namespaces.shift();\n\t\t\tnamespaces.sort();\n\t\t}\n\t\tontype = type.indexOf( \":\" ) < 0 && \"on\" + type;\n\n\t\t// Caller can pass in a jQuery.Event object, Object, or just an event type string\n\t\tevent = event[ jQuery.expando ] ?\n\t\t\tevent :\n\t\t\tnew jQuery.Event( type, typeof event === \"object\" && event );\n\n\t\t// Trigger bitmask: & 1 for native handlers; & 2 for jQuery (always true)\n\t\tevent.isTrigger = onlyHandlers ? 2 : 3;\n\t\tevent.namespace = namespaces.join( \".\" );\n\t\tevent.rnamespace = event.namespace ?\n\t\t\tnew RegExp( \"(^|\\\\.)\" + namespaces.join( \"\\\\.(?:.*\\\\.|)\" ) + \"(\\\\.|$)\" ) :\n\t\t\tnull;\n\n\t\t// Clean up the event in case it is being reused\n\t\tevent.result = undefined;\n\t\tif ( !event.target ) {\n\t\t\tevent.target = elem;\n\t\t}\n\n\t\t// Clone any incoming data and prepend the event, creating the handler arg list\n\t\tdata = data == null ?\n\t\t\t[ event ] :\n\t\t\tjQuery.makeArray( data, [ event ] );\n\n\t\t// Allow special events to draw outside the lines\n\t\tspecial = jQuery.event.special[ type ] || {};\n\t\tif ( !onlyHandlers && special.trigger && special.trigger.apply( elem, data ) === false ) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Determine event propagation path in advance, per W3C events spec (#9951)\n\t\t// Bubble up to document, then to window; watch for a global ownerDocument var (#9724)\n\t\tif ( !onlyHandlers && !special.noBubble && !jQuery.isWindow( elem ) ) {\n\n\t\t\tbubbleType = special.delegateType || type;\n\t\t\tif ( !rfocusMorph.test( bubbleType + type ) ) {\n\t\t\t\tcur = cur.parentNode;\n\t\t\t}\n\t\t\tfor ( ; cur; cur = cur.parentNode ) {\n\t\t\t\teventPath.push( cur );\n\t\t\t\ttmp = cur;\n\t\t\t}\n\n\t\t\t// Only add window if we got to document (e.g., not plain obj or detached DOM)\n\t\t\tif ( tmp === ( elem.ownerDocument || document ) ) {\n\t\t\t\teventPath.push( tmp.defaultView || tmp.parentWindow || window );\n\t\t\t}\n\t\t}\n\n\t\t// Fire handlers on the event path\n\t\ti = 0;\n\t\twhile ( ( cur = eventPath[ i++ ] ) && !event.isPropagationStopped() ) {\n\n\t\t\tevent.type = i > 1 ?\n\t\t\t\tbubbleType :\n\t\t\t\tspecial.bindType || type;\n\n\t\t\t// jQuery handler\n\t\t\thandle = ( dataPriv.get( cur, \"events\" ) || {} )[ event.type ] &&\n\t\t\t\tdataPriv.get( cur, \"handle\" );\n\t\t\tif ( handle ) {\n\t\t\t\thandle.apply( cur, data );\n\t\t\t}\n\n\t\t\t// Native handler\n\t\t\thandle = ontype && cur[ ontype ];\n\t\t\tif ( handle && handle.apply && acceptData( cur ) ) {\n\t\t\t\tevent.result = handle.apply( cur, data );\n\t\t\t\tif ( event.result === false ) {\n\t\t\t\t\tevent.preventDefault();\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tevent.type = type;\n\n\t\t// If nobody prevented the default action, do it now\n\t\tif ( !onlyHandlers && !event.isDefaultPrevented() ) {\n\n\t\t\tif ( ( !special._default ||\n\t\t\t\tspecial._default.apply( eventPath.pop(), data ) === false ) &&\n\t\t\t\tacceptData( elem ) ) {\n\n\t\t\t\t// Call a native DOM method on the target with the same name as the event.\n\t\t\t\t// Don't do default actions on window, that's where global variables be (#6170)\n\t\t\t\tif ( ontype && jQuery.isFunction( elem[ type ] ) && !jQuery.isWindow( elem ) ) {\n\n\t\t\t\t\t// Don't re-trigger an onFOO event when we call its FOO() method\n\t\t\t\t\ttmp = elem[ ontype ];\n\n\t\t\t\t\tif ( tmp ) {\n\t\t\t\t\t\telem[ ontype ] = null;\n\t\t\t\t\t}\n\n\t\t\t\t\t// Prevent re-triggering of the same event, since we already bubbled it above\n\t\t\t\t\tjQuery.event.triggered = type;\n\t\t\t\t\telem[ type ]();\n\t\t\t\t\tjQuery.event.triggered = undefined;\n\n\t\t\t\t\tif ( tmp ) {\n\t\t\t\t\t\telem[ ontype ] = tmp;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn event.result;\n\t},\n\n\t// Piggyback on a donor event to simulate a different one\n\t// Used only for `focus(in | out)` events\n\tsimulate: function( type, elem, event ) {\n\t\tvar e = jQuery.extend(\n\t\t\tnew jQuery.Event(),\n\t\t\tevent,\n\t\t\t{\n\t\t\t\ttype: type,\n\t\t\t\tisSimulated: true\n\t\t\t}\n\t\t);\n\n\t\tjQuery.event.trigger( e, null, elem );\n\t}\n\n} );\n\njQuery.fn.extend( {\n\n\ttrigger: function( type, data ) {\n\t\treturn this.each( function() {\n\t\t\tjQuery.event.trigger( type, data, this );\n\t\t} );\n\t},\n\ttriggerHandler: function( type, data ) {\n\t\tvar elem = this[ 0 ];\n\t\tif ( elem ) {\n\t\t\treturn jQuery.event.trigger( type, data, elem, true );\n\t\t}\n\t}\n} );\n\n\njQuery.each( ( \"blur focus focusin focusout resize scroll click dblclick \" +\n\t\"mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave \" +\n\t\"change select submit keydown keypress keyup contextmenu\" ).split( \" \" ),\n\tfunction( i, name ) {\n\n\t// Handle event binding\n\tjQuery.fn[ name ] = function( data, fn ) {\n\t\treturn arguments.length > 0 ?\n\t\t\tthis.on( name, null, data, fn ) :\n\t\t\tthis.trigger( name );\n\t};\n} );\n\njQuery.fn.extend( {\n\thover: function( fnOver, fnOut ) {\n\t\treturn this.mouseenter( fnOver ).mouseleave( fnOut || fnOver );\n\t}\n} );\n\n\n\n\nsupport.focusin = \"onfocusin\" in window;\n\n\n// Support: Firefox <=44\n// Firefox doesn't have focus(in | out) events\n// Related ticket - https://bugzilla.mozilla.org/show_bug.cgi?id=687787\n//\n// Support: Chrome <=48 - 49, Safari <=9.0 - 9.1\n// focus(in | out) events fire after focus & blur events,\n// which is spec violation - http://www.w3.org/TR/DOM-Level-3-Events/#events-focusevent-event-order\n// Related ticket - https://bugs.chromium.org/p/chromium/issues/detail?id=449857\nif ( !support.focusin ) {\n\tjQuery.each( { focus: \"focusin\", blur: \"focusout\" }, function( orig, fix ) {\n\n\t\t// Attach a single capturing handler on the document while someone wants focusin/focusout\n\t\tvar handler = function( event ) {\n\t\t\tjQuery.event.simulate( fix, event.target, jQuery.event.fix( event ) );\n\t\t};\n\n\t\tjQuery.event.special[ fix ] = {\n\t\t\tsetup: function() {\n\t\t\t\tvar doc = this.ownerDocument || this,\n\t\t\t\t\tattaches = dataPriv.access( doc, fix );\n\n\t\t\t\tif ( !attaches ) {\n\t\t\t\t\tdoc.addEventListener( orig, handler, true );\n\t\t\t\t}\n\t\t\t\tdataPriv.access( doc, fix, ( attaches || 0 ) + 1 );\n\t\t\t},\n\t\t\tteardown: function() {\n\t\t\t\tvar doc = this.ownerDocument || this,\n\t\t\t\t\tattaches = dataPriv.access( doc, fix ) - 1;\n\n\t\t\t\tif ( !attaches ) {\n\t\t\t\t\tdoc.removeEventListener( orig, handler, true );\n\t\t\t\t\tdataPriv.remove( doc, fix );\n\n\t\t\t\t} else {\n\t\t\t\t\tdataPriv.access( doc, fix, attaches );\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t} );\n}\nvar location = window.location;\n\nvar nonce = jQuery.now();\n\nvar rquery = ( /\\?/ );\n\n\n\n// Cross-browser xml parsing\njQuery.parseXML = function( data ) {\n\tvar xml;\n\tif ( !data || typeof data !== \"string\" ) {\n\t\treturn null;\n\t}\n\n\t// Support: IE 9 - 11 only\n\t// IE throws on parseFromString with invalid input.\n\ttry {\n\t\txml = ( new window.DOMParser() ).parseFromString( data, \"text/xml\" );\n\t} catch ( e ) {\n\t\txml = undefined;\n\t}\n\n\tif ( !xml || xml.getElementsByTagName( \"parsererror\" ).length ) {\n\t\tjQuery.error( \"Invalid XML: \" + data );\n\t}\n\treturn xml;\n};\n\n\nvar\n\trbracket = /\\[\\]$/,\n\trCRLF = /\\r?\\n/g,\n\trsubmitterTypes = /^(?:submit|button|image|reset|file)$/i,\n\trsubmittable = /^(?:input|select|textarea|keygen)/i;\n\nfunction buildParams( prefix, obj, traditional, add ) {\n\tvar name;\n\n\tif ( jQuery.isArray( obj ) ) {\n\n\t\t// Serialize array item.\n\t\tjQuery.each( obj, function( i, v ) {\n\t\t\tif ( traditional || rbracket.test( prefix ) ) {\n\n\t\t\t\t// Treat each array item as a scalar.\n\t\t\t\tadd( prefix, v );\n\n\t\t\t} else {\n\n\t\t\t\t// Item is non-scalar (array or object), encode its numeric index.\n\t\t\t\tbuildParams(\n\t\t\t\t\tprefix + \"[\" + ( typeof v === \"object\" && v != null ? i : \"\" ) + \"]\",\n\t\t\t\t\tv,\n\t\t\t\t\ttraditional,\n\t\t\t\t\tadd\n\t\t\t\t);\n\t\t\t}\n\t\t} );\n\n\t} else if ( !traditional && jQuery.type( obj ) === \"object\" ) {\n\n\t\t// Serialize object item.\n\t\tfor ( name in obj ) {\n\t\t\tbuildParams( prefix + \"[\" + name + \"]\", obj[ name ], traditional, add );\n\t\t}\n\n\t} else {\n\n\t\t// Serialize scalar item.\n\t\tadd( prefix, obj );\n\t}\n}\n\n// Serialize an array of form elements or a set of\n// key/values into a query string\njQuery.param = function( a, traditional ) {\n\tvar prefix,\n\t\ts = [],\n\t\tadd = function( key, valueOrFunction ) {\n\n\t\t\t// If value is a function, invoke it and use its return value\n\t\t\tvar value = jQuery.isFunction( valueOrFunction ) ?\n\t\t\t\tvalueOrFunction() :\n\t\t\t\tvalueOrFunction;\n\n\t\t\ts[ s.length ] = encodeURIComponent( key ) + \"=\" +\n\t\t\t\tencodeURIComponent( value == null ? \"\" : value );\n\t\t};\n\n\t// If an array was passed in, assume that it is an array of form elements.\n\tif ( jQuery.isArray( a ) || ( a.jquery && !jQuery.isPlainObject( a ) ) ) {\n\n\t\t// Serialize the form elements\n\t\tjQuery.each( a, function() {\n\t\t\tadd( this.name, this.value );\n\t\t} );\n\n\t} else {\n\n\t\t// If traditional, encode the \"old\" way (the way 1.3.2 or older\n\t\t// did it), otherwise encode params recursively.\n\t\tfor ( prefix in a ) {\n\t\t\tbuildParams( prefix, a[ prefix ], traditional, add );\n\t\t}\n\t}\n\n\t// Return the resulting serialization\n\treturn s.join( \"&\" );\n};\n\njQuery.fn.extend( {\n\tserialize: function() {\n\t\treturn jQuery.param( this.serializeArray() );\n\t},\n\tserializeArray: function() {\n\t\treturn this.map( function() {\n\n\t\t\t// Can add propHook for \"elements\" to filter or add form elements\n\t\t\tvar elements = jQuery.prop( this, \"elements\" );\n\t\t\treturn elements ? jQuery.makeArray( elements ) : this;\n\t\t} )\n\t\t.filter( function() {\n\t\t\tvar type = this.type;\n\n\t\t\t// Use .is( \":disabled\" ) so that fieldset[disabled] works\n\t\t\treturn this.name && !jQuery( this ).is( \":disabled\" ) &&\n\t\t\t\trsubmittable.test( this.nodeName ) && !rsubmitterTypes.test( type ) &&\n\t\t\t\t( this.checked || !rcheckableType.test( type ) );\n\t\t} )\n\t\t.map( function( i, elem ) {\n\t\t\tvar val = jQuery( this ).val();\n\n\t\t\tif ( val == null ) {\n\t\t\t\treturn null;\n\t\t\t}\n\n\t\t\tif ( jQuery.isArray( val ) ) {\n\t\t\t\treturn jQuery.map( val, function( val ) {\n\t\t\t\t\treturn { name: elem.name, value: val.replace( rCRLF, \"\\r\\n\" ) };\n\t\t\t\t} );\n\t\t\t}\n\n\t\t\treturn { name: elem.name, value: val.replace( rCRLF, \"\\r\\n\" ) };\n\t\t} ).get();\n\t}\n} );\n\n\nvar\n\tr20 = /%20/g,\n\trhash = /#.*$/,\n\trantiCache = /([?&])_=[^&]*/,\n\trheaders = /^(.*?):[ \\t]*([^\\r\\n]*)$/mg,\n\n\t// #7653, #8125, #8152: local protocol detection\n\trlocalProtocol = /^(?:about|app|app-storage|.+-extension|file|res|widget):$/,\n\trnoContent = /^(?:GET|HEAD)$/,\n\trprotocol = /^\\/\\//,\n\n\t/* Prefilters\n\t * 1) They are useful to introduce custom dataTypes (see ajax/jsonp.js for an example)\n\t * 2) These are called:\n\t *    - BEFORE asking for a transport\n\t *    - AFTER param serialization (s.data is a string if s.processData is true)\n\t * 3) key is the dataType\n\t * 4) the catchall symbol \"*\" can be used\n\t * 5) execution will start with transport dataType and THEN continue down to \"*\" if needed\n\t */\n\tprefilters = {},\n\n\t/* Transports bindings\n\t * 1) key is the dataType\n\t * 2) the catchall symbol \"*\" can be used\n\t * 3) selection will start with transport dataType and THEN go to \"*\" if needed\n\t */\n\ttransports = {},\n\n\t// Avoid comment-prolog char sequence (#10098); must appease lint and evade compression\n\tallTypes = \"*/\".concat( \"*\" ),\n\n\t// Anchor tag for parsing the document origin\n\toriginAnchor = document.createElement( \"a\" );\n\toriginAnchor.href = location.href;\n\n// Base \"constructor\" for jQuery.ajaxPrefilter and jQuery.ajaxTransport\nfunction addToPrefiltersOrTransports( structure ) {\n\n\t// dataTypeExpression is optional and defaults to \"*\"\n\treturn function( dataTypeExpression, func ) {\n\n\t\tif ( typeof dataTypeExpression !== \"string\" ) {\n\t\t\tfunc = dataTypeExpression;\n\t\t\tdataTypeExpression = \"*\";\n\t\t}\n\n\t\tvar dataType,\n\t\t\ti = 0,\n\t\t\tdataTypes = dataTypeExpression.toLowerCase().match( rnothtmlwhite ) || [];\n\n\t\tif ( jQuery.isFunction( func ) ) {\n\n\t\t\t// For each dataType in the dataTypeExpression\n\t\t\twhile ( ( dataType = dataTypes[ i++ ] ) ) {\n\n\t\t\t\t// Prepend if requested\n\t\t\t\tif ( dataType[ 0 ] === \"+\" ) {\n\t\t\t\t\tdataType = dataType.slice( 1 ) || \"*\";\n\t\t\t\t\t( structure[ dataType ] = structure[ dataType ] || [] ).unshift( func );\n\n\t\t\t\t// Otherwise append\n\t\t\t\t} else {\n\t\t\t\t\t( structure[ dataType ] = structure[ dataType ] || [] ).push( func );\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t};\n}\n\n// Base inspection function for prefilters and transports\nfunction inspectPrefiltersOrTransports( structure, options, originalOptions, jqXHR ) {\n\n\tvar inspected = {},\n\t\tseekingTransport = ( structure === transports );\n\n\tfunction inspect( dataType ) {\n\t\tvar selected;\n\t\tinspected[ dataType ] = true;\n\t\tjQuery.each( structure[ dataType ] || [], function( _, prefilterOrFactory ) {\n\t\t\tvar dataTypeOrTransport = prefilterOrFactory( options, originalOptions, jqXHR );\n\t\t\tif ( typeof dataTypeOrTransport === \"string\" &&\n\t\t\t\t!seekingTransport && !inspected[ dataTypeOrTransport ] ) {\n\n\t\t\t\toptions.dataTypes.unshift( dataTypeOrTransport );\n\t\t\t\tinspect( dataTypeOrTransport );\n\t\t\t\treturn false;\n\t\t\t} else if ( seekingTransport ) {\n\t\t\t\treturn !( selected = dataTypeOrTransport );\n\t\t\t}\n\t\t} );\n\t\treturn selected;\n\t}\n\n\treturn inspect( options.dataTypes[ 0 ] ) || !inspected[ \"*\" ] && inspect( \"*\" );\n}\n\n// A special extend for ajax options\n// that takes \"flat\" options (not to be deep extended)\n// Fixes #9887\nfunction ajaxExtend( target, src ) {\n\tvar key, deep,\n\t\tflatOptions = jQuery.ajaxSettings.flatOptions || {};\n\n\tfor ( key in src ) {\n\t\tif ( src[ key ] !== undefined ) {\n\t\t\t( flatOptions[ key ] ? target : ( deep || ( deep = {} ) ) )[ key ] = src[ key ];\n\t\t}\n\t}\n\tif ( deep ) {\n\t\tjQuery.extend( true, target, deep );\n\t}\n\n\treturn target;\n}\n\n/* Handles responses to an ajax request:\n * - finds the right dataType (mediates between content-type and expected dataType)\n * - returns the corresponding response\n */\nfunction ajaxHandleResponses( s, jqXHR, responses ) {\n\n\tvar ct, type, finalDataType, firstDataType,\n\t\tcontents = s.contents,\n\t\tdataTypes = s.dataTypes;\n\n\t// Remove auto dataType and get content-type in the process\n\twhile ( dataTypes[ 0 ] === \"*\" ) {\n\t\tdataTypes.shift();\n\t\tif ( ct === undefined ) {\n\t\t\tct = s.mimeType || jqXHR.getResponseHeader( \"Content-Type\" );\n\t\t}\n\t}\n\n\t// Check if we're dealing with a known content-type\n\tif ( ct ) {\n\t\tfor ( type in contents ) {\n\t\t\tif ( contents[ type ] && contents[ type ].test( ct ) ) {\n\t\t\t\tdataTypes.unshift( type );\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\t// Check to see if we have a response for the expected dataType\n\tif ( dataTypes[ 0 ] in responses ) {\n\t\tfinalDataType = dataTypes[ 0 ];\n\t} else {\n\n\t\t// Try convertible dataTypes\n\t\tfor ( type in responses ) {\n\t\t\tif ( !dataTypes[ 0 ] || s.converters[ type + \" \" + dataTypes[ 0 ] ] ) {\n\t\t\t\tfinalDataType = type;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif ( !firstDataType ) {\n\t\t\t\tfirstDataType = type;\n\t\t\t}\n\t\t}\n\n\t\t// Or just use first one\n\t\tfinalDataType = finalDataType || firstDataType;\n\t}\n\n\t// If we found a dataType\n\t// We add the dataType to the list if needed\n\t// and return the corresponding response\n\tif ( finalDataType ) {\n\t\tif ( finalDataType !== dataTypes[ 0 ] ) {\n\t\t\tdataTypes.unshift( finalDataType );\n\t\t}\n\t\treturn responses[ finalDataType ];\n\t}\n}\n\n/* Chain conversions given the request and the original response\n * Also sets the responseXXX fields on the jqXHR instance\n */\nfunction ajaxConvert( s, response, jqXHR, isSuccess ) {\n\tvar conv2, current, conv, tmp, prev,\n\t\tconverters = {},\n\n\t\t// Work with a copy of dataTypes in case we need to modify it for conversion\n\t\tdataTypes = s.dataTypes.slice();\n\n\t// Create converters map with lowercased keys\n\tif ( dataTypes[ 1 ] ) {\n\t\tfor ( conv in s.converters ) {\n\t\t\tconverters[ conv.toLowerCase() ] = s.converters[ conv ];\n\t\t}\n\t}\n\n\tcurrent = dataTypes.shift();\n\n\t// Convert to each sequential dataType\n\twhile ( current ) {\n\n\t\tif ( s.responseFields[ current ] ) {\n\t\t\tjqXHR[ s.responseFields[ current ] ] = response;\n\t\t}\n\n\t\t// Apply the dataFilter if provided\n\t\tif ( !prev && isSuccess && s.dataFilter ) {\n\t\t\tresponse = s.dataFilter( response, s.dataType );\n\t\t}\n\n\t\tprev = current;\n\t\tcurrent = dataTypes.shift();\n\n\t\tif ( current ) {\n\n\t\t\t// There's only work to do if current dataType is non-auto\n\t\t\tif ( current === \"*\" ) {\n\n\t\t\t\tcurrent = prev;\n\n\t\t\t// Convert response if prev dataType is non-auto and differs from current\n\t\t\t} else if ( prev !== \"*\" && prev !== current ) {\n\n\t\t\t\t// Seek a direct converter\n\t\t\t\tconv = converters[ prev + \" \" + current ] || converters[ \"* \" + current ];\n\n\t\t\t\t// If none found, seek a pair\n\t\t\t\tif ( !conv ) {\n\t\t\t\t\tfor ( conv2 in converters ) {\n\n\t\t\t\t\t\t// If conv2 outputs current\n\t\t\t\t\t\ttmp = conv2.split( \" \" );\n\t\t\t\t\t\tif ( tmp[ 1 ] === current ) {\n\n\t\t\t\t\t\t\t// If prev can be converted to accepted input\n\t\t\t\t\t\t\tconv = converters[ prev + \" \" + tmp[ 0 ] ] ||\n\t\t\t\t\t\t\t\tconverters[ \"* \" + tmp[ 0 ] ];\n\t\t\t\t\t\t\tif ( conv ) {\n\n\t\t\t\t\t\t\t\t// Condense equivalence converters\n\t\t\t\t\t\t\t\tif ( conv === true ) {\n\t\t\t\t\t\t\t\t\tconv = converters[ conv2 ];\n\n\t\t\t\t\t\t\t\t// Otherwise, insert the intermediate dataType\n\t\t\t\t\t\t\t\t} else if ( converters[ conv2 ] !== true ) {\n\t\t\t\t\t\t\t\t\tcurrent = tmp[ 0 ];\n\t\t\t\t\t\t\t\t\tdataTypes.unshift( tmp[ 1 ] );\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// Apply converter (if not an equivalence)\n\t\t\t\tif ( conv !== true ) {\n\n\t\t\t\t\t// Unless errors are allowed to bubble, catch and return them\n\t\t\t\t\tif ( conv && s.throws ) {\n\t\t\t\t\t\tresponse = conv( response );\n\t\t\t\t\t} else {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tresponse = conv( response );\n\t\t\t\t\t\t} catch ( e ) {\n\t\t\t\t\t\t\treturn {\n\t\t\t\t\t\t\t\tstate: \"parsererror\",\n\t\t\t\t\t\t\t\terror: conv ? e : \"No conversion from \" + prev + \" to \" + current\n\t\t\t\t\t\t\t};\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\treturn { state: \"success\", data: response };\n}\n\njQuery.extend( {\n\n\t// Counter for holding the number of active queries\n\tactive: 0,\n\n\t// Last-Modified header cache for next request\n\tlastModified: {},\n\tetag: {},\n\n\tajaxSettings: {\n\t\turl: location.href,\n\t\ttype: \"GET\",\n\t\tisLocal: rlocalProtocol.test( location.protocol ),\n\t\tglobal: true,\n\t\tprocessData: true,\n\t\tasync: true,\n\t\tcontentType: \"application/x-www-form-urlencoded; charset=UTF-8\",\n\n\t\t/*\n\t\ttimeout: 0,\n\t\tdata: null,\n\t\tdataType: null,\n\t\tusername: null,\n\t\tpassword: null,\n\t\tcache: null,\n\t\tthrows: false,\n\t\ttraditional: false,\n\t\theaders: {},\n\t\t*/\n\n\t\taccepts: {\n\t\t\t\"*\": allTypes,\n\t\t\ttext: \"text/plain\",\n\t\t\thtml: \"text/html\",\n\t\t\txml: \"application/xml, text/xml\",\n\t\t\tjson: \"application/json, text/javascript\"\n\t\t},\n\n\t\tcontents: {\n\t\t\txml: /\\bxml\\b/,\n\t\t\thtml: /\\bhtml/,\n\t\t\tjson: /\\bjson\\b/\n\t\t},\n\n\t\tresponseFields: {\n\t\t\txml: \"responseXML\",\n\t\t\ttext: \"responseText\",\n\t\t\tjson: \"responseJSON\"\n\t\t},\n\n\t\t// Data converters\n\t\t// Keys separate source (or catchall \"*\") and destination types with a single space\n\t\tconverters: {\n\n\t\t\t// Convert anything to text\n\t\t\t\"* text\": String,\n\n\t\t\t// Text to html (true = no transformation)\n\t\t\t\"text html\": true,\n\n\t\t\t// Evaluate text as a json expression\n\t\t\t\"text json\": JSON.parse,\n\n\t\t\t// Parse text as xml\n\t\t\t\"text xml\": jQuery.parseXML\n\t\t},\n\n\t\t// For options that shouldn't be deep extended:\n\t\t// you can add your own custom options here if\n\t\t// and when you create one that shouldn't be\n\t\t// deep extended (see ajaxExtend)\n\t\tflatOptions: {\n\t\t\turl: true,\n\t\t\tcontext: true\n\t\t}\n\t},\n\n\t// Creates a full fledged settings object into target\n\t// with both ajaxSettings and settings fields.\n\t// If target is omitted, writes into ajaxSettings.\n\tajaxSetup: function( target, settings ) {\n\t\treturn settings ?\n\n\t\t\t// Building a settings object\n\t\t\tajaxExtend( ajaxExtend( target, jQuery.ajaxSettings ), settings ) :\n\n\t\t\t// Extending ajaxSettings\n\t\t\tajaxExtend( jQuery.ajaxSettings, target );\n\t},\n\n\tajaxPrefilter: addToPrefiltersOrTransports( prefilters ),\n\tajaxTransport: addToPrefiltersOrTransports( transports ),\n\n\t// Main method\n\tajax: function( url, options ) {\n\n\t\t// If url is an object, simulate pre-1.5 signature\n\t\tif ( typeof url === \"object\" ) {\n\t\t\toptions = url;\n\t\t\turl = undefined;\n\t\t}\n\n\t\t// Force options to be an object\n\t\toptions = options || {};\n\n\t\tvar transport,\n\n\t\t\t// URL without anti-cache param\n\t\t\tcacheURL,\n\n\t\t\t// Response headers\n\t\t\tresponseHeadersString,\n\t\t\tresponseHeaders,\n\n\t\t\t// timeout handle\n\t\t\ttimeoutTimer,\n\n\t\t\t// Url cleanup var\n\t\t\turlAnchor,\n\n\t\t\t// Request state (becomes false upon send and true upon completion)\n\t\t\tcompleted,\n\n\t\t\t// To know if global events are to be dispatched\n\t\t\tfireGlobals,\n\n\t\t\t// Loop variable\n\t\t\ti,\n\n\t\t\t// uncached part of the url\n\t\t\tuncached,\n\n\t\t\t// Create the final options object\n\t\t\ts = jQuery.ajaxSetup( {}, options ),\n\n\t\t\t// Callbacks context\n\t\t\tcallbackContext = s.context || s,\n\n\t\t\t// Context for global events is callbackContext if it is a DOM node or jQuery collection\n\t\t\tglobalEventContext = s.context &&\n\t\t\t\t( callbackContext.nodeType || callbackContext.jquery ) ?\n\t\t\t\t\tjQuery( callbackContext ) :\n\t\t\t\t\tjQuery.event,\n\n\t\t\t// Deferreds\n\t\t\tdeferred = jQuery.Deferred(),\n\t\t\tcompleteDeferred = jQuery.Callbacks( \"once memory\" ),\n\n\t\t\t// Status-dependent callbacks\n\t\t\tstatusCode = s.statusCode || {},\n\n\t\t\t// Headers (they are sent all at once)\n\t\t\trequestHeaders = {},\n\t\t\trequestHeadersNames = {},\n\n\t\t\t// Default abort message\n\t\t\tstrAbort = \"canceled\",\n\n\t\t\t// Fake xhr\n\t\t\tjqXHR = {\n\t\t\t\treadyState: 0,\n\n\t\t\t\t// Builds headers hashtable if needed\n\t\t\t\tgetResponseHeader: function( key ) {\n\t\t\t\t\tvar match;\n\t\t\t\t\tif ( completed ) {\n\t\t\t\t\t\tif ( !responseHeaders ) {\n\t\t\t\t\t\t\tresponseHeaders = {};\n\t\t\t\t\t\t\twhile ( ( match = rheaders.exec( responseHeadersString ) ) ) {\n\t\t\t\t\t\t\t\tresponseHeaders[ match[ 1 ].toLowerCase() ] = match[ 2 ];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\tmatch = responseHeaders[ key.toLowerCase() ];\n\t\t\t\t\t}\n\t\t\t\t\treturn match == null ? null : match;\n\t\t\t\t},\n\n\t\t\t\t// Raw string\n\t\t\t\tgetAllResponseHeaders: function() {\n\t\t\t\t\treturn completed ? responseHeadersString : null;\n\t\t\t\t},\n\n\t\t\t\t// Caches the header\n\t\t\t\tsetRequestHeader: function( name, value ) {\n\t\t\t\t\tif ( completed == null ) {\n\t\t\t\t\t\tname = requestHeadersNames[ name.toLowerCase() ] =\n\t\t\t\t\t\t\trequestHeadersNames[ name.toLowerCase() ] || name;\n\t\t\t\t\t\trequestHeaders[ name ] = value;\n\t\t\t\t\t}\n\t\t\t\t\treturn this;\n\t\t\t\t},\n\n\t\t\t\t// Overrides response content-type header\n\t\t\t\toverrideMimeType: function( type ) {\n\t\t\t\t\tif ( completed == null ) {\n\t\t\t\t\t\ts.mimeType = type;\n\t\t\t\t\t}\n\t\t\t\t\treturn this;\n\t\t\t\t},\n\n\t\t\t\t// Status-dependent callbacks\n\t\t\t\tstatusCode: function( map ) {\n\t\t\t\t\tvar code;\n\t\t\t\t\tif ( map ) {\n\t\t\t\t\t\tif ( completed ) {\n\n\t\t\t\t\t\t\t// Execute the appropriate callbacks\n\t\t\t\t\t\t\tjqXHR.always( map[ jqXHR.status ] );\n\t\t\t\t\t\t} else {\n\n\t\t\t\t\t\t\t// Lazy-add the new callbacks in a way that preserves old ones\n\t\t\t\t\t\t\tfor ( code in map ) {\n\t\t\t\t\t\t\t\tstatusCode[ code ] = [ statusCode[ code ], map[ code ] ];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\treturn this;\n\t\t\t\t},\n\n\t\t\t\t// Cancel the request\n\t\t\t\tabort: function( statusText ) {\n\t\t\t\t\tvar finalText = statusText || strAbort;\n\t\t\t\t\tif ( transport ) {\n\t\t\t\t\t\ttransport.abort( finalText );\n\t\t\t\t\t}\n\t\t\t\t\tdone( 0, finalText );\n\t\t\t\t\treturn this;\n\t\t\t\t}\n\t\t\t};\n\n\t\t// Attach deferreds\n\t\tdeferred.promise( jqXHR );\n\n\t\t// Add protocol if not provided (prefilters might expect it)\n\t\t// Handle falsy url in the settings object (#10093: consistency with old signature)\n\t\t// We also use the url parameter if available\n\t\ts.url = ( ( url || s.url || location.href ) + \"\" )\n\t\t\t.replace( rprotocol, location.protocol + \"//\" );\n\n\t\t// Alias method option to type as per ticket #12004\n\t\ts.type = options.method || options.type || s.method || s.type;\n\n\t\t// Extract dataTypes list\n\t\ts.dataTypes = ( s.dataType || \"*\" ).toLowerCase().match( rnothtmlwhite ) || [ \"\" ];\n\n\t\t// A cross-domain request is in order when the origin doesn't match the current origin.\n\t\tif ( s.crossDomain == null ) {\n\t\t\turlAnchor = document.createElement( \"a\" );\n\n\t\t\t// Support: IE <=8 - 11, Edge 12 - 13\n\t\t\t// IE throws exception on accessing the href property if url is malformed,\n\t\t\t// e.g. http://example.com:80x/\n\t\t\ttry {\n\t\t\t\turlAnchor.href = s.url;\n\n\t\t\t\t// Support: IE <=8 - 11 only\n\t\t\t\t// Anchor's host property isn't correctly set when s.url is relative\n\t\t\t\turlAnchor.href = urlAnchor.href;\n\t\t\t\ts.crossDomain = originAnchor.protocol + \"//\" + originAnchor.host !==\n\t\t\t\t\turlAnchor.protocol + \"//\" + urlAnchor.host;\n\t\t\t} catch ( e ) {\n\n\t\t\t\t// If there is an error parsing the URL, assume it is crossDomain,\n\t\t\t\t// it can be rejected by the transport if it is invalid\n\t\t\t\ts.crossDomain = true;\n\t\t\t}\n\t\t}\n\n\t\t// Convert data if not already a string\n\t\tif ( s.data && s.processData && typeof s.data !== \"string\" ) {\n\t\t\ts.data = jQuery.param( s.data, s.traditional );\n\t\t}\n\n\t\t// Apply prefilters\n\t\tinspectPrefiltersOrTransports( prefilters, s, options, jqXHR );\n\n\t\t// If request was aborted inside a prefilter, stop there\n\t\tif ( completed ) {\n\t\t\treturn jqXHR;\n\t\t}\n\n\t\t// We can fire global events as of now if asked to\n\t\t// Don't fire events if jQuery.event is undefined in an AMD-usage scenario (#15118)\n\t\tfireGlobals = jQuery.event && s.global;\n\n\t\t// Watch for a new set of requests\n\t\tif ( fireGlobals && jQuery.active++ === 0 ) {\n\t\t\tjQuery.event.trigger( \"ajaxStart\" );\n\t\t}\n\n\t\t// Uppercase the type\n\t\ts.type = s.type.toUpperCase();\n\n\t\t// Determine if request has content\n\t\ts.hasContent = !rnoContent.test( s.type );\n\n\t\t// Save the URL in case we're toying with the If-Modified-Since\n\t\t// and/or If-None-Match header later on\n\t\t// Remove hash to simplify url manipulation\n\t\tcacheURL = s.url.replace( rhash, \"\" );\n\n\t\t// More options handling for requests with no content\n\t\tif ( !s.hasContent ) {\n\n\t\t\t// Remember the hash so we can put it back\n\t\t\tuncached = s.url.slice( cacheURL.length );\n\n\t\t\t// If data is available, append data to url\n\t\t\tif ( s.data ) {\n\t\t\t\tcacheURL += ( rquery.test( cacheURL ) ? \"&\" : \"?\" ) + s.data;\n\n\t\t\t\t// #9682: remove data so that it's not used in an eventual retry\n\t\t\t\tdelete s.data;\n\t\t\t}\n\n\t\t\t// Add or update anti-cache param if needed\n\t\t\tif ( s.cache === false ) {\n\t\t\t\tcacheURL = cacheURL.replace( rantiCache, \"$1\" );\n\t\t\t\tuncached = ( rquery.test( cacheURL ) ? \"&\" : \"?\" ) + \"_=\" + ( nonce++ ) + uncached;\n\t\t\t}\n\n\t\t\t// Put hash and anti-cache on the URL that will be requested (gh-1732)\n\t\t\ts.url = cacheURL + uncached;\n\n\t\t// Change '%20' to '+' if this is encoded form body content (gh-2658)\n\t\t} else if ( s.data && s.processData &&\n\t\t\t( s.contentType || \"\" ).indexOf( \"application/x-www-form-urlencoded\" ) === 0 ) {\n\t\t\ts.data = s.data.replace( r20, \"+\" );\n\t\t}\n\n\t\t// Set the If-Modified-Since and/or If-None-Match header, if in ifModified mode.\n\t\tif ( s.ifModified ) {\n\t\t\tif ( jQuery.lastModified[ cacheURL ] ) {\n\t\t\t\tjqXHR.setRequestHeader( \"If-Modified-Since\", jQuery.lastModified[ cacheURL ] );\n\t\t\t}\n\t\t\tif ( jQuery.etag[ cacheURL ] ) {\n\t\t\t\tjqXHR.setRequestHeader( \"If-None-Match\", jQuery.etag[ cacheURL ] );\n\t\t\t}\n\t\t}\n\n\t\t// Set the correct header, if data is being sent\n\t\tif ( s.data && s.hasContent && s.contentType !== false || options.contentType ) {\n\t\t\tjqXHR.setRequestHeader( \"Content-Type\", s.contentType );\n\t\t}\n\n\t\t// Set the Accepts header for the server, depending on the dataType\n\t\tjqXHR.setRequestHeader(\n\t\t\t\"Accept\",\n\t\t\ts.dataTypes[ 0 ] && s.accepts[ s.dataTypes[ 0 ] ] ?\n\t\t\t\ts.accepts[ s.dataTypes[ 0 ] ] +\n\t\t\t\t\t( s.dataTypes[ 0 ] !== \"*\" ? \", \" + allTypes + \"; q=0.01\" : \"\" ) :\n\t\t\t\ts.accepts[ \"*\" ]\n\t\t);\n\n\t\t// Check for headers option\n\t\tfor ( i in s.headers ) {\n\t\t\tjqXHR.setRequestHeader( i, s.headers[ i ] );\n\t\t}\n\n\t\t// Allow custom headers/mimetypes and early abort\n\t\tif ( s.beforeSend &&\n\t\t\t( s.beforeSend.call( callbackContext, jqXHR, s ) === false || completed ) ) {\n\n\t\t\t// Abort if not done already and return\n\t\t\treturn jqXHR.abort();\n\t\t}\n\n\t\t// Aborting is no longer a cancellation\n\t\tstrAbort = \"abort\";\n\n\t\t// Install callbacks on deferreds\n\t\tcompleteDeferred.add( s.complete );\n\t\tjqXHR.done( s.success );\n\t\tjqXHR.fail( s.error );\n\n\t\t// Get transport\n\t\ttransport = inspectPrefiltersOrTransports( transports, s, options, jqXHR );\n\n\t\t// If no transport, we auto-abort\n\t\tif ( !transport ) {\n\t\t\tdone( -1, \"No Transport\" );\n\t\t} else {\n\t\t\tjqXHR.readyState = 1;\n\n\t\t\t// Send global event\n\t\t\tif ( fireGlobals ) {\n\t\t\t\tglobalEventContext.trigger( \"ajaxSend\", [ jqXHR, s ] );\n\t\t\t}\n\n\t\t\t// If request was aborted inside ajaxSend, stop there\n\t\t\tif ( completed ) {\n\t\t\t\treturn jqXHR;\n\t\t\t}\n\n\t\t\t// Timeout\n\t\t\tif ( s.async && s.timeout > 0 ) {\n\t\t\t\ttimeoutTimer = window.setTimeout( function() {\n\t\t\t\t\tjqXHR.abort( \"timeout\" );\n\t\t\t\t}, s.timeout );\n\t\t\t}\n\n\t\t\ttry {\n\t\t\t\tcompleted = false;\n\t\t\t\ttransport.send( requestHeaders, done );\n\t\t\t} catch ( e ) {\n\n\t\t\t\t// Rethrow post-completion exceptions\n\t\t\t\tif ( completed ) {\n\t\t\t\t\tthrow e;\n\t\t\t\t}\n\n\t\t\t\t// Propagate others as results\n\t\t\t\tdone( -1, e );\n\t\t\t}\n\t\t}\n\n\t\t// Callback for when everything is done\n\t\tfunction done( status, nativeStatusText, responses, headers ) {\n\t\t\tvar isSuccess, success, error, response, modified,\n\t\t\t\tstatusText = nativeStatusText;\n\n\t\t\t// Ignore repeat invocations\n\t\t\tif ( completed ) {\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tcompleted = true;\n\n\t\t\t// Clear timeout if it exists\n\t\t\tif ( timeoutTimer ) {\n\t\t\t\twindow.clearTimeout( timeoutTimer );\n\t\t\t}\n\n\t\t\t// Dereference transport for early garbage collection\n\t\t\t// (no matter how long the jqXHR object will be used)\n\t\t\ttransport = undefined;\n\n\t\t\t// Cache response headers\n\t\t\tresponseHeadersString = headers || \"\";\n\n\t\t\t// Set readyState\n\t\t\tjqXHR.readyState = status > 0 ? 4 : 0;\n\n\t\t\t// Determine if successful\n\t\t\tisSuccess = status >= 200 && status < 300 || status === 304;\n\n\t\t\t// Get response data\n\t\t\tif ( responses ) {\n\t\t\t\tresponse = ajaxHandleResponses( s, jqXHR, responses );\n\t\t\t}\n\n\t\t\t// Convert no matter what (that way responseXXX fields are always set)\n\t\t\tresponse = ajaxConvert( s, response, jqXHR, isSuccess );\n\n\t\t\t// If successful, handle type chaining\n\t\t\tif ( isSuccess ) {\n\n\t\t\t\t// Set the If-Modified-Since and/or If-None-Match header, if in ifModified mode.\n\t\t\t\tif ( s.ifModified ) {\n\t\t\t\t\tmodified = jqXHR.getResponseHeader( \"Last-Modified\" );\n\t\t\t\t\tif ( modified ) {\n\t\t\t\t\t\tjQuery.lastModified[ cacheURL ] = modified;\n\t\t\t\t\t}\n\t\t\t\t\tmodified = jqXHR.getResponseHeader( \"etag\" );\n\t\t\t\t\tif ( modified ) {\n\t\t\t\t\t\tjQuery.etag[ cacheURL ] = modified;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// if no content\n\t\t\t\tif ( status === 204 || s.type === \"HEAD\" ) {\n\t\t\t\t\tstatusText = \"nocontent\";\n\n\t\t\t\t// if not modified\n\t\t\t\t} else if ( status === 304 ) {\n\t\t\t\t\tstatusText = \"notmodified\";\n\n\t\t\t\t// If we have data, let's convert it\n\t\t\t\t} else {\n\t\t\t\t\tstatusText = response.state;\n\t\t\t\t\tsuccess = response.data;\n\t\t\t\t\terror = response.error;\n\t\t\t\t\tisSuccess = !error;\n\t\t\t\t}\n\t\t\t} else {\n\n\t\t\t\t// Extract error from statusText and normalize for non-aborts\n\t\t\t\terror = statusText;\n\t\t\t\tif ( status || !statusText ) {\n\t\t\t\t\tstatusText = \"error\";\n\t\t\t\t\tif ( status < 0 ) {\n\t\t\t\t\t\tstatus = 0;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Set data for the fake xhr object\n\t\t\tjqXHR.status = status;\n\t\t\tjqXHR.statusText = ( nativeStatusText || statusText ) + \"\";\n\n\t\t\t// Success/Error\n\t\t\tif ( isSuccess ) {\n\t\t\t\tdeferred.resolveWith( callbackContext, [ success, statusText, jqXHR ] );\n\t\t\t} else {\n\t\t\t\tdeferred.rejectWith( callbackContext, [ jqXHR, statusText, error ] );\n\t\t\t}\n\n\t\t\t// Status-dependent callbacks\n\t\t\tjqXHR.statusCode( statusCode );\n\t\t\tstatusCode = undefined;\n\n\t\t\tif ( fireGlobals ) {\n\t\t\t\tglobalEventContext.trigger( isSuccess ? \"ajaxSuccess\" : \"ajaxError\",\n\t\t\t\t\t[ jqXHR, s, isSuccess ? success : error ] );\n\t\t\t}\n\n\t\t\t// Complete\n\t\t\tcompleteDeferred.fireWith( callbackContext, [ jqXHR, statusText ] );\n\n\t\t\tif ( fireGlobals ) {\n\t\t\t\tglobalEventContext.trigger( \"ajaxComplete\", [ jqXHR, s ] );\n\n\t\t\t\t// Handle the global AJAX counter\n\t\t\t\tif ( !( --jQuery.active ) ) {\n\t\t\t\t\tjQuery.event.trigger( \"ajaxStop\" );\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn jqXHR;\n\t},\n\n\tgetJSON: function( url, data, callback ) {\n\t\treturn jQuery.get( url, data, callback, \"json\" );\n\t},\n\n\tgetScript: function( url, callback ) {\n\t\treturn jQuery.get( url, undefined, callback, \"script\" );\n\t}\n} );\n\njQuery.each( [ \"get\", \"post\" ], function( i, method ) {\n\tjQuery[ method ] = function( url, data, callback, type ) {\n\n\t\t// Shift arguments if data argument was omitted\n\t\tif ( jQuery.isFunction( data ) ) {\n\t\t\ttype = type || callback;\n\t\t\tcallback = data;\n\t\t\tdata = undefined;\n\t\t}\n\n\t\t// The url can be an options object (which then must have .url)\n\t\treturn jQuery.ajax( jQuery.extend( {\n\t\t\turl: url,\n\t\t\ttype: method,\n\t\t\tdataType: type,\n\t\t\tdata: data,\n\t\t\tsuccess: callback\n\t\t}, jQuery.isPlainObject( url ) && url ) );\n\t};\n} );\n\n\njQuery._evalUrl = function( url ) {\n\treturn jQuery.ajax( {\n\t\turl: url,\n\n\t\t// Make this explicit, since user can override this through ajaxSetup (#11264)\n\t\ttype: \"GET\",\n\t\tdataType: \"script\",\n\t\tcache: true,\n\t\tasync: false,\n\t\tglobal: false,\n\t\t\"throws\": true\n\t} );\n};\n\n\njQuery.fn.extend( {\n\twrapAll: function( html ) {\n\t\tvar wrap;\n\n\t\tif ( this[ 0 ] ) {\n\t\t\tif ( jQuery.isFunction( html ) ) {\n\t\t\t\thtml = html.call( this[ 0 ] );\n\t\t\t}\n\n\t\t\t// The elements to wrap the target around\n\t\t\twrap = jQuery( html, this[ 0 ].ownerDocument ).eq( 0 ).clone( true );\n\n\t\t\tif ( this[ 0 ].parentNode ) {\n\t\t\t\twrap.insertBefore( this[ 0 ] );\n\t\t\t}\n\n\t\t\twrap.map( function() {\n\t\t\t\tvar elem = this;\n\n\t\t\t\twhile ( elem.firstElementChild ) {\n\t\t\t\t\telem = elem.firstElementChild;\n\t\t\t\t}\n\n\t\t\t\treturn elem;\n\t\t\t} ).append( this );\n\t\t}\n\n\t\treturn this;\n\t},\n\n\twrapInner: function( html ) {\n\t\tif ( jQuery.isFunction( html ) ) {\n\t\t\treturn this.each( function( i ) {\n\t\t\t\tjQuery( this ).wrapInner( html.call( this, i ) );\n\t\t\t} );\n\t\t}\n\n\t\treturn this.each( function() {\n\t\t\tvar self = jQuery( this ),\n\t\t\t\tcontents = self.contents();\n\n\t\t\tif ( contents.length ) {\n\t\t\t\tcontents.wrapAll( html );\n\n\t\t\t} else {\n\t\t\t\tself.append( html );\n\t\t\t}\n\t\t} );\n\t},\n\n\twrap: function( html ) {\n\t\tvar isFunction = jQuery.isFunction( html );\n\n\t\treturn this.each( function( i ) {\n\t\t\tjQuery( this ).wrapAll( isFunction ? html.call( this, i ) : html );\n\t\t} );\n\t},\n\n\tunwrap: function( selector ) {\n\t\tthis.parent( selector ).not( \"body\" ).each( function() {\n\t\t\tjQuery( this ).replaceWith( this.childNodes );\n\t\t} );\n\t\treturn this;\n\t}\n} );\n\n\njQuery.expr.pseudos.hidden = function( elem ) {\n\treturn !jQuery.expr.pseudos.visible( elem );\n};\njQuery.expr.pseudos.visible = function( elem ) {\n\treturn !!( elem.offsetWidth || elem.offsetHeight || elem.getClientRects().length );\n};\n\n\n\n\njQuery.ajaxSettings.xhr = function() {\n\ttry {\n\t\treturn new window.XMLHttpRequest();\n\t} catch ( e ) {}\n};\n\nvar xhrSuccessStatus = {\n\n\t\t// File protocol always yields status code 0, assume 200\n\t\t0: 200,\n\n\t\t// Support: IE <=9 only\n\t\t// #1450: sometimes IE returns 1223 when it should be 204\n\t\t1223: 204\n\t},\n\txhrSupported = jQuery.ajaxSettings.xhr();\n\nsupport.cors = !!xhrSupported && ( \"withCredentials\" in xhrSupported );\nsupport.ajax = xhrSupported = !!xhrSupported;\n\njQuery.ajaxTransport( function( options ) {\n\tvar callback, errorCallback;\n\n\t// Cross domain only allowed if supported through XMLHttpRequest\n\tif ( support.cors || xhrSupported && !options.crossDomain ) {\n\t\treturn {\n\t\t\tsend: function( headers, complete ) {\n\t\t\t\tvar i,\n\t\t\t\t\txhr = options.xhr();\n\n\t\t\t\txhr.open(\n\t\t\t\t\toptions.type,\n\t\t\t\t\toptions.url,\n\t\t\t\t\toptions.async,\n\t\t\t\t\toptions.username,\n\t\t\t\t\toptions.password\n\t\t\t\t);\n\n\t\t\t\t// Apply custom fields if provided\n\t\t\t\tif ( options.xhrFields ) {\n\t\t\t\t\tfor ( i in options.xhrFields ) {\n\t\t\t\t\t\txhr[ i ] = options.xhrFields[ i ];\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// Override mime type if needed\n\t\t\t\tif ( options.mimeType && xhr.overrideMimeType ) {\n\t\t\t\t\txhr.overrideMimeType( options.mimeType );\n\t\t\t\t}\n\n\t\t\t\t// X-Requested-With header\n\t\t\t\t// For cross-domain requests, seeing as conditions for a preflight are\n\t\t\t\t// akin to a jigsaw puzzle, we simply never set it to be sure.\n\t\t\t\t// (it can always be set on a per-request basis or even using ajaxSetup)\n\t\t\t\t// For same-domain requests, won't change header if already provided.\n\t\t\t\tif ( !options.crossDomain && !headers[ \"X-Requested-With\" ] ) {\n\t\t\t\t\theaders[ \"X-Requested-With\" ] = \"XMLHttpRequest\";\n\t\t\t\t}\n\n\t\t\t\t// Set headers\n\t\t\t\tfor ( i in headers ) {\n\t\t\t\t\txhr.setRequestHeader( i, headers[ i ] );\n\t\t\t\t}\n\n\t\t\t\t// Callback\n\t\t\t\tcallback = function( type ) {\n\t\t\t\t\treturn function() {\n\t\t\t\t\t\tif ( callback ) {\n\t\t\t\t\t\t\tcallback = errorCallback = xhr.onload =\n\t\t\t\t\t\t\t\txhr.onerror = xhr.onabort = xhr.onreadystatechange = null;\n\n\t\t\t\t\t\t\tif ( type === \"abort\" ) {\n\t\t\t\t\t\t\t\txhr.abort();\n\t\t\t\t\t\t\t} else if ( type === \"error\" ) {\n\n\t\t\t\t\t\t\t\t// Support: IE <=9 only\n\t\t\t\t\t\t\t\t// On a manual native abort, IE9 throws\n\t\t\t\t\t\t\t\t// errors on any property access that is not readyState\n\t\t\t\t\t\t\t\tif ( typeof xhr.status !== \"number\" ) {\n\t\t\t\t\t\t\t\t\tcomplete( 0, \"error\" );\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\tcomplete(\n\n\t\t\t\t\t\t\t\t\t\t// File: protocol always yields status 0; see #8605, #14207\n\t\t\t\t\t\t\t\t\t\txhr.status,\n\t\t\t\t\t\t\t\t\t\txhr.statusText\n\t\t\t\t\t\t\t\t\t);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tcomplete(\n\t\t\t\t\t\t\t\t\txhrSuccessStatus[ xhr.status ] || xhr.status,\n\t\t\t\t\t\t\t\t\txhr.statusText,\n\n\t\t\t\t\t\t\t\t\t// Support: IE <=9 only\n\t\t\t\t\t\t\t\t\t// IE9 has no XHR2 but throws on binary (trac-11426)\n\t\t\t\t\t\t\t\t\t// For XHR2 non-text, let the caller handle it (gh-2498)\n\t\t\t\t\t\t\t\t\t( xhr.responseType || \"text\" ) !== \"text\"  ||\n\t\t\t\t\t\t\t\t\ttypeof xhr.responseText !== \"string\" ?\n\t\t\t\t\t\t\t\t\t\t{ binary: xhr.response } :\n\t\t\t\t\t\t\t\t\t\t{ text: xhr.responseText },\n\t\t\t\t\t\t\t\t\txhr.getAllResponseHeaders()\n\t\t\t\t\t\t\t\t);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t};\n\t\t\t\t};\n\n\t\t\t\t// Listen to events\n\t\t\t\txhr.onload = callback();\n\t\t\t\terrorCallback = xhr.onerror = callback( \"error\" );\n\n\t\t\t\t// Support: IE 9 only\n\t\t\t\t// Use onreadystatechange to replace onabort\n\t\t\t\t// to handle uncaught aborts\n\t\t\t\tif ( xhr.onabort !== undefined ) {\n\t\t\t\t\txhr.onabort = errorCallback;\n\t\t\t\t} else {\n\t\t\t\t\txhr.onreadystatechange = function() {\n\n\t\t\t\t\t\t// Check readyState before timeout as it changes\n\t\t\t\t\t\tif ( xhr.readyState === 4 ) {\n\n\t\t\t\t\t\t\t// Allow onerror to be called first,\n\t\t\t\t\t\t\t// but that will not handle a native abort\n\t\t\t\t\t\t\t// Also, save errorCallback to a variable\n\t\t\t\t\t\t\t// as xhr.onerror cannot be accessed\n\t\t\t\t\t\t\twindow.setTimeout( function() {\n\t\t\t\t\t\t\t\tif ( callback ) {\n\t\t\t\t\t\t\t\t\terrorCallback();\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t} );\n\t\t\t\t\t\t}\n\t\t\t\t\t};\n\t\t\t\t}\n\n\t\t\t\t// Create the abort callback\n\t\t\t\tcallback = callback( \"abort\" );\n\n\t\t\t\ttry {\n\n\t\t\t\t\t// Do send the request (this may raise an exception)\n\t\t\t\t\txhr.send( options.hasContent && options.data || null );\n\t\t\t\t} catch ( e ) {\n\n\t\t\t\t\t// #14683: Only rethrow if this hasn't been notified as an error yet\n\t\t\t\t\tif ( callback ) {\n\t\t\t\t\t\tthrow e;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t},\n\n\t\t\tabort: function() {\n\t\t\t\tif ( callback ) {\n\t\t\t\t\tcallback();\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t}\n} );\n\n\n\n\n// Prevent auto-execution of scripts when no explicit dataType was provided (See gh-2432)\njQuery.ajaxPrefilter( function( s ) {\n\tif ( s.crossDomain ) {\n\t\ts.contents.script = false;\n\t}\n} );\n\n// Install script dataType\njQuery.ajaxSetup( {\n\taccepts: {\n\t\tscript: \"text/javascript, application/javascript, \" +\n\t\t\t\"application/ecmascript, application/x-ecmascript\"\n\t},\n\tcontents: {\n\t\tscript: /\\b(?:java|ecma)script\\b/\n\t},\n\tconverters: {\n\t\t\"text script\": function( text ) {\n\t\t\tjQuery.globalEval( text );\n\t\t\treturn text;\n\t\t}\n\t}\n} );\n\n// Handle cache's special case and crossDomain\njQuery.ajaxPrefilter( \"script\", function( s ) {\n\tif ( s.cache === undefined ) {\n\t\ts.cache = false;\n\t}\n\tif ( s.crossDomain ) {\n\t\ts.type = \"GET\";\n\t}\n} );\n\n// Bind script tag hack transport\njQuery.ajaxTransport( \"script\", function( s ) {\n\n\t// This transport only deals with cross domain requests\n\tif ( s.crossDomain ) {\n\t\tvar script, callback;\n\t\treturn {\n\t\t\tsend: function( _, complete ) {\n\t\t\t\tscript = jQuery( \"<script>\" ).prop( {\n\t\t\t\t\tcharset: s.scriptCharset,\n\t\t\t\t\tsrc: s.url\n\t\t\t\t} ).on(\n\t\t\t\t\t\"load error\",\n\t\t\t\t\tcallback = function( evt ) {\n\t\t\t\t\t\tscript.remove();\n\t\t\t\t\t\tcallback = null;\n\t\t\t\t\t\tif ( evt ) {\n\t\t\t\t\t\t\tcomplete( evt.type === \"error\" ? 404 : 200, evt.type );\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t);\n\n\t\t\t\t// Use native DOM manipulation to avoid our domManip AJAX trickery\n\t\t\t\tdocument.head.appendChild( script[ 0 ] );\n\t\t\t},\n\t\t\tabort: function() {\n\t\t\t\tif ( callback ) {\n\t\t\t\t\tcallback();\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t}\n} );\n\n\n\n\nvar oldCallbacks = [],\n\trjsonp = /(=)\\?(?=&|$)|\\?\\?/;\n\n// Default jsonp settings\njQuery.ajaxSetup( {\n\tjsonp: \"callback\",\n\tjsonpCallback: function() {\n\t\tvar callback = oldCallbacks.pop() || ( jQuery.expando + \"_\" + ( nonce++ ) );\n\t\tthis[ callback ] = true;\n\t\treturn callback;\n\t}\n} );\n\n// Detect, normalize options and install callbacks for jsonp requests\njQuery.ajaxPrefilter( \"json jsonp\", function( s, originalSettings, jqXHR ) {\n\n\tvar callbackName, overwritten, responseContainer,\n\t\tjsonProp = s.jsonp !== false && ( rjsonp.test( s.url ) ?\n\t\t\t\"url\" :\n\t\t\ttypeof s.data === \"string\" &&\n\t\t\t\t( s.contentType || \"\" )\n\t\t\t\t\t.indexOf( \"application/x-www-form-urlencoded\" ) === 0 &&\n\t\t\t\trjsonp.test( s.data ) && \"data\"\n\t\t);\n\n\t// Handle iff the expected data type is \"jsonp\" or we have a parameter to set\n\tif ( jsonProp || s.dataTypes[ 0 ] === \"jsonp\" ) {\n\n\t\t// Get callback name, remembering preexisting value associated with it\n\t\tcallbackName = s.jsonpCallback = jQuery.isFunction( s.jsonpCallback ) ?\n\t\t\ts.jsonpCallback() :\n\t\t\ts.jsonpCallback;\n\n\t\t// Insert callback into url or form data\n\t\tif ( jsonProp ) {\n\t\t\ts[ jsonProp ] = s[ jsonProp ].replace( rjsonp, \"$1\" + callbackName );\n\t\t} else if ( s.jsonp !== false ) {\n\t\t\ts.url += ( rquery.test( s.url ) ? \"&\" : \"?\" ) + s.jsonp + \"=\" + callbackName;\n\t\t}\n\n\t\t// Use data converter to retrieve json after script execution\n\t\ts.converters[ \"script json\" ] = function() {\n\t\t\tif ( !responseContainer ) {\n\t\t\t\tjQuery.error( callbackName + \" was not called\" );\n\t\t\t}\n\t\t\treturn responseContainer[ 0 ];\n\t\t};\n\n\t\t// Force json dataType\n\t\ts.dataTypes[ 0 ] = \"json\";\n\n\t\t// Install callback\n\t\toverwritten = window[ callbackName ];\n\t\twindow[ callbackName ] = function() {\n\t\t\tresponseContainer = arguments;\n\t\t};\n\n\t\t// Clean-up function (fires after converters)\n\t\tjqXHR.always( function() {\n\n\t\t\t// If previous value didn't exist - remove it\n\t\t\tif ( overwritten === undefined ) {\n\t\t\t\tjQuery( window ).removeProp( callbackName );\n\n\t\t\t// Otherwise restore preexisting value\n\t\t\t} else {\n\t\t\t\twindow[ callbackName ] = overwritten;\n\t\t\t}\n\n\t\t\t// Save back as free\n\t\t\tif ( s[ callbackName ] ) {\n\n\t\t\t\t// Make sure that re-using the options doesn't screw things around\n\t\t\t\ts.jsonpCallback = originalSettings.jsonpCallback;\n\n\t\t\t\t// Save the callback name for future use\n\t\t\t\toldCallbacks.push( callbackName );\n\t\t\t}\n\n\t\t\t// Call if it was a function and we have a response\n\t\t\tif ( responseContainer && jQuery.isFunction( overwritten ) ) {\n\t\t\t\toverwritten( responseContainer[ 0 ] );\n\t\t\t}\n\n\t\t\tresponseContainer = overwritten = undefined;\n\t\t} );\n\n\t\t// Delegate to script\n\t\treturn \"script\";\n\t}\n} );\n\n\n\n\n// Support: Safari 8 only\n// In Safari 8 documents created via document.implementation.createHTMLDocument\n// collapse sibling forms: the second one becomes a child of the first one.\n// Because of that, this security measure has to be disabled in Safari 8.\n// https://bugs.webkit.org/show_bug.cgi?id=137337\nsupport.createHTMLDocument = ( function() {\n\tvar body = document.implementation.createHTMLDocument( \"\" ).body;\n\tbody.innerHTML = \"<form></form><form></form>\";\n\treturn body.childNodes.length === 2;\n} )();\n\n\n// Argument \"data\" should be string of html\n// context (optional): If specified, the fragment will be created in this context,\n// defaults to document\n// keepScripts (optional): If true, will include scripts passed in the html string\njQuery.parseHTML = function( data, context, keepScripts ) {\n\tif ( typeof data !== \"string\" ) {\n\t\treturn [];\n\t}\n\tif ( typeof context === \"boolean\" ) {\n\t\tkeepScripts = context;\n\t\tcontext = false;\n\t}\n\n\tvar base, parsed, scripts;\n\n\tif ( !context ) {\n\n\t\t// Stop scripts or inline event handlers from being executed immediately\n\t\t// by using document.implementation\n\t\tif ( support.createHTMLDocument ) {\n\t\t\tcontext = document.implementation.createHTMLDocument( \"\" );\n\n\t\t\t// Set the base href for the created document\n\t\t\t// so any parsed elements with URLs\n\t\t\t// are based on the document's URL (gh-2965)\n\t\t\tbase = context.createElement( \"base\" );\n\t\t\tbase.href = document.location.href;\n\t\t\tcontext.head.appendChild( base );\n\t\t} else {\n\t\t\tcontext = document;\n\t\t}\n\t}\n\n\tparsed = rsingleTag.exec( data );\n\tscripts = !keepScripts && [];\n\n\t// Single tag\n\tif ( parsed ) {\n\t\treturn [ context.createElement( parsed[ 1 ] ) ];\n\t}\n\n\tparsed = buildFragment( [ data ], context, scripts );\n\n\tif ( scripts && scripts.length ) {\n\t\tjQuery( scripts ).remove();\n\t}\n\n\treturn jQuery.merge( [], parsed.childNodes );\n};\n\n\n/**\n * Load a url into a page\n */\njQuery.fn.load = function( url, params, callback ) {\n\tvar selector, type, response,\n\t\tself = this,\n\t\toff = url.indexOf( \" \" );\n\n\tif ( off > -1 ) {\n\t\tselector = stripAndCollapse( url.slice( off ) );\n\t\turl = url.slice( 0, off );\n\t}\n\n\t// If it's a function\n\tif ( jQuery.isFunction( params ) ) {\n\n\t\t// We assume that it's the callback\n\t\tcallback = params;\n\t\tparams = undefined;\n\n\t// Otherwise, build a param string\n\t} else if ( params && typeof params === \"object\" ) {\n\t\ttype = \"POST\";\n\t}\n\n\t// If we have elements to modify, make the request\n\tif ( self.length > 0 ) {\n\t\tjQuery.ajax( {\n\t\t\turl: url,\n\n\t\t\t// If \"type\" variable is undefined, then \"GET\" method will be used.\n\t\t\t// Make value of this field explicit since\n\t\t\t// user can override it through ajaxSetup method\n\t\t\ttype: type || \"GET\",\n\t\t\tdataType: \"html\",\n\t\t\tdata: params\n\t\t} ).done( function( responseText ) {\n\n\t\t\t// Save response for use in complete callback\n\t\t\tresponse = arguments;\n\n\t\t\tself.html( selector ?\n\n\t\t\t\t// If a selector was specified, locate the right elements in a dummy div\n\t\t\t\t// Exclude scripts to avoid IE 'Permission Denied' errors\n\t\t\t\tjQuery( \"<div>\" ).append( jQuery.parseHTML( responseText ) ).find( selector ) :\n\n\t\t\t\t// Otherwise use the full result\n\t\t\t\tresponseText );\n\n\t\t// If the request succeeds, this function gets \"data\", \"status\", \"jqXHR\"\n\t\t// but they are ignored because response was set above.\n\t\t// If it fails, this function gets \"jqXHR\", \"status\", \"error\"\n\t\t} ).always( callback && function( jqXHR, status ) {\n\t\t\tself.each( function() {\n\t\t\t\tcallback.apply( this, response || [ jqXHR.responseText, status, jqXHR ] );\n\t\t\t} );\n\t\t} );\n\t}\n\n\treturn this;\n};\n\n\n\n\n// Attach a bunch of functions for handling common AJAX events\njQuery.each( [\n\t\"ajaxStart\",\n\t\"ajaxStop\",\n\t\"ajaxComplete\",\n\t\"ajaxError\",\n\t\"ajaxSuccess\",\n\t\"ajaxSend\"\n], function( i, type ) {\n\tjQuery.fn[ type ] = function( fn ) {\n\t\treturn this.on( type, fn );\n\t};\n} );\n\n\n\n\njQuery.expr.pseudos.animated = function( elem ) {\n\treturn jQuery.grep( jQuery.timers, function( fn ) {\n\t\treturn elem === fn.elem;\n\t} ).length;\n};\n\n\n\n\n/**\n * Gets a window from an element\n */\nfunction getWindow( elem ) {\n\treturn jQuery.isWindow( elem ) ? elem : elem.nodeType === 9 && elem.defaultView;\n}\n\njQuery.offset = {\n\tsetOffset: function( elem, options, i ) {\n\t\tvar curPosition, curLeft, curCSSTop, curTop, curOffset, curCSSLeft, calculatePosition,\n\t\t\tposition = jQuery.css( elem, \"position\" ),\n\t\t\tcurElem = jQuery( elem ),\n\t\t\tprops = {};\n\n\t\t// Set position first, in-case top/left are set even on static elem\n\t\tif ( position === \"static\" ) {\n\t\t\telem.style.position = \"relative\";\n\t\t}\n\n\t\tcurOffset = curElem.offset();\n\t\tcurCSSTop = jQuery.css( elem, \"top\" );\n\t\tcurCSSLeft = jQuery.css( elem, \"left\" );\n\t\tcalculatePosition = ( position === \"absolute\" || position === \"fixed\" ) &&\n\t\t\t( curCSSTop + curCSSLeft ).indexOf( \"auto\" ) > -1;\n\n\t\t// Need to be able to calculate position if either\n\t\t// top or left is auto and position is either absolute or fixed\n\t\tif ( calculatePosition ) {\n\t\t\tcurPosition = curElem.position();\n\t\t\tcurTop = curPosition.top;\n\t\t\tcurLeft = curPosition.left;\n\n\t\t} else {\n\t\t\tcurTop = parseFloat( curCSSTop ) || 0;\n\t\t\tcurLeft = parseFloat( curCSSLeft ) || 0;\n\t\t}\n\n\t\tif ( jQuery.isFunction( options ) ) {\n\n\t\t\t// Use jQuery.extend here to allow modification of coordinates argument (gh-1848)\n\t\t\toptions = options.call( elem, i, jQuery.extend( {}, curOffset ) );\n\t\t}\n\n\t\tif ( options.top != null ) {\n\t\t\tprops.top = ( options.top - curOffset.top ) + curTop;\n\t\t}\n\t\tif ( options.left != null ) {\n\t\t\tprops.left = ( options.left - curOffset.left ) + curLeft;\n\t\t}\n\n\t\tif ( \"using\" in options ) {\n\t\t\toptions.using.call( elem, props );\n\n\t\t} else {\n\t\t\tcurElem.css( props );\n\t\t}\n\t}\n};\n\njQuery.fn.extend( {\n\toffset: function( options ) {\n\n\t\t// Preserve chaining for setter\n\t\tif ( arguments.length ) {\n\t\t\treturn options === undefined ?\n\t\t\t\tthis :\n\t\t\t\tthis.each( function( i ) {\n\t\t\t\t\tjQuery.offset.setOffset( this, options, i );\n\t\t\t\t} );\n\t\t}\n\n\t\tvar docElem, win, rect, doc,\n\t\t\telem = this[ 0 ];\n\n\t\tif ( !elem ) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Support: IE <=11 only\n\t\t// Running getBoundingClientRect on a\n\t\t// disconnected node in IE throws an error\n\t\tif ( !elem.getClientRects().length ) {\n\t\t\treturn { top: 0, left: 0 };\n\t\t}\n\n\t\trect = elem.getBoundingClientRect();\n\n\t\t// Make sure element is not hidden (display: none)\n\t\tif ( rect.width || rect.height ) {\n\t\t\tdoc = elem.ownerDocument;\n\t\t\twin = getWindow( doc );\n\t\t\tdocElem = doc.documentElement;\n\n\t\t\treturn {\n\t\t\t\ttop: rect.top + win.pageYOffset - docElem.clientTop,\n\t\t\t\tleft: rect.left + win.pageXOffset - docElem.clientLeft\n\t\t\t};\n\t\t}\n\n\t\t// Return zeros for disconnected and hidden elements (gh-2310)\n\t\treturn rect;\n\t},\n\n\tposition: function() {\n\t\tif ( !this[ 0 ] ) {\n\t\t\treturn;\n\t\t}\n\n\t\tvar offsetParent, offset,\n\t\t\telem = this[ 0 ],\n\t\t\tparentOffset = { top: 0, left: 0 };\n\n\t\t// Fixed elements are offset from window (parentOffset = {top:0, left: 0},\n\t\t// because it is its only offset parent\n\t\tif ( jQuery.css( elem, \"position\" ) === \"fixed\" ) {\n\n\t\t\t// Assume getBoundingClientRect is there when computed position is fixed\n\t\t\toffset = elem.getBoundingClientRect();\n\n\t\t} else {\n\n\t\t\t// Get *real* offsetParent\n\t\t\toffsetParent = this.offsetParent();\n\n\t\t\t// Get correct offsets\n\t\t\toffset = this.offset();\n\t\t\tif ( !jQuery.nodeName( offsetParent[ 0 ], \"html\" ) ) {\n\t\t\t\tparentOffset = offsetParent.offset();\n\t\t\t}\n\n\t\t\t// Add offsetParent borders\n\t\t\tparentOffset = {\n\t\t\t\ttop: parentOffset.top + jQuery.css( offsetParent[ 0 ], \"borderTopWidth\", true ),\n\t\t\t\tleft: parentOffset.left + jQuery.css( offsetParent[ 0 ], \"borderLeftWidth\", true )\n\t\t\t};\n\t\t}\n\n\t\t// Subtract parent offsets and element margins\n\t\treturn {\n\t\t\ttop: offset.top - parentOffset.top - jQuery.css( elem, \"marginTop\", true ),\n\t\t\tleft: offset.left - parentOffset.left - jQuery.css( elem, \"marginLeft\", true )\n\t\t};\n\t},\n\n\t// This method will return documentElement in the following cases:\n\t// 1) For the element inside the iframe without offsetParent, this method will return\n\t//    documentElement of the parent window\n\t// 2) For the hidden or detached element\n\t// 3) For body or html element, i.e. in case of the html node - it will return itself\n\t//\n\t// but those exceptions were never presented as a real life use-cases\n\t// and might be considered as more preferable results.\n\t//\n\t// This logic, however, is not guaranteed and can change at any point in the future\n\toffsetParent: function() {\n\t\treturn this.map( function() {\n\t\t\tvar offsetParent = this.offsetParent;\n\n\t\t\twhile ( offsetParent && jQuery.css( offsetParent, \"position\" ) === \"static\" ) {\n\t\t\t\toffsetParent = offsetParent.offsetParent;\n\t\t\t}\n\n\t\t\treturn offsetParent || documentElement;\n\t\t} );\n\t}\n} );\n\n// Create scrollLeft and scrollTop methods\njQuery.each( { scrollLeft: \"pageXOffset\", scrollTop: \"pageYOffset\" }, function( method, prop ) {\n\tvar top = \"pageYOffset\" === prop;\n\n\tjQuery.fn[ method ] = function( val ) {\n\t\treturn access( this, function( elem, method, val ) {\n\t\t\tvar win = getWindow( elem );\n\n\t\t\tif ( val === undefined ) {\n\t\t\t\treturn win ? win[ prop ] : elem[ method ];\n\t\t\t}\n\n\t\t\tif ( win ) {\n\t\t\t\twin.scrollTo(\n\t\t\t\t\t!top ? val : win.pageXOffset,\n\t\t\t\t\ttop ? val : win.pageYOffset\n\t\t\t\t);\n\n\t\t\t} else {\n\t\t\t\telem[ method ] = val;\n\t\t\t}\n\t\t}, method, val, arguments.length );\n\t};\n} );\n\n// Support: Safari <=7 - 9.1, Chrome <=37 - 49\n// Add the top/left cssHooks using jQuery.fn.position\n// Webkit bug: https://bugs.webkit.org/show_bug.cgi?id=29084\n// Blink bug: https://bugs.chromium.org/p/chromium/issues/detail?id=589347\n// getComputedStyle returns percent when specified for top/left/bottom/right;\n// rather than make the css module depend on the offset module, just check for it here\njQuery.each( [ \"top\", \"left\" ], function( i, prop ) {\n\tjQuery.cssHooks[ prop ] = addGetHookIf( support.pixelPosition,\n\t\tfunction( elem, computed ) {\n\t\t\tif ( computed ) {\n\t\t\t\tcomputed = curCSS( elem, prop );\n\n\t\t\t\t// If curCSS returns percentage, fallback to offset\n\t\t\t\treturn rnumnonpx.test( computed ) ?\n\t\t\t\t\tjQuery( elem ).position()[ prop ] + \"px\" :\n\t\t\t\t\tcomputed;\n\t\t\t}\n\t\t}\n\t);\n} );\n\n\n// Create innerHeight, innerWidth, height, width, outerHeight and outerWidth methods\njQuery.each( { Height: \"height\", Width: \"width\" }, function( name, type ) {\n\tjQuery.each( { padding: \"inner\" + name, content: type, \"\": \"outer\" + name },\n\t\tfunction( defaultExtra, funcName ) {\n\n\t\t// Margin is only for outerHeight, outerWidth\n\t\tjQuery.fn[ funcName ] = function( margin, value ) {\n\t\t\tvar chainable = arguments.length && ( defaultExtra || typeof margin !== \"boolean\" ),\n\t\t\t\textra = defaultExtra || ( margin === true || value === true ? \"margin\" : \"border\" );\n\n\t\t\treturn access( this, function( elem, type, value ) {\n\t\t\t\tvar doc;\n\n\t\t\t\tif ( jQuery.isWindow( elem ) ) {\n\n\t\t\t\t\t// $( window ).outerWidth/Height return w/h including scrollbars (gh-1729)\n\t\t\t\t\treturn funcName.indexOf( \"outer\" ) === 0 ?\n\t\t\t\t\t\telem[ \"inner\" + name ] :\n\t\t\t\t\t\telem.document.documentElement[ \"client\" + name ];\n\t\t\t\t}\n\n\t\t\t\t// Get document width or height\n\t\t\t\tif ( elem.nodeType === 9 ) {\n\t\t\t\t\tdoc = elem.documentElement;\n\n\t\t\t\t\t// Either scroll[Width/Height] or offset[Width/Height] or client[Width/Height],\n\t\t\t\t\t// whichever is greatest\n\t\t\t\t\treturn Math.max(\n\t\t\t\t\t\telem.body[ \"scroll\" + name ], doc[ \"scroll\" + name ],\n\t\t\t\t\t\telem.body[ \"offset\" + name ], doc[ \"offset\" + name ],\n\t\t\t\t\t\tdoc[ \"client\" + name ]\n\t\t\t\t\t);\n\t\t\t\t}\n\n\t\t\t\treturn value === undefined ?\n\n\t\t\t\t\t// Get width or height on the element, requesting but not forcing parseFloat\n\t\t\t\t\tjQuery.css( elem, type, extra ) :\n\n\t\t\t\t\t// Set width or height on the element\n\t\t\t\t\tjQuery.style( elem, type, value, extra );\n\t\t\t}, type, chainable ? margin : undefined, chainable );\n\t\t};\n\t} );\n} );\n\n\njQuery.fn.extend( {\n\n\tbind: function( types, data, fn ) {\n\t\treturn this.on( types, null, data, fn );\n\t},\n\tunbind: function( types, fn ) {\n\t\treturn this.off( types, null, fn );\n\t},\n\n\tdelegate: function( selector, types, data, fn ) {\n\t\treturn this.on( types, selector, data, fn );\n\t},\n\tundelegate: function( selector, types, fn ) {\n\n\t\t// ( namespace ) or ( selector, types [, fn] )\n\t\treturn arguments.length === 1 ?\n\t\t\tthis.off( selector, \"**\" ) :\n\t\t\tthis.off( types, selector || \"**\", fn );\n\t}\n} );\n\njQuery.parseJSON = JSON.parse;\n\n\n\n\n// Register as a named AMD module, since jQuery can be concatenated with other\n// files that may use define, but not via a proper concatenation script that\n// understands anonymous AMD modules. A named AMD is safest and most robust\n// way to register. Lowercase jquery is used because AMD module names are\n// derived from file names, and jQuery is normally delivered in a lowercase\n// file name. Do this after creating the global so that if an AMD module wants\n// to call noConflict to hide this version of jQuery, it will work.\n\n// Note that for maximum portability, libraries that are not jQuery should\n// declare themselves as anonymous modules, and avoid setting a global if an\n// AMD loader is present. jQuery is a special case. For more information, see\n// https://github.com/jrburke/requirejs/wiki/Updating-existing-libraries#wiki-anon\n\nif ( typeof define === \"function\" && define.amd ) {\n\tdefine( \"jquery\", [], function() {\n\t\treturn jQuery;\n\t} );\n}\n\n\n\n\nvar\n\n\t// Map over jQuery in case of overwrite\n\t_jQuery = window.jQuery,\n\n\t// Map over the $ in case of overwrite\n\t_$ = window.$;\n\njQuery.noConflict = function( deep ) {\n\tif ( window.$ === jQuery ) {\n\t\twindow.$ = _$;\n\t}\n\n\tif ( deep && window.jQuery === jQuery ) {\n\t\twindow.jQuery = _jQuery;\n\t}\n\n\treturn jQuery;\n};\n\n// Expose jQuery and $ identifiers, even in AMD\n// (#7102#comment:10, https://github.com/jquery/jquery/pull/557)\n// and CommonJS for browser emulators (#13566)\nif ( !noGlobal ) {\n\twindow.jQuery = window.$ = jQuery;\n}\n\n\n\n\n\nreturn jQuery;\n} );\n"
  },
  {
    "path": "public/themes/pterodactyl/vendor/lodash/lodash.js",
    "content": "/**\n * @license\n * lodash lodash.com/license | Underscore.js 1.8.3 underscorejs.org/LICENSE\n */\n;(function(){function t(t,n){return t.set(n[0],n[1]),t}function n(t,n){return t.add(n),t}function r(t,n,r){switch(r.length){case 0:return t.call(n);case 1:return t.call(n,r[0]);case 2:return t.call(n,r[0],r[1]);case 3:return t.call(n,r[0],r[1],r[2])}return t.apply(n,r)}function e(t,n,r,e){for(var u=-1,i=t?t.length:0;++u<i;){var o=t[u];n(e,o,r(o),t)}return e}function u(t,n){for(var r=-1,e=t?t.length:0;++r<e&&false!==n(t[r],r,t););return t}function i(t,n){for(var r=t?t.length:0;r--&&false!==n(t[r],r,t););\nreturn t}function o(t,n){for(var r=-1,e=t?t.length:0;++r<e;)if(!n(t[r],r,t))return false;return true}function f(t,n){for(var r=-1,e=t?t.length:0,u=0,i=[];++r<e;){var o=t[r];n(o,r,t)&&(i[u++]=o)}return i}function c(t,n){return!(!t||!t.length)&&-1<d(t,n,0)}function a(t,n,r){for(var e=-1,u=t?t.length:0;++e<u;)if(r(n,t[e]))return true;return false}function l(t,n){for(var r=-1,e=t?t.length:0,u=Array(e);++r<e;)u[r]=n(t[r],r,t);return u}function s(t,n){for(var r=-1,e=n.length,u=t.length;++r<e;)t[u+r]=n[r];return t}function h(t,n,r,e){\nvar u=-1,i=t?t.length:0;for(e&&i&&(r=t[++u]);++u<i;)r=n(r,t[u],u,t);return r}function p(t,n,r,e){var u=t?t.length:0;for(e&&u&&(r=t[--u]);u--;)r=n(r,t[u],u,t);return r}function _(t,n){for(var r=-1,e=t?t.length:0;++r<e;)if(n(t[r],r,t))return true;return false}function v(t,n,r){var e;return r(t,function(t,r,u){if(n(t,r,u))return e=r,false}),e}function g(t,n,r,e){var u=t.length;for(r+=e?1:-1;e?r--:++r<u;)if(n(t[r],r,t))return r;return-1}function d(t,n,r){if(n===n)t:{--r;for(var e=t.length;++r<e;)if(t[r]===n){t=r;\nbreak t}t=-1}else t=g(t,b,r);return t}function y(t,n,r,e){--r;for(var u=t.length;++r<u;)if(e(t[r],n))return r;return-1}function b(t){return t!==t}function x(t,n){var r=t?t.length:0;return r?k(t,n)/r:P}function j(t){return function(n){return null==n?F:n[t]}}function w(t){return function(n){return null==t?F:t[n]}}function m(t,n,r,e,u){return u(t,function(t,u,i){r=e?(e=false,t):n(r,t,u,i)}),r}function A(t,n){var r=t.length;for(t.sort(n);r--;)t[r]=t[r].c;return t}function k(t,n){for(var r,e=-1,u=t.length;++e<u;){\nvar i=n(t[e]);i!==F&&(r=r===F?i:r+i)}return r}function E(t,n){for(var r=-1,e=Array(t);++r<t;)e[r]=n(r);return e}function O(t,n){return l(n,function(n){return[n,t[n]]})}function S(t){return function(n){return t(n)}}function I(t,n){return l(n,function(n){return t[n]})}function R(t,n){return t.has(n)}function z(t,n){for(var r=-1,e=t.length;++r<e&&-1<d(n,t[r],0););return r}function W(t,n){for(var r=t.length;r--&&-1<d(n,t[r],0););return r}function B(t){return\"\\\\\"+Dt[t]}function L(t){var n=-1,r=Array(t.size);\nreturn t.forEach(function(t,e){r[++n]=[e,t]}),r}function U(t,n){return function(r){return t(n(r))}}function C(t,n){for(var r=-1,e=t.length,u=0,i=[];++r<e;){var o=t[r];o!==n&&\"__lodash_placeholder__\"!==o||(t[r]=\"__lodash_placeholder__\",i[u++]=r)}return i}function M(t){var n=-1,r=Array(t.size);return t.forEach(function(t){r[++n]=t}),r}function D(t){var n=-1,r=Array(t.size);return t.forEach(function(t){r[++n]=[t,t]}),r}function T(t){if(Wt.test(t)){for(var n=Rt.lastIndex=0;Rt.test(t);)++n;t=n}else t=tn(t);\nreturn t}function $(t){return Wt.test(t)?t.match(Rt)||[]:t.split(\"\")}var F,N=1/0,P=NaN,Z=[[\"ary\",128],[\"bind\",1],[\"bindKey\",2],[\"curry\",8],[\"curryRight\",16],[\"flip\",512],[\"partial\",32],[\"partialRight\",64],[\"rearg\",256]],q=/\\b__p\\+='';/g,V=/\\b(__p\\+=)''\\+/g,K=/(__e\\(.*?\\)|\\b__t\\))\\+'';/g,G=/&(?:amp|lt|gt|quot|#39);/g,J=/[&<>\"']/g,Y=RegExp(G.source),H=RegExp(J.source),Q=/<%-([\\s\\S]+?)%>/g,X=/<%([\\s\\S]+?)%>/g,tt=/<%=([\\s\\S]+?)%>/g,nt=/\\.|\\[(?:[^[\\]]*|([\"'])(?:(?!\\1)[^\\\\]|\\\\.)*?\\1)\\]/,rt=/^\\w*$/,et=/^\\./,ut=/[^.[\\]]+|\\[(?:(-?\\d+(?:\\.\\d+)?)|([\"'])((?:(?!\\2)[^\\\\]|\\\\.)*?)\\2)\\]|(?=(?:\\.|\\[\\])(?:\\.|\\[\\]|$))/g,it=/[\\\\^$.*+?()[\\]{}|]/g,ot=RegExp(it.source),ft=/^\\s+|\\s+$/g,ct=/^\\s+/,at=/\\s+$/,lt=/\\{(?:\\n\\/\\* \\[wrapped with .+\\] \\*\\/)?\\n?/,st=/\\{\\n\\/\\* \\[wrapped with (.+)\\] \\*/,ht=/,? & /,pt=/[^\\x00-\\x2f\\x3a-\\x40\\x5b-\\x60\\x7b-\\x7f]+/g,_t=/\\\\(\\\\)?/g,vt=/\\$\\{([^\\\\}]*(?:\\\\.[^\\\\}]*)*)\\}/g,gt=/\\w*$/,dt=/^[-+]0x[0-9a-f]+$/i,yt=/^0b[01]+$/i,bt=/^\\[object .+?Constructor\\]$/,xt=/^0o[0-7]+$/i,jt=/^(?:0|[1-9]\\d*)$/,wt=/[\\xc0-\\xd6\\xd8-\\xf6\\xf8-\\xff\\u0100-\\u017f]/g,mt=/($^)/,At=/['\\n\\r\\u2028\\u2029\\\\]/g,kt=\"[\\\\ufe0e\\\\ufe0f]?(?:[\\\\u0300-\\\\u036f\\\\ufe20-\\\\ufe23\\\\u20d0-\\\\u20f0]|\\\\ud83c[\\\\udffb-\\\\udfff])?(?:\\\\u200d(?:[^\\\\ud800-\\\\udfff]|(?:\\\\ud83c[\\\\udde6-\\\\uddff]){2}|[\\\\ud800-\\\\udbff][\\\\udc00-\\\\udfff])[\\\\ufe0e\\\\ufe0f]?(?:[\\\\u0300-\\\\u036f\\\\ufe20-\\\\ufe23\\\\u20d0-\\\\u20f0]|\\\\ud83c[\\\\udffb-\\\\udfff])?)*\",Et=\"(?:[\\\\u2700-\\\\u27bf]|(?:\\\\ud83c[\\\\udde6-\\\\uddff]){2}|[\\\\ud800-\\\\udbff][\\\\udc00-\\\\udfff])\"+kt,Ot=\"(?:[^\\\\ud800-\\\\udfff][\\\\u0300-\\\\u036f\\\\ufe20-\\\\ufe23\\\\u20d0-\\\\u20f0]?|[\\\\u0300-\\\\u036f\\\\ufe20-\\\\ufe23\\\\u20d0-\\\\u20f0]|(?:\\\\ud83c[\\\\udde6-\\\\uddff]){2}|[\\\\ud800-\\\\udbff][\\\\udc00-\\\\udfff]|[\\\\ud800-\\\\udfff])\",St=RegExp(\"['\\u2019]\",\"g\"),It=RegExp(\"[\\\\u0300-\\\\u036f\\\\ufe20-\\\\ufe23\\\\u20d0-\\\\u20f0]\",\"g\"),Rt=RegExp(\"\\\\ud83c[\\\\udffb-\\\\udfff](?=\\\\ud83c[\\\\udffb-\\\\udfff])|\"+Ot+kt,\"g\"),zt=RegExp([\"[A-Z\\\\xc0-\\\\xd6\\\\xd8-\\\\xde]?[a-z\\\\xdf-\\\\xf6\\\\xf8-\\\\xff]+(?:['\\u2019](?:d|ll|m|re|s|t|ve))?(?=[\\\\xac\\\\xb1\\\\xd7\\\\xf7\\\\x00-\\\\x2f\\\\x3a-\\\\x40\\\\x5b-\\\\x60\\\\x7b-\\\\xbf\\\\u2000-\\\\u206f \\\\t\\\\x0b\\\\f\\\\xa0\\\\ufeff\\\\n\\\\r\\\\u2028\\\\u2029\\\\u1680\\\\u180e\\\\u2000\\\\u2001\\\\u2002\\\\u2003\\\\u2004\\\\u2005\\\\u2006\\\\u2007\\\\u2008\\\\u2009\\\\u200a\\\\u202f\\\\u205f\\\\u3000]|[A-Z\\\\xc0-\\\\xd6\\\\xd8-\\\\xde]|$)|(?:[A-Z\\\\xc0-\\\\xd6\\\\xd8-\\\\xde]|[^\\\\ud800-\\\\udfff\\\\xac\\\\xb1\\\\xd7\\\\xf7\\\\x00-\\\\x2f\\\\x3a-\\\\x40\\\\x5b-\\\\x60\\\\x7b-\\\\xbf\\\\u2000-\\\\u206f \\\\t\\\\x0b\\\\f\\\\xa0\\\\ufeff\\\\n\\\\r\\\\u2028\\\\u2029\\\\u1680\\\\u180e\\\\u2000\\\\u2001\\\\u2002\\\\u2003\\\\u2004\\\\u2005\\\\u2006\\\\u2007\\\\u2008\\\\u2009\\\\u200a\\\\u202f\\\\u205f\\\\u3000\\\\d+\\\\u2700-\\\\u27bfa-z\\\\xdf-\\\\xf6\\\\xf8-\\\\xffA-Z\\\\xc0-\\\\xd6\\\\xd8-\\\\xde])+(?:['\\u2019](?:D|LL|M|RE|S|T|VE))?(?=[\\\\xac\\\\xb1\\\\xd7\\\\xf7\\\\x00-\\\\x2f\\\\x3a-\\\\x40\\\\x5b-\\\\x60\\\\x7b-\\\\xbf\\\\u2000-\\\\u206f \\\\t\\\\x0b\\\\f\\\\xa0\\\\ufeff\\\\n\\\\r\\\\u2028\\\\u2029\\\\u1680\\\\u180e\\\\u2000\\\\u2001\\\\u2002\\\\u2003\\\\u2004\\\\u2005\\\\u2006\\\\u2007\\\\u2008\\\\u2009\\\\u200a\\\\u202f\\\\u205f\\\\u3000]|[A-Z\\\\xc0-\\\\xd6\\\\xd8-\\\\xde](?:[a-z\\\\xdf-\\\\xf6\\\\xf8-\\\\xff]|[^\\\\ud800-\\\\udfff\\\\xac\\\\xb1\\\\xd7\\\\xf7\\\\x00-\\\\x2f\\\\x3a-\\\\x40\\\\x5b-\\\\x60\\\\x7b-\\\\xbf\\\\u2000-\\\\u206f \\\\t\\\\x0b\\\\f\\\\xa0\\\\ufeff\\\\n\\\\r\\\\u2028\\\\u2029\\\\u1680\\\\u180e\\\\u2000\\\\u2001\\\\u2002\\\\u2003\\\\u2004\\\\u2005\\\\u2006\\\\u2007\\\\u2008\\\\u2009\\\\u200a\\\\u202f\\\\u205f\\\\u3000\\\\d+\\\\u2700-\\\\u27bfa-z\\\\xdf-\\\\xf6\\\\xf8-\\\\xffA-Z\\\\xc0-\\\\xd6\\\\xd8-\\\\xde])|$)|[A-Z\\\\xc0-\\\\xd6\\\\xd8-\\\\xde]?(?:[a-z\\\\xdf-\\\\xf6\\\\xf8-\\\\xff]|[^\\\\ud800-\\\\udfff\\\\xac\\\\xb1\\\\xd7\\\\xf7\\\\x00-\\\\x2f\\\\x3a-\\\\x40\\\\x5b-\\\\x60\\\\x7b-\\\\xbf\\\\u2000-\\\\u206f \\\\t\\\\x0b\\\\f\\\\xa0\\\\ufeff\\\\n\\\\r\\\\u2028\\\\u2029\\\\u1680\\\\u180e\\\\u2000\\\\u2001\\\\u2002\\\\u2003\\\\u2004\\\\u2005\\\\u2006\\\\u2007\\\\u2008\\\\u2009\\\\u200a\\\\u202f\\\\u205f\\\\u3000\\\\d+\\\\u2700-\\\\u27bfa-z\\\\xdf-\\\\xf6\\\\xf8-\\\\xffA-Z\\\\xc0-\\\\xd6\\\\xd8-\\\\xde])+(?:['\\u2019](?:d|ll|m|re|s|t|ve))?|[A-Z\\\\xc0-\\\\xd6\\\\xd8-\\\\xde]+(?:['\\u2019](?:D|LL|M|RE|S|T|VE))?|\\\\d+\",Et].join(\"|\"),\"g\"),Wt=RegExp(\"[\\\\u200d\\\\ud800-\\\\udfff\\\\u0300-\\\\u036f\\\\ufe20-\\\\ufe23\\\\u20d0-\\\\u20f0\\\\ufe0e\\\\ufe0f]\"),Bt=/[a-z][A-Z]|[A-Z]{2,}[a-z]|[0-9][a-zA-Z]|[a-zA-Z][0-9]|[^a-zA-Z0-9 ]/,Lt=\"Array Buffer DataView Date Error Float32Array Float64Array Function Int8Array Int16Array Int32Array Map Math Object Promise RegExp Set String Symbol TypeError Uint8Array Uint8ClampedArray Uint16Array Uint32Array WeakMap _ clearTimeout isFinite parseInt setTimeout\".split(\" \"),Ut={};\nUt[\"[object Float32Array]\"]=Ut[\"[object Float64Array]\"]=Ut[\"[object Int8Array]\"]=Ut[\"[object Int16Array]\"]=Ut[\"[object Int32Array]\"]=Ut[\"[object Uint8Array]\"]=Ut[\"[object Uint8ClampedArray]\"]=Ut[\"[object Uint16Array]\"]=Ut[\"[object Uint32Array]\"]=true,Ut[\"[object Arguments]\"]=Ut[\"[object Array]\"]=Ut[\"[object ArrayBuffer]\"]=Ut[\"[object Boolean]\"]=Ut[\"[object DataView]\"]=Ut[\"[object Date]\"]=Ut[\"[object Error]\"]=Ut[\"[object Function]\"]=Ut[\"[object Map]\"]=Ut[\"[object Number]\"]=Ut[\"[object Object]\"]=Ut[\"[object RegExp]\"]=Ut[\"[object Set]\"]=Ut[\"[object String]\"]=Ut[\"[object WeakMap]\"]=false;\nvar Ct={};Ct[\"[object Arguments]\"]=Ct[\"[object Array]\"]=Ct[\"[object ArrayBuffer]\"]=Ct[\"[object DataView]\"]=Ct[\"[object Boolean]\"]=Ct[\"[object Date]\"]=Ct[\"[object Float32Array]\"]=Ct[\"[object Float64Array]\"]=Ct[\"[object Int8Array]\"]=Ct[\"[object Int16Array]\"]=Ct[\"[object Int32Array]\"]=Ct[\"[object Map]\"]=Ct[\"[object Number]\"]=Ct[\"[object Object]\"]=Ct[\"[object RegExp]\"]=Ct[\"[object Set]\"]=Ct[\"[object String]\"]=Ct[\"[object Symbol]\"]=Ct[\"[object Uint8Array]\"]=Ct[\"[object Uint8ClampedArray]\"]=Ct[\"[object Uint16Array]\"]=Ct[\"[object Uint32Array]\"]=true,\nCt[\"[object Error]\"]=Ct[\"[object Function]\"]=Ct[\"[object WeakMap]\"]=false;var Mt,Dt={\"\\\\\":\"\\\\\",\"'\":\"'\",\"\\n\":\"n\",\"\\r\":\"r\",\"\\u2028\":\"u2028\",\"\\u2029\":\"u2029\"},Tt=parseFloat,$t=parseInt,Ft=typeof global==\"object\"&&global&&global.Object===Object&&global,Nt=typeof self==\"object\"&&self&&self.Object===Object&&self,Pt=Ft||Nt||Function(\"return this\")(),Zt=typeof exports==\"object\"&&exports&&!exports.nodeType&&exports,qt=Zt&&typeof module==\"object\"&&module&&!module.nodeType&&module,Vt=qt&&qt.exports===Zt,Kt=Vt&&Ft.h;\nt:{try{Mt=Kt&&Kt.g(\"util\");break t}catch(t){}Mt=void 0}var Gt=Mt&&Mt.isArrayBuffer,Jt=Mt&&Mt.isDate,Yt=Mt&&Mt.isMap,Ht=Mt&&Mt.isRegExp,Qt=Mt&&Mt.isSet,Xt=Mt&&Mt.isTypedArray,tn=j(\"length\"),nn=w({\"\\xc0\":\"A\",\"\\xc1\":\"A\",\"\\xc2\":\"A\",\"\\xc3\":\"A\",\"\\xc4\":\"A\",\"\\xc5\":\"A\",\"\\xe0\":\"a\",\"\\xe1\":\"a\",\"\\xe2\":\"a\",\"\\xe3\":\"a\",\"\\xe4\":\"a\",\"\\xe5\":\"a\",\"\\xc7\":\"C\",\"\\xe7\":\"c\",\"\\xd0\":\"D\",\"\\xf0\":\"d\",\"\\xc8\":\"E\",\"\\xc9\":\"E\",\"\\xca\":\"E\",\"\\xcb\":\"E\",\"\\xe8\":\"e\",\"\\xe9\":\"e\",\"\\xea\":\"e\",\"\\xeb\":\"e\",\"\\xcc\":\"I\",\"\\xcd\":\"I\",\"\\xce\":\"I\",\"\\xcf\":\"I\",\n\"\\xec\":\"i\",\"\\xed\":\"i\",\"\\xee\":\"i\",\"\\xef\":\"i\",\"\\xd1\":\"N\",\"\\xf1\":\"n\",\"\\xd2\":\"O\",\"\\xd3\":\"O\",\"\\xd4\":\"O\",\"\\xd5\":\"O\",\"\\xd6\":\"O\",\"\\xd8\":\"O\",\"\\xf2\":\"o\",\"\\xf3\":\"o\",\"\\xf4\":\"o\",\"\\xf5\":\"o\",\"\\xf6\":\"o\",\"\\xf8\":\"o\",\"\\xd9\":\"U\",\"\\xda\":\"U\",\"\\xdb\":\"U\",\"\\xdc\":\"U\",\"\\xf9\":\"u\",\"\\xfa\":\"u\",\"\\xfb\":\"u\",\"\\xfc\":\"u\",\"\\xdd\":\"Y\",\"\\xfd\":\"y\",\"\\xff\":\"y\",\"\\xc6\":\"Ae\",\"\\xe6\":\"ae\",\"\\xde\":\"Th\",\"\\xfe\":\"th\",\"\\xdf\":\"ss\",\"\\u0100\":\"A\",\"\\u0102\":\"A\",\"\\u0104\":\"A\",\"\\u0101\":\"a\",\"\\u0103\":\"a\",\"\\u0105\":\"a\",\"\\u0106\":\"C\",\"\\u0108\":\"C\",\"\\u010a\":\"C\",\"\\u010c\":\"C\",\n\"\\u0107\":\"c\",\"\\u0109\":\"c\",\"\\u010b\":\"c\",\"\\u010d\":\"c\",\"\\u010e\":\"D\",\"\\u0110\":\"D\",\"\\u010f\":\"d\",\"\\u0111\":\"d\",\"\\u0112\":\"E\",\"\\u0114\":\"E\",\"\\u0116\":\"E\",\"\\u0118\":\"E\",\"\\u011a\":\"E\",\"\\u0113\":\"e\",\"\\u0115\":\"e\",\"\\u0117\":\"e\",\"\\u0119\":\"e\",\"\\u011b\":\"e\",\"\\u011c\":\"G\",\"\\u011e\":\"G\",\"\\u0120\":\"G\",\"\\u0122\":\"G\",\"\\u011d\":\"g\",\"\\u011f\":\"g\",\"\\u0121\":\"g\",\"\\u0123\":\"g\",\"\\u0124\":\"H\",\"\\u0126\":\"H\",\"\\u0125\":\"h\",\"\\u0127\":\"h\",\"\\u0128\":\"I\",\"\\u012a\":\"I\",\"\\u012c\":\"I\",\"\\u012e\":\"I\",\"\\u0130\":\"I\",\"\\u0129\":\"i\",\"\\u012b\":\"i\",\"\\u012d\":\"i\",\"\\u012f\":\"i\",\n\"\\u0131\":\"i\",\"\\u0134\":\"J\",\"\\u0135\":\"j\",\"\\u0136\":\"K\",\"\\u0137\":\"k\",\"\\u0138\":\"k\",\"\\u0139\":\"L\",\"\\u013b\":\"L\",\"\\u013d\":\"L\",\"\\u013f\":\"L\",\"\\u0141\":\"L\",\"\\u013a\":\"l\",\"\\u013c\":\"l\",\"\\u013e\":\"l\",\"\\u0140\":\"l\",\"\\u0142\":\"l\",\"\\u0143\":\"N\",\"\\u0145\":\"N\",\"\\u0147\":\"N\",\"\\u014a\":\"N\",\"\\u0144\":\"n\",\"\\u0146\":\"n\",\"\\u0148\":\"n\",\"\\u014b\":\"n\",\"\\u014c\":\"O\",\"\\u014e\":\"O\",\"\\u0150\":\"O\",\"\\u014d\":\"o\",\"\\u014f\":\"o\",\"\\u0151\":\"o\",\"\\u0154\":\"R\",\"\\u0156\":\"R\",\"\\u0158\":\"R\",\"\\u0155\":\"r\",\"\\u0157\":\"r\",\"\\u0159\":\"r\",\"\\u015a\":\"S\",\"\\u015c\":\"S\",\"\\u015e\":\"S\",\n\"\\u0160\":\"S\",\"\\u015b\":\"s\",\"\\u015d\":\"s\",\"\\u015f\":\"s\",\"\\u0161\":\"s\",\"\\u0162\":\"T\",\"\\u0164\":\"T\",\"\\u0166\":\"T\",\"\\u0163\":\"t\",\"\\u0165\":\"t\",\"\\u0167\":\"t\",\"\\u0168\":\"U\",\"\\u016a\":\"U\",\"\\u016c\":\"U\",\"\\u016e\":\"U\",\"\\u0170\":\"U\",\"\\u0172\":\"U\",\"\\u0169\":\"u\",\"\\u016b\":\"u\",\"\\u016d\":\"u\",\"\\u016f\":\"u\",\"\\u0171\":\"u\",\"\\u0173\":\"u\",\"\\u0174\":\"W\",\"\\u0175\":\"w\",\"\\u0176\":\"Y\",\"\\u0177\":\"y\",\"\\u0178\":\"Y\",\"\\u0179\":\"Z\",\"\\u017b\":\"Z\",\"\\u017d\":\"Z\",\"\\u017a\":\"z\",\"\\u017c\":\"z\",\"\\u017e\":\"z\",\"\\u0132\":\"IJ\",\"\\u0133\":\"ij\",\"\\u0152\":\"Oe\",\"\\u0153\":\"oe\",\"\\u0149\":\"'n\",\n\"\\u017f\":\"s\"}),rn=w({\"&\":\"&amp;\",\"<\":\"&lt;\",\">\":\"&gt;\",'\"':\"&quot;\",\"'\":\"&#39;\"}),en=w({\"&amp;\":\"&\",\"&lt;\":\"<\",\"&gt;\":\">\",\"&quot;\":'\"',\"&#39;\":\"'\"}),un=function w(kt){function Et(t){return oi.call(t)}function Ot(t){if(_u(t)&&!tf(t)&&!(t instanceof Dt)){if(t instanceof Mt)return t;if(ei.call(t,\"__wrapped__\"))return Ce(t)}return new Mt(t)}function Rt(){}function Mt(t,n){this.__wrapped__=t,this.__actions__=[],this.__chain__=!!n,this.__index__=0,this.__values__=F}function Dt(t){this.__wrapped__=t,this.__actions__=[],\nthis.__dir__=1,this.__filtered__=false,this.__iteratees__=[],this.__takeCount__=4294967295,this.__views__=[]}function Ft(t){var n=-1,r=t?t.length:0;for(this.clear();++n<r;){var e=t[n];this.set(e[0],e[1])}}function Nt(t){var n=-1,r=t?t.length:0;for(this.clear();++n<r;){var e=t[n];this.set(e[0],e[1])}}function Zt(t){var n=-1,r=t?t.length:0;for(this.clear();++n<r;){var e=t[n];this.set(e[0],e[1])}}function qt(t){var n=-1,r=t?t.length:0;for(this.__data__=new Zt;++n<r;)this.add(t[n])}function Kt(t){this.size=(this.__data__=new Nt(t)).size;\n}function tn(t,n){var r,e=tf(t)||ou(t)?E(t.length,Yu):[],u=e.length,i=!!u;for(r in t)!n&&!ei.call(t,r)||i&&(\"length\"==r||je(r,u))||e.push(r);return e}function on(t){var n=t.length;return n?t[cr(0,n-1)]:F}function fn(t,n){return We(Ur(t),n)}function cn(t){return We(Ur(t))}function an(t,n,r,e){return t===F||iu(t,Xu[r])&&!ei.call(e,r)?n:t}function ln(t,n,r){(r===F||iu(t[n],r))&&(typeof n!=\"number\"||r!==F||n in t)||vn(t,n,r)}function sn(t,n,r){var e=t[n];ei.call(t,n)&&iu(e,r)&&(r!==F||n in t)||vn(t,n,r);\n}function hn(t,n){for(var r=t.length;r--;)if(iu(t[r][0],n))return r;return-1}function pn(t,n,r,e){return to(t,function(t,u,i){n(e,t,r(t),i)}),e}function _n(t,n){return t&&Cr(n,Su(n),t)}function vn(t,n,r){\"__proto__\"==n&&pi?pi(t,n,{configurable:true,enumerable:true,value:r,writable:true}):t[n]=r}function gn(t,n){for(var r=-1,e=null==t,u=n.length,i=Pu(u);++r<u;)i[r]=e?F:Eu(t,n[r]);return i}function dn(t,n,r){return t===t&&(r!==F&&(t=t<=r?t:r),n!==F&&(t=t>=n?t:n)),t}function yn(t,n,r,e,i,o,f){var c;if(e&&(c=o?e(t,i,o,f):e(t)),\nc!==F)return c;if(!pu(t))return t;if(i=tf(t)){if(c=de(t),!n)return Ur(t,c)}else{var a=Et(t),l=\"[object Function]\"==a||\"[object GeneratorFunction]\"==a;if(rf(t))return Rr(t,n);if(\"[object Object]\"==a||\"[object Arguments]\"==a||l&&!o){if(c=ye(l?{}:t),!n)return Mr(t,_n(c,t))}else{if(!Ct[a])return o?t:{};c=be(t,a,yn,n)}}if(f||(f=new Kt),o=f.get(t))return o;if(f.set(t,c),!i)var s=r?zn(t,Su,ao):Su(t);return u(s||t,function(u,i){s&&(i=u,u=t[i]),sn(c,i,yn(u,n,r,e,i,t,f))}),c}function bn(t){var n=Su(t);return function(r){\nreturn xn(r,t,n)}}function xn(t,n,r){var e=r.length;if(null==t)return!e;for(t=Gu(t);e--;){var u=r[e],i=n[u],o=t[u];if(o===F&&!(u in t)||!i(o))return false}return true}function jn(t,n,r){if(typeof t!=\"function\")throw new Hu(\"Expected a function\");return po(function(){t.apply(F,r)},n)}function wn(t,n,r,e){var u=-1,i=c,o=true,f=t.length,s=[],h=n.length;if(!f)return s;r&&(n=l(n,S(r))),e?(i=a,o=false):200<=n.length&&(i=R,o=false,n=new qt(n));t:for(;++u<f;){var p=t[u],_=r?r(p):p,p=e||0!==p?p:0;if(o&&_===_){for(var v=h;v--;)if(n[v]===_)continue t;\ns.push(p)}else i(n,_,e)||s.push(p)}return s}function mn(t,n){var r=true;return to(t,function(t,e,u){return r=!!n(t,e,u)}),r}function An(t,n,r){for(var e=-1,u=t.length;++e<u;){var i=t[e],o=n(i);if(null!=o&&(f===F?o===o&&!yu(o):r(o,f)))var f=o,c=i}return c}function kn(t,n){var r=[];return to(t,function(t,e,u){n(t,e,u)&&r.push(t)}),r}function En(t,n,r,e,u){var i=-1,o=t.length;for(r||(r=xe),u||(u=[]);++i<o;){var f=t[i];0<n&&r(f)?1<n?En(f,n-1,r,e,u):s(u,f):e||(u[u.length]=f)}return u}function On(t,n){return t&&ro(t,n,Su);\n}function Sn(t,n){return t&&eo(t,n,Su)}function In(t,n){return f(n,function(n){return lu(t[n])})}function Rn(t,n){n=me(n,t)?[n]:Sr(n);for(var r=0,e=n.length;null!=t&&r<e;)t=t[Be(n[r++])];return r&&r==e?t:F}function zn(t,n,r){return n=n(t),tf(t)?n:s(n,r(t))}function Wn(t,n){return t>n}function Bn(t,n){return null!=t&&ei.call(t,n)}function Ln(t,n){return null!=t&&n in Gu(t)}function Un(t,n,r){for(var e=r?a:c,u=t[0].length,i=t.length,o=i,f=Pu(i),s=1/0,h=[];o--;){var p=t[o];o&&n&&(p=l(p,S(n))),s=zi(p.length,s),\nf[o]=!r&&(n||120<=u&&120<=p.length)?new qt(o&&p):F}var p=t[0],_=-1,v=f[0];t:for(;++_<u&&h.length<s;){var g=p[_],d=n?n(g):g,g=r||0!==g?g:0;if(v?!R(v,d):!e(h,d,r)){for(o=i;--o;){var y=f[o];if(y?!R(y,d):!e(t[o],d,r))continue t}v&&v.push(d),h.push(g)}}return h}function Cn(t,n,r){var e={};return On(t,function(t,u,i){n(e,r(t),u,i)}),e}function Mn(t,n,e){return me(n,t)||(n=Sr(n),t=Ie(t,n),n=Fe(n)),n=null==t?t:t[Be(n)],null==n?F:r(n,t,e)}function Dn(t){return _u(t)&&\"[object ArrayBuffer]\"==oi.call(t)}function Tn(t){\nreturn _u(t)&&\"[object Date]\"==oi.call(t)}function $n(t,n,r,e,u){if(t===n)n=true;else if(null==t||null==n||!pu(t)&&!_u(n))n=t!==t&&n!==n;else t:{var i=tf(t),o=tf(n),f=\"[object Array]\",c=\"[object Array]\";i||(f=Et(t),f=\"[object Arguments]\"==f?\"[object Object]\":f),o||(c=Et(n),c=\"[object Arguments]\"==c?\"[object Object]\":c);var a=\"[object Object]\"==f,o=\"[object Object]\"==c;if((c=f==c)&&!a)u||(u=new Kt),n=i||cf(t)?fe(t,n,$n,r,e,u):ce(t,n,f,$n,r,e,u);else{if(!(2&e)&&(i=a&&ei.call(t,\"__wrapped__\"),f=o&&ei.call(n,\"__wrapped__\"),\ni||f)){t=i?t.value():t,n=f?n.value():n,u||(u=new Kt),n=$n(t,n,r,e,u);break t}if(c)n:if(u||(u=new Kt),i=2&e,f=Su(t),o=f.length,c=Su(n).length,o==c||i){for(a=o;a--;){var l=f[a];if(!(i?l in n:ei.call(n,l))){n=false;break n}}if((c=u.get(t))&&u.get(n))n=c==n;else{c=true,u.set(t,n),u.set(n,t);for(var s=i;++a<o;){var l=f[a],h=t[l],p=n[l];if(r)var _=i?r(p,h,l,n,t,u):r(h,p,l,t,n,u);if(_===F?h!==p&&!$n(h,p,r,e,u):!_){c=false;break}s||(s=\"constructor\"==l)}c&&!s&&(r=t.constructor,e=n.constructor,r!=e&&\"constructor\"in t&&\"constructor\"in n&&!(typeof r==\"function\"&&r instanceof r&&typeof e==\"function\"&&e instanceof e)&&(c=false)),\nu.delete(t),u.delete(n),n=c}}else n=false;else n=false}}return n}function Fn(t){return _u(t)&&\"[object Map]\"==Et(t)}function Nn(t,n,r,e){var u=r.length,i=u,o=!e;if(null==t)return!i;for(t=Gu(t);u--;){var f=r[u];if(o&&f[2]?f[1]!==t[f[0]]:!(f[0]in t))return false}for(;++u<i;){var f=r[u],c=f[0],a=t[c],l=f[1];if(o&&f[2]){if(a===F&&!(c in t))return false}else{if(f=new Kt,e)var s=e(a,l,c,t,n,f);if(s===F?!$n(l,a,e,3,f):!s)return false}}return true}function Pn(t){return!(!pu(t)||ni&&ni in t)&&(lu(t)?ci:bt).test(Le(t))}function Zn(t){\nreturn pu(t)&&\"[object RegExp]\"==oi.call(t)}function qn(t){return _u(t)&&\"[object Set]\"==Et(t)}function Vn(t){return _u(t)&&hu(t.length)&&!!Ut[oi.call(t)]}function Kn(t){return typeof t==\"function\"?t:null==t?Cu:typeof t==\"object\"?tf(t)?Xn(t[0],t[1]):Qn(t):$u(t)}function Gn(t){if(!ke(t))return Ii(t);var n,r=[];for(n in Gu(t))ei.call(t,n)&&\"constructor\"!=n&&r.push(n);return r}function Jn(t){if(!pu(t)){var n=[];if(null!=t)for(var r in Gu(t))n.push(r);return n}r=ke(t);var e=[];for(n in t)(\"constructor\"!=n||!r&&ei.call(t,n))&&e.push(n);\nreturn e}function Yn(t,n){return t<n}function Hn(t,n){var r=-1,e=fu(t)?Pu(t.length):[];return to(t,function(t,u,i){e[++r]=n(t,u,i)}),e}function Qn(t){var n=_e(t);return 1==n.length&&n[0][2]?Ee(n[0][0],n[0][1]):function(r){return r===t||Nn(r,t,n)}}function Xn(t,n){return me(t)&&n===n&&!pu(n)?Ee(Be(t),n):function(r){var e=Eu(r,t);return e===F&&e===n?Ou(r,t):$n(n,e,F,3)}}function tr(t,n,r,e,i){if(t!==n){if(!tf(n)&&!cf(n))var o=Jn(n);u(o||n,function(u,f){if(o&&(f=u,u=n[f]),pu(u)){i||(i=new Kt);var c=f,a=i,l=t[c],s=n[c],h=a.get(s);\nif(h)ln(t,c,h);else{var h=e?e(l,s,c+\"\",t,n,a):F,p=h===F;p&&(h=s,tf(s)||cf(s)?tf(l)?h=l:cu(l)?h=Ur(l):(p=false,h=yn(s,true)):gu(s)||ou(s)?ou(l)?h=Au(l):!pu(l)||r&&lu(l)?(p=false,h=yn(s,true)):h=l:p=false),p&&(a.set(s,h),tr(h,s,r,e,a),a.delete(s)),ln(t,c,h)}}else c=e?e(t[f],u,f+\"\",t,n,i):F,c===F&&(c=u),ln(t,f,c)})}}function nr(t,n){var r=t.length;if(r)return n+=0>n?r:0,je(n,r)?t[n]:F}function rr(t,n,r){var e=-1;return n=l(n.length?n:[Cu],S(he())),t=Hn(t,function(t){return{a:l(n,function(n){return n(t)}),b:++e,c:t\n}}),A(t,function(t,n){var e;t:{e=-1;for(var u=t.a,i=n.a,o=u.length,f=r.length;++e<o;){var c=Wr(u[e],i[e]);if(c){e=e>=f?c:c*(\"desc\"==r[e]?-1:1);break t}}e=t.b-n.b}return e})}function er(t,n){return t=Gu(t),ur(t,n,function(n,r){return r in t})}function ur(t,n,r){for(var e=-1,u=n.length,i={};++e<u;){var o=n[e],f=t[o];r(f,o)&&vn(i,o,f)}return i}function ir(t){return function(n){return Rn(n,t)}}function or(t,n,r,e){var u=e?y:d,i=-1,o=n.length,f=t;for(t===n&&(n=Ur(n)),r&&(f=l(t,S(r)));++i<o;)for(var c=0,a=n[i],a=r?r(a):a;-1<(c=u(f,a,c,e));)f!==t&&yi.call(f,c,1),\nyi.call(t,c,1);return t}function fr(t,n){for(var r=t?n.length:0,e=r-1;r--;){var u=n[r];if(r==e||u!==i){var i=u;if(je(u))yi.call(t,u,1);else if(me(u,t))delete t[Be(u)];else{var u=Sr(u),o=Ie(t,u);null!=o&&delete o[Be(Fe(u))]}}}}function cr(t,n){return t+Ai(Li()*(n-t+1))}function ar(t,n){var r=\"\";if(!t||1>n||9007199254740991<n)return r;do n%2&&(r+=t),(n=Ai(n/2))&&(t+=t);while(n);return r}function lr(t,n){return _o(Se(t,n,Cu),t+\"\")}function sr(t){return on(zu(t))}function hr(t,n){return We(zu(t),n)}function pr(t,n,r,e){\nif(!pu(t))return t;n=me(n,t)?[n]:Sr(n);for(var u=-1,i=n.length,o=i-1,f=t;null!=f&&++u<i;){var c=Be(n[u]),a=r;if(u!=o){var l=f[c],a=e?e(l,c,f):F;a===F&&(a=pu(l)?l:je(n[u+1])?[]:{})}sn(f,c,a),f=f[c]}return t}function _r(t){return We(zu(t))}function vr(t,n,r){var e=-1,u=t.length;for(0>n&&(n=-n>u?0:u+n),r=r>u?u:r,0>r&&(r+=u),u=n>r?0:r-n>>>0,n>>>=0,r=Pu(u);++e<u;)r[e]=t[e+n];return r}function gr(t,n){var r;return to(t,function(t,e,u){return r=n(t,e,u),!r}),!!r}function dr(t,n,r){var e=0,u=t?t.length:e;\nif(typeof n==\"number\"&&n===n&&2147483647>=u){for(;e<u;){var i=e+u>>>1,o=t[i];null!==o&&!yu(o)&&(r?o<=n:o<n)?e=i+1:u=i}return u}return yr(t,n,Cu,r)}function yr(t,n,r,e){n=r(n);for(var u=0,i=t?t.length:0,o=n!==n,f=null===n,c=yu(n),a=n===F;u<i;){var l=Ai((u+i)/2),s=r(t[l]),h=s!==F,p=null===s,_=s===s,v=yu(s);(o?e||_:a?_&&(e||h):f?_&&h&&(e||!p):c?_&&h&&!p&&(e||!v):p||v?0:e?s<=n:s<n)?u=l+1:i=l}return zi(i,4294967294)}function br(t,n){for(var r=-1,e=t.length,u=0,i=[];++r<e;){var o=t[r],f=n?n(o):o;if(!r||!iu(f,c)){\nvar c=f;i[u++]=0===o?0:o}}return i}function xr(t){return typeof t==\"number\"?t:yu(t)?P:+t}function jr(t){if(typeof t==\"string\")return t;if(yu(t))return Qi?Qi.call(t):\"\";var n=t+\"\";return\"0\"==n&&1/t==-N?\"-0\":n}function wr(t,n,r){var e=-1,u=c,i=t.length,o=true,f=[],l=f;if(r)o=false,u=a;else if(200<=i){if(u=n?null:fo(t))return M(u);o=false,u=R,l=new qt}else l=n?[]:f;t:for(;++e<i;){var s=t[e],h=n?n(s):s,s=r||0!==s?s:0;if(o&&h===h){for(var p=l.length;p--;)if(l[p]===h)continue t;n&&l.push(h),f.push(s)}else u(l,h,r)||(l!==f&&l.push(h),\nf.push(s))}return f}function mr(t,n,r,e){for(var u=t.length,i=e?u:-1;(e?i--:++i<u)&&n(t[i],i,t););return r?vr(t,e?0:i,e?i+1:u):vr(t,e?i+1:0,e?u:i)}function Ar(t,n){var r=t;return r instanceof Dt&&(r=r.value()),h(n,function(t,n){return n.func.apply(n.thisArg,s([t],n.args))},r)}function kr(t,n,r){for(var e=-1,u=t.length;++e<u;)var i=i?s(wn(i,t[e],n,r),wn(t[e],i,n,r)):t[e];return i&&i.length?wr(i,n,r):[]}function Er(t,n,r){for(var e=-1,u=t.length,i=n.length,o={};++e<u;)r(o,t[e],e<i?n[e]:F);return o}\nfunction Or(t){return cu(t)?t:[]}function Sr(t){return tf(t)?t:vo(t)}function Ir(t,n,r){var e=t.length;return r=r===F?e:r,!n&&r>=e?t:vr(t,n,r)}function Rr(t,n){if(n)return t.slice();var r=t.length,r=hi?hi(r):new t.constructor(r);return t.copy(r),r}function zr(t){var n=new t.constructor(t.byteLength);return new si(n).set(new si(t)),n}function Wr(t,n){if(t!==n){var r=t!==F,e=null===t,u=t===t,i=yu(t),o=n!==F,f=null===n,c=n===n,a=yu(n);if(!f&&!a&&!i&&t>n||i&&o&&c&&!f&&!a||e&&o&&c||!r&&c||!u)return 1;if(!e&&!i&&!a&&t<n||a&&r&&u&&!e&&!i||f&&r&&u||!o&&u||!c)return-1;\n}return 0}function Br(t,n,r,e){var u=-1,i=t.length,o=r.length,f=-1,c=n.length,a=Ri(i-o,0),l=Pu(c+a);for(e=!e;++f<c;)l[f]=n[f];for(;++u<o;)(e||u<i)&&(l[r[u]]=t[u]);for(;a--;)l[f++]=t[u++];return l}function Lr(t,n,r,e){var u=-1,i=t.length,o=-1,f=r.length,c=-1,a=n.length,l=Ri(i-f,0),s=Pu(l+a);for(e=!e;++u<l;)s[u]=t[u];for(l=u;++c<a;)s[l+c]=n[c];for(;++o<f;)(e||u<i)&&(s[l+r[o]]=t[u++]);return s}function Ur(t,n){var r=-1,e=t.length;for(n||(n=Pu(e));++r<e;)n[r]=t[r];return n}function Cr(t,n,r,e){var u=!r;\nr||(r={});for(var i=-1,o=n.length;++i<o;){var f=n[i],c=e?e(r[f],t[f],f,r,t):F;c===F&&(c=t[f]),u?vn(r,f,c):sn(r,f,c)}return r}function Mr(t,n){return Cr(t,ao(t),n)}function Dr(t,n){return function(r,u){var i=tf(r)?e:pn,o=n?n():{};return i(r,t,he(u,2),o)}}function Tr(t){return lr(function(n,r){var e=-1,u=r.length,i=1<u?r[u-1]:F,o=2<u?r[2]:F,i=3<t.length&&typeof i==\"function\"?(u--,i):F;for(o&&we(r[0],r[1],o)&&(i=3>u?F:i,u=1),n=Gu(n);++e<u;)(o=r[e])&&t(n,o,e,i);return n})}function $r(t,n){return function(r,e){\nif(null==r)return r;if(!fu(r))return t(r,e);for(var u=r.length,i=n?u:-1,o=Gu(r);(n?i--:++i<u)&&false!==e(o[i],i,o););return r}}function Fr(t){return function(n,r,e){var u=-1,i=Gu(n);e=e(n);for(var o=e.length;o--;){var f=e[t?o:++u];if(false===r(i[f],f,i))break}return n}}function Nr(t,n,r){function e(){return(this&&this!==Pt&&this instanceof e?i:t).apply(u?r:this,arguments)}var u=1&n,i=qr(t);return e}function Pr(t){return function(n){n=ku(n);var r=Wt.test(n)?$(n):F,e=r?r[0]:n.charAt(0);return n=r?Ir(r,1).join(\"\"):n.slice(1),\ne[t]()+n}}function Zr(t){return function(n){return h(Lu(Bu(n).replace(St,\"\")),t,\"\")}}function qr(t){return function(){var n=arguments;switch(n.length){case 0:return new t;case 1:return new t(n[0]);case 2:return new t(n[0],n[1]);case 3:return new t(n[0],n[1],n[2]);case 4:return new t(n[0],n[1],n[2],n[3]);case 5:return new t(n[0],n[1],n[2],n[3],n[4]);case 6:return new t(n[0],n[1],n[2],n[3],n[4],n[5]);case 7:return new t(n[0],n[1],n[2],n[3],n[4],n[5],n[6])}var r=Xi(t.prototype),n=t.apply(r,n);return pu(n)?n:r;\n}}function Vr(t,n,e){function u(){for(var o=arguments.length,f=Pu(o),c=o,a=se(u);c--;)f[c]=arguments[c];return c=3>o&&f[0]!==a&&f[o-1]!==a?[]:C(f,a),o-=c.length,o<e?ee(t,n,Jr,u.placeholder,F,f,c,F,F,e-o):r(this&&this!==Pt&&this instanceof u?i:t,this,f)}var i=qr(t);return u}function Kr(t){return function(n,r,e){var u=Gu(n);if(!fu(n)){var i=he(r,3);n=Su(n),r=function(t){return i(u[t],t,u)}}return r=t(n,r,e),-1<r?u[i?n[r]:r]:F}}function Gr(t){return ae(function(n){var r=n.length,e=r,u=Mt.prototype.thru;\nfor(t&&n.reverse();e--;){var i=n[e];if(typeof i!=\"function\")throw new Hu(\"Expected a function\");if(u&&!o&&\"wrapper\"==le(i))var o=new Mt([],true)}for(e=o?e:r;++e<r;)var i=n[e],u=le(i),f=\"wrapper\"==u?co(i):F,o=f&&Ae(f[0])&&424==f[1]&&!f[4].length&&1==f[9]?o[le(f[0])].apply(o,f[3]):1==i.length&&Ae(i)?o[u]():o.thru(i);return function(){var t=arguments,e=t[0];if(o&&1==t.length&&tf(e)&&200<=e.length)return o.plant(e).value();for(var u=0,t=r?n[u].apply(this,t):e;++u<r;)t=n[u].call(this,t);return t}})}function Jr(t,n,r,e,u,i,o,f,c,a){\nfunction l(){for(var d=arguments.length,y=Pu(d),b=d;b--;)y[b]=arguments[b];if(_){var x,j=se(l),b=y.length;for(x=0;b--;)y[b]===j&&++x}if(e&&(y=Br(y,e,u,_)),i&&(y=Lr(y,i,o,_)),d-=x,_&&d<a)return j=C(y,j),ee(t,n,Jr,l.placeholder,r,y,j,f,c,a-d);if(j=h?r:this,b=p?j[t]:t,d=y.length,f){x=y.length;for(var w=zi(f.length,x),m=Ur(y);w--;){var A=f[w];y[w]=je(A,x)?m[A]:F}}else v&&1<d&&y.reverse();return s&&c<d&&(y.length=c),this&&this!==Pt&&this instanceof l&&(b=g||qr(b)),b.apply(j,y)}var s=128&n,h=1&n,p=2&n,_=24&n,v=512&n,g=p?F:qr(t);\nreturn l}function Yr(t,n){return function(r,e){return Cn(r,t,n(e))}}function Hr(t,n){return function(r,e){var u;if(r===F&&e===F)return n;if(r!==F&&(u=r),e!==F){if(u===F)return e;typeof r==\"string\"||typeof e==\"string\"?(r=jr(r),e=jr(e)):(r=xr(r),e=xr(e)),u=t(r,e)}return u}}function Qr(t){return ae(function(n){return n=l(n,S(he())),lr(function(e){var u=this;return t(n,function(t){return r(t,u,e)})})})}function Xr(t,n){n=n===F?\" \":jr(n);var r=n.length;return 2>r?r?ar(n,t):n:(r=ar(n,mi(t/T(n))),Wt.test(n)?Ir($(r),0,t).join(\"\"):r.slice(0,t));\n}function te(t,n,e,u){function i(){for(var n=-1,c=arguments.length,a=-1,l=u.length,s=Pu(l+c),h=this&&this!==Pt&&this instanceof i?f:t;++a<l;)s[a]=u[a];for(;c--;)s[a++]=arguments[++n];return r(h,o?e:this,s)}var o=1&n,f=qr(t);return i}function ne(t){return function(n,r,e){e&&typeof e!=\"number\"&&we(n,r,e)&&(r=e=F),n=xu(n),r===F?(r=n,n=0):r=xu(r),e=e===F?n<r?1:-1:xu(e);var u=-1;r=Ri(mi((r-n)/(e||1)),0);for(var i=Pu(r);r--;)i[t?r:++u]=n,n+=e;return i}}function re(t){return function(n,r){return typeof n==\"string\"&&typeof r==\"string\"||(n=mu(n),\nr=mu(r)),t(n,r)}}function ee(t,n,r,e,u,i,o,f,c,a){var l=8&n,s=l?o:F;o=l?F:o;var h=l?i:F;return i=l?F:i,n=(n|(l?32:64))&~(l?64:32),4&n||(n&=-4),u=[t,n,u,h,s,i,o,f,c,a],r=r.apply(F,u),Ae(t)&&ho(r,u),r.placeholder=e,Re(r,t,n)}function ue(t){var n=Ku[t];return function(t,r){if(t=mu(t),r=zi(ju(r),292)){var e=(ku(t)+\"e\").split(\"e\"),e=n(e[0]+\"e\"+(+e[1]+r)),e=(ku(e)+\"e\").split(\"e\");return+(e[0]+\"e\"+(+e[1]-r))}return n(t)}}function ie(t){return function(n){var r=Et(n);return\"[object Map]\"==r?L(n):\"[object Set]\"==r?D(n):O(n,t(n));\n}}function oe(t,n,r,e,u,i,o,f){var c=2&n;if(!c&&typeof t!=\"function\")throw new Hu(\"Expected a function\");var a=e?e.length:0;if(a||(n&=-97,e=u=F),o=o===F?o:Ri(ju(o),0),f=f===F?f:ju(f),a-=u?u.length:0,64&n){var l=e,s=u;e=u=F}var h=c?F:co(t);return i=[t,n,r,e,u,l,s,i,o,f],h&&(r=i[1],t=h[1],n=r|t,e=128==t&&8==r||128==t&&256==r&&i[7].length<=h[8]||384==t&&h[7].length<=h[8]&&8==r,131>n||e)&&(1&t&&(i[2]=h[2],n|=1&r?0:4),(r=h[3])&&(e=i[3],i[3]=e?Br(e,r,h[4]):r,i[4]=e?C(i[3],\"__lodash_placeholder__\"):h[4]),\n(r=h[5])&&(e=i[5],i[5]=e?Lr(e,r,h[6]):r,i[6]=e?C(i[5],\"__lodash_placeholder__\"):h[6]),(r=h[7])&&(i[7]=r),128&t&&(i[8]=null==i[8]?h[8]:zi(i[8],h[8])),null==i[9]&&(i[9]=h[9]),i[0]=h[0],i[1]=n),t=i[0],n=i[1],r=i[2],e=i[3],u=i[4],f=i[9]=null==i[9]?c?0:t.length:Ri(i[9]-a,0),!f&&24&n&&(n&=-25),Re((h?uo:ho)(n&&1!=n?8==n||16==n?Vr(t,n,f):32!=n&&33!=n||u.length?Jr.apply(F,i):te(t,n,r,e):Nr(t,n,r),i),t,n)}function fe(t,n,r,e,u,i){var o=2&u,f=t.length,c=n.length;if(f!=c&&!(o&&c>f))return false;if((c=i.get(t))&&i.get(n))return c==n;\nvar c=-1,a=true,l=1&u?new qt:F;for(i.set(t,n),i.set(n,t);++c<f;){var s=t[c],h=n[c];if(e)var p=o?e(h,s,c,n,t,i):e(s,h,c,t,n,i);if(p!==F){if(p)continue;a=false;break}if(l){if(!_(n,function(t,n){if(!R(l,n)&&(s===t||r(s,t,e,u,i)))return l.push(n)})){a=false;break}}else if(s!==h&&!r(s,h,e,u,i)){a=false;break}}return i.delete(t),i.delete(n),a}function ce(t,n,r,e,u,i,o){switch(r){case\"[object DataView]\":if(t.byteLength!=n.byteLength||t.byteOffset!=n.byteOffset)break;t=t.buffer,n=n.buffer;case\"[object ArrayBuffer]\":\nif(t.byteLength!=n.byteLength||!e(new si(t),new si(n)))break;return true;case\"[object Boolean]\":case\"[object Date]\":case\"[object Number]\":return iu(+t,+n);case\"[object Error]\":return t.name==n.name&&t.message==n.message;case\"[object RegExp]\":case\"[object String]\":return t==n+\"\";case\"[object Map]\":var f=L;case\"[object Set]\":if(f||(f=M),t.size!=n.size&&!(2&i))break;return(r=o.get(t))?r==n:(i|=1,o.set(t,n),n=fe(f(t),f(n),e,u,i,o),o.delete(t),n);case\"[object Symbol]\":if(Hi)return Hi.call(t)==Hi.call(n)}\nreturn false}function ae(t){return _o(Se(t,F,Te),t+\"\")}function le(t){for(var n=t.name+\"\",r=Zi[n],e=ei.call(Zi,n)?r.length:0;e--;){var u=r[e],i=u.func;if(null==i||i==t)return u.name}return n}function se(t){return(ei.call(Ot,\"placeholder\")?Ot:t).placeholder}function he(){var t=Ot.iteratee||Mu,t=t===Mu?Kn:t;return arguments.length?t(arguments[0],arguments[1]):t}function pe(t,n){var r=t.__data__,e=typeof n;return(\"string\"==e||\"number\"==e||\"symbol\"==e||\"boolean\"==e?\"__proto__\"!==n:null===n)?r[typeof n==\"string\"?\"string\":\"hash\"]:r.map;\n}function _e(t){for(var n=Su(t),r=n.length;r--;){var e=n[r],u=t[e];n[r]=[e,u,u===u&&!pu(u)]}return n}function ve(t,n){var r=null==t?F:t[n];return Pn(r)?r:F}function ge(t,n,r){n=me(n,t)?[n]:Sr(n);for(var e=-1,u=n.length,i=false;++e<u;){var o=Be(n[e]);if(!(i=null!=t&&r(t,o)))break;t=t[o]}return i||++e!=u?i:(u=t?t.length:0,!!u&&hu(u)&&je(o,u)&&(tf(t)||ou(t)))}function de(t){var n=t.length,r=t.constructor(n);return n&&\"string\"==typeof t[0]&&ei.call(t,\"index\")&&(r.index=t.index,r.input=t.input),r}function ye(t){\nreturn typeof t.constructor!=\"function\"||ke(t)?{}:Xi(_i(t))}function be(r,e,u,i){var o=r.constructor;switch(e){case\"[object ArrayBuffer]\":return zr(r);case\"[object Boolean]\":case\"[object Date]\":return new o(+r);case\"[object DataView]\":return e=i?zr(r.buffer):r.buffer,new r.constructor(e,r.byteOffset,r.byteLength);case\"[object Float32Array]\":case\"[object Float64Array]\":case\"[object Int8Array]\":case\"[object Int16Array]\":case\"[object Int32Array]\":case\"[object Uint8Array]\":case\"[object Uint8ClampedArray]\":\ncase\"[object Uint16Array]\":case\"[object Uint32Array]\":return e=i?zr(r.buffer):r.buffer,new r.constructor(e,r.byteOffset,r.length);case\"[object Map]\":return e=i?u(L(r),true):L(r),h(e,t,new r.constructor);case\"[object Number]\":case\"[object String]\":return new o(r);case\"[object RegExp]\":return e=new r.constructor(r.source,gt.exec(r)),e.lastIndex=r.lastIndex,e;case\"[object Set]\":return e=i?u(M(r),true):M(r),h(e,n,new r.constructor);case\"[object Symbol]\":return Hi?Gu(Hi.call(r)):{}}}function xe(t){return tf(t)||ou(t)||!!(bi&&t&&t[bi]);\n}function je(t,n){return n=null==n?9007199254740991:n,!!n&&(typeof t==\"number\"||jt.test(t))&&-1<t&&0==t%1&&t<n}function we(t,n,r){if(!pu(r))return false;var e=typeof n;return!!(\"number\"==e?fu(r)&&je(n,r.length):\"string\"==e&&n in r)&&iu(r[n],t)}function me(t,n){if(tf(t))return false;var r=typeof t;return!(\"number\"!=r&&\"symbol\"!=r&&\"boolean\"!=r&&null!=t&&!yu(t))||(rt.test(t)||!nt.test(t)||null!=n&&t in Gu(n))}function Ae(t){var n=le(t),r=Ot[n];return typeof r==\"function\"&&n in Dt.prototype&&(t===r||(n=co(r),\n!!n&&t===n[0]))}function ke(t){var n=t&&t.constructor;return t===(typeof n==\"function\"&&n.prototype||Xu)}function Ee(t,n){return function(r){return null!=r&&(r[t]===n&&(n!==F||t in Gu(r)))}}function Oe(t,n,r,e,u,i){return pu(t)&&pu(n)&&(i.set(n,t),tr(t,n,F,Oe,i),i.delete(n)),t}function Se(t,n,e){return n=Ri(n===F?t.length-1:n,0),function(){for(var u=arguments,i=-1,o=Ri(u.length-n,0),f=Pu(o);++i<o;)f[i]=u[n+i];for(i=-1,o=Pu(n+1);++i<n;)o[i]=u[i];return o[n]=e(f),r(t,this,o)}}function Ie(t,n){return 1==n.length?t:Rn(t,vr(n,0,-1));\n}function Re(t,n,r){var e=n+\"\";n=_o;var u,i=Ue;return u=(u=e.match(st))?u[1].split(ht):[],r=i(u,r),(i=r.length)&&(u=i-1,r[u]=(1<i?\"& \":\"\")+r[u],r=r.join(2<i?\", \":\" \"),e=e.replace(lt,\"{\\n/* [wrapped with \"+r+\"] */\\n\")),n(t,e)}function ze(t){var n=0,r=0;return function(){var e=Wi(),u=16-(e-r);if(r=e,0<u){if(500<=++n)return arguments[0]}else n=0;return t.apply(F,arguments)}}function We(t,n){var r=-1,e=t.length,u=e-1;for(n=n===F?e:dn(n,0,e);++r<n;){var e=cr(r,u),i=t[e];t[e]=t[r],t[r]=i}return t.length=n,\nt}function Be(t){if(typeof t==\"string\"||yu(t))return t;var n=t+\"\";return\"0\"==n&&1/t==-N?\"-0\":n}function Le(t){if(null!=t){try{return ri.call(t)}catch(t){}return t+\"\"}return\"\"}function Ue(t,n){return u(Z,function(r){var e=\"_.\"+r[0];n&r[1]&&!c(t,e)&&t.push(e)}),t.sort()}function Ce(t){if(t instanceof Dt)return t.clone();var n=new Mt(t.__wrapped__,t.__chain__);return n.__actions__=Ur(t.__actions__),n.__index__=t.__index__,n.__values__=t.__values__,n}function Me(t,n,r){var e=t?t.length:0;return e?(r=null==r?0:ju(r),\n0>r&&(r=Ri(e+r,0)),g(t,he(n,3),r)):-1}function De(t,n,r){var e=t?t.length:0;if(!e)return-1;var u=e-1;return r!==F&&(u=ju(r),u=0>r?Ri(e+u,0):zi(u,e-1)),g(t,he(n,3),u,true)}function Te(t){return t&&t.length?En(t,1):[]}function $e(t){return t&&t.length?t[0]:F}function Fe(t){var n=t?t.length:0;return n?t[n-1]:F}function Ne(t,n){return t&&t.length&&n&&n.length?or(t,n):t}function Pe(t){return t?Ui.call(t):t}function Ze(t){if(!t||!t.length)return[];var n=0;return t=f(t,function(t){if(cu(t))return n=Ri(t.length,n),\n!0}),E(n,function(n){return l(t,j(n))})}function qe(t,n){if(!t||!t.length)return[];var e=Ze(t);return null==n?e:l(e,function(t){return r(n,F,t)})}function Ve(t){return t=Ot(t),t.__chain__=true,t}function Ke(t,n){return n(t)}function Ge(){return this}function Je(t,n){return(tf(t)?u:to)(t,he(n,3))}function Ye(t,n){return(tf(t)?i:no)(t,he(n,3))}function He(t,n){return(tf(t)?l:Hn)(t,he(n,3))}function Qe(t,n,r){return n=r?F:n,n=t&&null==n?t.length:n,oe(t,128,F,F,F,F,n)}function Xe(t,n){var r;if(typeof n!=\"function\")throw new Hu(\"Expected a function\");\nreturn t=ju(t),function(){return 0<--t&&(r=n.apply(this,arguments)),1>=t&&(n=F),r}}function tu(t,n,r){return n=r?F:n,t=oe(t,8,F,F,F,F,F,n),t.placeholder=tu.placeholder,t}function nu(t,n,r){return n=r?F:n,t=oe(t,16,F,F,F,F,F,n),t.placeholder=nu.placeholder,t}function ru(t,n,r){function e(n){var r=c,e=a;return c=a=F,_=n,s=t.apply(e,r)}function u(t){var r=t-p;return t-=_,p===F||r>=n||0>r||g&&t>=l}function i(){var t=Po();if(u(t))return o(t);var r,e=po;r=t-_,t=n-(t-p),r=g?zi(t,l-r):t,h=e(i,r)}function o(t){\nreturn h=F,d&&c?e(t):(c=a=F,s)}function f(){var t=Po(),r=u(t);if(c=arguments,a=this,p=t,r){if(h===F)return _=t=p,h=po(i,n),v?e(t):s;if(g)return h=po(i,n),e(p)}return h===F&&(h=po(i,n)),s}var c,a,l,s,h,p,_=0,v=false,g=false,d=true;if(typeof t!=\"function\")throw new Hu(\"Expected a function\");return n=mu(n)||0,pu(r)&&(v=!!r.leading,l=(g=\"maxWait\"in r)?Ri(mu(r.maxWait)||0,n):l,d=\"trailing\"in r?!!r.trailing:d),f.cancel=function(){h!==F&&oo(h),_=0,c=p=a=h=F},f.flush=function(){return h===F?s:o(Po())},f}function eu(t,n){\nfunction r(){var e=arguments,u=n?n.apply(this,e):e[0],i=r.cache;return i.has(u)?i.get(u):(e=t.apply(this,e),r.cache=i.set(u,e)||i,e)}if(typeof t!=\"function\"||n&&typeof n!=\"function\")throw new Hu(\"Expected a function\");return r.cache=new(eu.Cache||Zt),r}function uu(t){if(typeof t!=\"function\")throw new Hu(\"Expected a function\");return function(){var n=arguments;switch(n.length){case 0:return!t.call(this);case 1:return!t.call(this,n[0]);case 2:return!t.call(this,n[0],n[1]);case 3:return!t.call(this,n[0],n[1],n[2]);\n}return!t.apply(this,n)}}function iu(t,n){return t===n||t!==t&&n!==n}function ou(t){return cu(t)&&ei.call(t,\"callee\")&&(!di.call(t,\"callee\")||\"[object Arguments]\"==oi.call(t))}function fu(t){return null!=t&&hu(t.length)&&!lu(t)}function cu(t){return _u(t)&&fu(t)}function au(t){return!!_u(t)&&(\"[object Error]\"==oi.call(t)||typeof t.message==\"string\"&&typeof t.name==\"string\")}function lu(t){return t=pu(t)?oi.call(t):\"\",\"[object Function]\"==t||\"[object GeneratorFunction]\"==t}function su(t){return typeof t==\"number\"&&t==ju(t);\n}function hu(t){return typeof t==\"number\"&&-1<t&&0==t%1&&9007199254740991>=t}function pu(t){var n=typeof t;return null!=t&&(\"object\"==n||\"function\"==n)}function _u(t){return null!=t&&typeof t==\"object\"}function vu(t){return typeof t==\"number\"||_u(t)&&\"[object Number]\"==oi.call(t)}function gu(t){return!(!_u(t)||\"[object Object]\"!=oi.call(t))&&(t=_i(t),null===t||(t=ei.call(t,\"constructor\")&&t.constructor,typeof t==\"function\"&&t instanceof t&&ri.call(t)==ii))}function du(t){return typeof t==\"string\"||!tf(t)&&_u(t)&&\"[object String]\"==oi.call(t);\n}function yu(t){return typeof t==\"symbol\"||_u(t)&&\"[object Symbol]\"==oi.call(t)}function bu(t){if(!t)return[];if(fu(t))return du(t)?$(t):Ur(t);if(vi&&t[vi]){t=t[vi]();for(var n,r=[];!(n=t.next()).done;)r.push(n.value);return r}return n=Et(t),(\"[object Map]\"==n?L:\"[object Set]\"==n?M:zu)(t)}function xu(t){return t?(t=mu(t),t===N||t===-N?1.7976931348623157e308*(0>t?-1:1):t===t?t:0):0===t?t:0}function ju(t){t=xu(t);var n=t%1;return t===t?n?t-n:t:0}function wu(t){return t?dn(ju(t),0,4294967295):0}function mu(t){\nif(typeof t==\"number\")return t;if(yu(t))return P;if(pu(t)&&(t=typeof t.valueOf==\"function\"?t.valueOf():t,t=pu(t)?t+\"\":t),typeof t!=\"string\")return 0===t?t:+t;t=t.replace(ft,\"\");var n=yt.test(t);return n||xt.test(t)?$t(t.slice(2),n?2:8):dt.test(t)?P:+t}function Au(t){return Cr(t,Iu(t))}function ku(t){return null==t?\"\":jr(t)}function Eu(t,n,r){return t=null==t?F:Rn(t,n),t===F?r:t}function Ou(t,n){return null!=t&&ge(t,n,Ln)}function Su(t){return fu(t)?tn(t):Gn(t)}function Iu(t){return fu(t)?tn(t,true):Jn(t);\n}function Ru(t,n){return null==t?{}:ur(t,zn(t,Iu,lo),he(n))}function zu(t){return t?I(t,Su(t)):[]}function Wu(t){return Lf(ku(t).toLowerCase())}function Bu(t){return(t=ku(t))&&t.replace(wt,nn).replace(It,\"\")}function Lu(t,n,r){return t=ku(t),n=r?F:n,n===F?Bt.test(t)?t.match(zt)||[]:t.match(pt)||[]:t.match(n)||[]}function Uu(t){return function(){return t}}function Cu(t){return t}function Mu(t){return Kn(typeof t==\"function\"?t:yn(t,true))}function Du(t,n,r){var e=Su(n),i=In(n,e);null!=r||pu(n)&&(i.length||!e.length)||(r=n,\nn=t,t=this,i=In(n,Su(n)));var o=!(pu(r)&&\"chain\"in r&&!r.chain),f=lu(t);return u(i,function(r){var e=n[r];t[r]=e,f&&(t.prototype[r]=function(){var n=this.__chain__;if(o||n){var r=t(this.__wrapped__);return(r.__actions__=Ur(this.__actions__)).push({func:e,args:arguments,thisArg:t}),r.__chain__=n,r}return e.apply(t,s([this.value()],arguments))})}),t}function Tu(){}function $u(t){return me(t)?j(Be(t)):ir(t)}function Fu(){return[]}function Nu(){return false}kt=kt?un.defaults(Pt.Object(),kt,un.pick(Pt,Lt)):Pt;\nvar Pu=kt.Array,Zu=kt.Date,qu=kt.Error,Vu=kt.Function,Ku=kt.Math,Gu=kt.Object,Ju=kt.RegExp,Yu=kt.String,Hu=kt.TypeError,Qu=Pu.prototype,Xu=Gu.prototype,ti=kt[\"__core-js_shared__\"],ni=function(){var t=/[^.]+$/.exec(ti&&ti.keys&&ti.keys.IE_PROTO||\"\");return t?\"Symbol(src)_1.\"+t:\"\"}(),ri=Vu.prototype.toString,ei=Xu.hasOwnProperty,ui=0,ii=ri.call(Gu),oi=Xu.toString,fi=Pt._,ci=Ju(\"^\"+ri.call(ei).replace(it,\"\\\\$&\").replace(/hasOwnProperty|(function).*?(?=\\\\\\()| for .+?(?=\\\\\\])/g,\"$1.*?\")+\"$\"),ai=Vt?kt.Buffer:F,li=kt.Symbol,si=kt.Uint8Array,hi=ai?ai.f:F,pi=Gu.defineProperty,_i=U(Gu.getPrototypeOf,Gu),vi=li?li.iterator:F,gi=Gu.create,di=Xu.propertyIsEnumerable,yi=Qu.splice,bi=li?li.isConcatSpreadable:F,xi=kt.clearTimeout!==Pt.clearTimeout&&kt.clearTimeout,ji=Zu&&Zu.now!==Pt.Date.now&&Zu.now,wi=kt.setTimeout!==Pt.setTimeout&&kt.setTimeout,mi=Ku.ceil,Ai=Ku.floor,ki=Gu.getOwnPropertySymbols,Ei=ai?ai.isBuffer:F,Oi=kt.isFinite,Si=Qu.join,Ii=U(Gu.keys,Gu),Ri=Ku.max,zi=Ku.min,Wi=Zu.now,Bi=kt.parseInt,Li=Ku.random,Ui=Qu.reverse,Ci=ve(kt,\"DataView\"),Mi=ve(kt,\"Map\"),Di=ve(kt,\"Promise\"),Ti=ve(kt,\"Set\"),$i=ve(kt,\"WeakMap\"),Fi=ve(Gu,\"create\"),Ni=ve(Gu,\"defineProperty\"),Pi=$i&&new $i,Zi={},qi=Le(Ci),Vi=Le(Mi),Ki=Le(Di),Gi=Le(Ti),Ji=Le($i),Yi=li?li.prototype:F,Hi=Yi?Yi.valueOf:F,Qi=Yi?Yi.toString:F,Xi=function(){\nfunction t(){}return function(n){return pu(n)?gi?gi(n):(t.prototype=prototype,n=new t,t.prototype=F,n):{}}}();Ot.templateSettings={escape:Q,evaluate:X,interpolate:tt,variable:\"\",imports:{_:Ot}},Ot.prototype=Rt.prototype,Ot.prototype.constructor=Ot,Mt.prototype=Xi(Rt.prototype),Mt.prototype.constructor=Mt,Dt.prototype=Xi(Rt.prototype),Dt.prototype.constructor=Dt,Ft.prototype.clear=function(){this.__data__=Fi?Fi(null):{},this.size=0},Ft.prototype.delete=function(t){return t=this.has(t)&&delete this.__data__[t],\nthis.size-=t?1:0,t},Ft.prototype.get=function(t){var n=this.__data__;return Fi?(t=n[t],\"__lodash_hash_undefined__\"===t?F:t):ei.call(n,t)?n[t]:F},Ft.prototype.has=function(t){var n=this.__data__;return Fi?n[t]!==F:ei.call(n,t)},Ft.prototype.set=function(t,n){var r=this.__data__;return this.size+=this.has(t)?0:1,r[t]=Fi&&n===F?\"__lodash_hash_undefined__\":n,this},Nt.prototype.clear=function(){this.__data__=[],this.size=0},Nt.prototype.delete=function(t){var n=this.__data__;return t=hn(n,t),!(0>t)&&(t==n.length-1?n.pop():yi.call(n,t,1),\n--this.size,true)},Nt.prototype.get=function(t){var n=this.__data__;return t=hn(n,t),0>t?F:n[t][1]},Nt.prototype.has=function(t){return-1<hn(this.__data__,t)},Nt.prototype.set=function(t,n){var r=this.__data__,e=hn(r,t);return 0>e?(++this.size,r.push([t,n])):r[e][1]=n,this},Zt.prototype.clear=function(){this.size=0,this.__data__={hash:new Ft,map:new(Mi||Nt),string:new Ft}},Zt.prototype.delete=function(t){return t=pe(this,t).delete(t),this.size-=t?1:0,t},Zt.prototype.get=function(t){return pe(this,t).get(t);\n},Zt.prototype.has=function(t){return pe(this,t).has(t)},Zt.prototype.set=function(t,n){var r=pe(this,t),e=r.size;return r.set(t,n),this.size+=r.size==e?0:1,this},qt.prototype.add=qt.prototype.push=function(t){return this.__data__.set(t,\"__lodash_hash_undefined__\"),this},qt.prototype.has=function(t){return this.__data__.has(t)},Kt.prototype.clear=function(){this.__data__=new Nt,this.size=0},Kt.prototype.delete=function(t){var n=this.__data__;return t=n.delete(t),this.size=n.size,t},Kt.prototype.get=function(t){\nreturn this.__data__.get(t)},Kt.prototype.has=function(t){return this.__data__.has(t)},Kt.prototype.set=function(t,n){var r=this.__data__;if(r instanceof Nt){var e=r.__data__;if(!Mi||199>e.length)return e.push([t,n]),this.size=++r.size,this;r=this.__data__=new Zt(e)}return r.set(t,n),this.size=r.size,this};var to=$r(On),no=$r(Sn,true),ro=Fr(),eo=Fr(true),uo=Pi?function(t,n){return Pi.set(t,n),t}:Cu,io=Ni?function(t,n){return Ni(t,\"toString\",{configurable:true,enumerable:false,value:Uu(n),writable:true})}:Cu,oo=xi||function(t){\nreturn Pt.clearTimeout(t)},fo=Ti&&1/M(new Ti([,-0]))[1]==N?function(t){return new Ti(t)}:Tu,co=Pi?function(t){return Pi.get(t)}:Tu,ao=ki?U(ki,Gu):Fu,lo=ki?function(t){for(var n=[];t;)s(n,ao(t)),t=_i(t);return n}:Fu;(Ci&&\"[object DataView]\"!=Et(new Ci(new ArrayBuffer(1)))||Mi&&\"[object Map]\"!=Et(new Mi)||Di&&\"[object Promise]\"!=Et(Di.resolve())||Ti&&\"[object Set]\"!=Et(new Ti)||$i&&\"[object WeakMap]\"!=Et(new $i))&&(Et=function(t){var n=oi.call(t);if(t=(t=\"[object Object]\"==n?t.constructor:F)?Le(t):F)switch(t){\ncase qi:return\"[object DataView]\";case Vi:return\"[object Map]\";case Ki:return\"[object Promise]\";case Gi:return\"[object Set]\";case Ji:return\"[object WeakMap]\"}return n});var so=ti?lu:Nu,ho=ze(uo),po=wi||function(t,n){return Pt.setTimeout(t,n)},_o=ze(io),vo=function(t){t=eu(t,function(t){return 500===n.size&&n.clear(),t});var n=t.cache;return t}(function(t){t=ku(t);var n=[];return et.test(t)&&n.push(\"\"),t.replace(ut,function(t,r,e,u){n.push(e?u.replace(_t,\"$1\"):r||t)}),n}),go=lr(function(t,n){return cu(t)?wn(t,En(n,1,cu,true)):[];\n}),yo=lr(function(t,n){var r=Fe(n);return cu(r)&&(r=F),cu(t)?wn(t,En(n,1,cu,true),he(r,2)):[]}),bo=lr(function(t,n){var r=Fe(n);return cu(r)&&(r=F),cu(t)?wn(t,En(n,1,cu,true),F,r):[]}),xo=lr(function(t){var n=l(t,Or);return n.length&&n[0]===t[0]?Un(n):[]}),jo=lr(function(t){var n=Fe(t),r=l(t,Or);return n===Fe(r)?n=F:r.pop(),r.length&&r[0]===t[0]?Un(r,he(n,2)):[]}),wo=lr(function(t){var n=Fe(t),r=l(t,Or);return n===Fe(r)?n=F:r.pop(),r.length&&r[0]===t[0]?Un(r,F,n):[]}),mo=lr(Ne),Ao=ae(function(t,n){var r=t?t.length:0,e=gn(t,n);\nreturn fr(t,l(n,function(t){return je(t,r)?+t:t}).sort(Wr)),e}),ko=lr(function(t){return wr(En(t,1,cu,true))}),Eo=lr(function(t){var n=Fe(t);return cu(n)&&(n=F),wr(En(t,1,cu,true),he(n,2))}),Oo=lr(function(t){var n=Fe(t);return cu(n)&&(n=F),wr(En(t,1,cu,true),F,n)}),So=lr(function(t,n){return cu(t)?wn(t,n):[]}),Io=lr(function(t){return kr(f(t,cu))}),Ro=lr(function(t){var n=Fe(t);return cu(n)&&(n=F),kr(f(t,cu),he(n,2))}),zo=lr(function(t){var n=Fe(t);return cu(n)&&(n=F),kr(f(t,cu),F,n)}),Wo=lr(Ze),Bo=lr(function(t){\nvar n=t.length,n=1<n?t[n-1]:F,n=typeof n==\"function\"?(t.pop(),n):F;return qe(t,n)}),Lo=ae(function(t){function n(n){return gn(n,t)}var r=t.length,e=r?t[0]:0,u=this.__wrapped__;return!(1<r||this.__actions__.length)&&u instanceof Dt&&je(e)?(u=u.slice(e,+e+(r?1:0)),u.__actions__.push({func:Ke,args:[n],thisArg:F}),new Mt(u,this.__chain__).thru(function(t){return r&&!t.length&&t.push(F),t})):this.thru(n)}),Uo=Dr(function(t,n,r){ei.call(t,r)?++t[r]:vn(t,r,1)}),Co=Kr(Me),Mo=Kr(De),Do=Dr(function(t,n,r){\nei.call(t,r)?t[r].push(n):vn(t,r,[n])}),To=lr(function(t,n,e){var u=-1,i=typeof n==\"function\",o=me(n),f=fu(t)?Pu(t.length):[];return to(t,function(t){var c=i?n:o&&null!=t?t[n]:F;f[++u]=c?r(c,t,e):Mn(t,n,e)}),f}),$o=Dr(function(t,n,r){vn(t,r,n)}),Fo=Dr(function(t,n,r){t[r?0:1].push(n)},function(){return[[],[]]}),No=lr(function(t,n){if(null==t)return[];var r=n.length;return 1<r&&we(t,n[0],n[1])?n=[]:2<r&&we(n[0],n[1],n[2])&&(n=[n[0]]),rr(t,En(n,1),[])}),Po=ji||function(){return Pt.Date.now()},Zo=lr(function(t,n,r){\nvar e=1;if(r.length)var u=C(r,se(Zo)),e=32|e;return oe(t,e,n,r,u)}),qo=lr(function(t,n,r){var e=3;if(r.length)var u=C(r,se(qo)),e=32|e;return oe(n,e,t,r,u)}),Vo=lr(function(t,n){return jn(t,1,n)}),Ko=lr(function(t,n,r){return jn(t,mu(n)||0,r)});eu.Cache=Zt;var Go=lr(function(t,n){n=1==n.length&&tf(n[0])?l(n[0],S(he())):l(En(n,1),S(he()));var e=n.length;return lr(function(u){for(var i=-1,o=zi(u.length,e);++i<o;)u[i]=n[i].call(this,u[i]);return r(t,this,u)})}),Jo=lr(function(t,n){return oe(t,32,F,n,C(n,se(Jo)));\n}),Yo=lr(function(t,n){return oe(t,64,F,n,C(n,se(Yo)))}),Ho=ae(function(t,n){return oe(t,256,F,F,F,n)}),Qo=re(Wn),Xo=re(function(t,n){return t>=n}),tf=Pu.isArray,nf=Gt?S(Gt):Dn,rf=Ei||Nu,ef=Jt?S(Jt):Tn,uf=Yt?S(Yt):Fn,of=Ht?S(Ht):Zn,ff=Qt?S(Qt):qn,cf=Xt?S(Xt):Vn,af=re(Yn),lf=re(function(t,n){return t<=n}),sf=Tr(function(t,n){if(ke(n)||fu(n))Cr(n,Su(n),t);else for(var r in n)ei.call(n,r)&&sn(t,r,n[r])}),hf=Tr(function(t,n){Cr(n,Iu(n),t)}),pf=Tr(function(t,n,r,e){Cr(n,Iu(n),t,e)}),_f=Tr(function(t,n,r,e){\nCr(n,Su(n),t,e)}),vf=ae(gn),gf=lr(function(t){return t.push(F,an),r(pf,F,t)}),df=lr(function(t){return t.push(F,Oe),r(wf,F,t)}),yf=Yr(function(t,n,r){t[n]=r},Uu(Cu)),bf=Yr(function(t,n,r){ei.call(t,n)?t[n].push(r):t[n]=[r]},he),xf=lr(Mn),jf=Tr(function(t,n,r){tr(t,n,r)}),wf=Tr(function(t,n,r,e){tr(t,n,r,e)}),mf=ae(function(t,n){return null==t?{}:(n=l(n,Be),er(t,wn(zn(t,Iu,lo),n)))}),Af=ae(function(t,n){return null==t?{}:er(t,l(n,Be))}),kf=ie(Su),Ef=ie(Iu),Of=Zr(function(t,n,r){return n=n.toLowerCase(),\nt+(r?Wu(n):n)}),Sf=Zr(function(t,n,r){return t+(r?\"-\":\"\")+n.toLowerCase()}),If=Zr(function(t,n,r){return t+(r?\" \":\"\")+n.toLowerCase()}),Rf=Pr(\"toLowerCase\"),zf=Zr(function(t,n,r){return t+(r?\"_\":\"\")+n.toLowerCase()}),Wf=Zr(function(t,n,r){return t+(r?\" \":\"\")+Lf(n)}),Bf=Zr(function(t,n,r){return t+(r?\" \":\"\")+n.toUpperCase()}),Lf=Pr(\"toUpperCase\"),Uf=lr(function(t,n){try{return r(t,F,n)}catch(t){return au(t)?t:new qu(t)}}),Cf=ae(function(t,n){return u(n,function(n){n=Be(n),vn(t,n,Zo(t[n],t))}),t}),Mf=Gr(),Df=Gr(true),Tf=lr(function(t,n){\nreturn function(r){return Mn(r,t,n)}}),$f=lr(function(t,n){return function(r){return Mn(t,r,n)}}),Ff=Qr(l),Nf=Qr(o),Pf=Qr(_),Zf=ne(),qf=ne(true),Vf=Hr(function(t,n){return t+n},0),Kf=ue(\"ceil\"),Gf=Hr(function(t,n){return t/n},1),Jf=ue(\"floor\"),Yf=Hr(function(t,n){return t*n},1),Hf=ue(\"round\"),Qf=Hr(function(t,n){return t-n},0);return Ot.after=function(t,n){if(typeof n!=\"function\")throw new Hu(\"Expected a function\");return t=ju(t),function(){if(1>--t)return n.apply(this,arguments)}},Ot.ary=Qe,Ot.assign=sf,\nOt.assignIn=hf,Ot.assignInWith=pf,Ot.assignWith=_f,Ot.at=vf,Ot.before=Xe,Ot.bind=Zo,Ot.bindAll=Cf,Ot.bindKey=qo,Ot.castArray=function(){if(!arguments.length)return[];var t=arguments[0];return tf(t)?t:[t]},Ot.chain=Ve,Ot.chunk=function(t,n,r){if(n=(r?we(t,n,r):n===F)?1:Ri(ju(n),0),r=t?t.length:0,!r||1>n)return[];for(var e=0,u=0,i=Pu(mi(r/n));e<r;)i[u++]=vr(t,e,e+=n);return i},Ot.compact=function(t){for(var n=-1,r=t?t.length:0,e=0,u=[];++n<r;){var i=t[n];i&&(u[e++]=i)}return u},Ot.concat=function(){\nvar t=arguments.length;if(!t)return[];for(var n=Pu(t-1),r=arguments[0];t--;)n[t-1]=arguments[t];return s(tf(r)?Ur(r):[r],En(n,1))},Ot.cond=function(t){var n=t?t.length:0,e=he();return t=n?l(t,function(t){if(\"function\"!=typeof t[1])throw new Hu(\"Expected a function\");return[e(t[0]),t[1]]}):[],lr(function(e){for(var u=-1;++u<n;){var i=t[u];if(r(i[0],this,e))return r(i[1],this,e)}})},Ot.conforms=function(t){return bn(yn(t,true))},Ot.constant=Uu,Ot.countBy=Uo,Ot.create=function(t,n){var r=Xi(t);return n?_n(r,n):r;\n},Ot.curry=tu,Ot.curryRight=nu,Ot.debounce=ru,Ot.defaults=gf,Ot.defaultsDeep=df,Ot.defer=Vo,Ot.delay=Ko,Ot.difference=go,Ot.differenceBy=yo,Ot.differenceWith=bo,Ot.drop=function(t,n,r){var e=t?t.length:0;return e?(n=r||n===F?1:ju(n),vr(t,0>n?0:n,e)):[]},Ot.dropRight=function(t,n,r){var e=t?t.length:0;return e?(n=r||n===F?1:ju(n),n=e-n,vr(t,0,0>n?0:n)):[]},Ot.dropRightWhile=function(t,n){return t&&t.length?mr(t,he(n,3),true,true):[]},Ot.dropWhile=function(t,n){return t&&t.length?mr(t,he(n,3),true):[]},Ot.fill=function(t,n,r,e){\nvar u=t?t.length:0;if(!u)return[];for(r&&typeof r!=\"number\"&&we(t,n,r)&&(r=0,e=u),u=t.length,r=ju(r),0>r&&(r=-r>u?0:u+r),e=e===F||e>u?u:ju(e),0>e&&(e+=u),e=r>e?0:wu(e);r<e;)t[r++]=n;return t},Ot.filter=function(t,n){return(tf(t)?f:kn)(t,he(n,3))},Ot.flatMap=function(t,n){return En(He(t,n),1)},Ot.flatMapDeep=function(t,n){return En(He(t,n),N)},Ot.flatMapDepth=function(t,n,r){return r=r===F?1:ju(r),En(He(t,n),r)},Ot.flatten=Te,Ot.flattenDeep=function(t){return t&&t.length?En(t,N):[]},Ot.flattenDepth=function(t,n){\nreturn t&&t.length?(n=n===F?1:ju(n),En(t,n)):[]},Ot.flip=function(t){return oe(t,512)},Ot.flow=Mf,Ot.flowRight=Df,Ot.fromPairs=function(t){for(var n=-1,r=t?t.length:0,e={};++n<r;){var u=t[n];e[u[0]]=u[1]}return e},Ot.functions=function(t){return null==t?[]:In(t,Su(t))},Ot.functionsIn=function(t){return null==t?[]:In(t,Iu(t))},Ot.groupBy=Do,Ot.initial=function(t){return t&&t.length?vr(t,0,-1):[]},Ot.intersection=xo,Ot.intersectionBy=jo,Ot.intersectionWith=wo,Ot.invert=yf,Ot.invertBy=bf,Ot.invokeMap=To,\nOt.iteratee=Mu,Ot.keyBy=$o,Ot.keys=Su,Ot.keysIn=Iu,Ot.map=He,Ot.mapKeys=function(t,n){var r={};return n=he(n,3),On(t,function(t,e,u){vn(r,n(t,e,u),t)}),r},Ot.mapValues=function(t,n){var r={};return n=he(n,3),On(t,function(t,e,u){vn(r,e,n(t,e,u))}),r},Ot.matches=function(t){return Qn(yn(t,true))},Ot.matchesProperty=function(t,n){return Xn(t,yn(n,true))},Ot.memoize=eu,Ot.merge=jf,Ot.mergeWith=wf,Ot.method=Tf,Ot.methodOf=$f,Ot.mixin=Du,Ot.negate=uu,Ot.nthArg=function(t){return t=ju(t),lr(function(n){return nr(n,t);\n})},Ot.omit=mf,Ot.omitBy=function(t,n){return Ru(t,uu(he(n)))},Ot.once=function(t){return Xe(2,t)},Ot.orderBy=function(t,n,r,e){return null==t?[]:(tf(n)||(n=null==n?[]:[n]),r=e?F:r,tf(r)||(r=null==r?[]:[r]),rr(t,n,r))},Ot.over=Ff,Ot.overArgs=Go,Ot.overEvery=Nf,Ot.overSome=Pf,Ot.partial=Jo,Ot.partialRight=Yo,Ot.partition=Fo,Ot.pick=Af,Ot.pickBy=Ru,Ot.property=$u,Ot.propertyOf=function(t){return function(n){return null==t?F:Rn(t,n)}},Ot.pull=mo,Ot.pullAll=Ne,Ot.pullAllBy=function(t,n,r){return t&&t.length&&n&&n.length?or(t,n,he(r,2)):t;\n},Ot.pullAllWith=function(t,n,r){return t&&t.length&&n&&n.length?or(t,n,F,r):t},Ot.pullAt=Ao,Ot.range=Zf,Ot.rangeRight=qf,Ot.rearg=Ho,Ot.reject=function(t,n){return(tf(t)?f:kn)(t,uu(he(n,3)))},Ot.remove=function(t,n){var r=[];if(!t||!t.length)return r;var e=-1,u=[],i=t.length;for(n=he(n,3);++e<i;){var o=t[e];n(o,e,t)&&(r.push(o),u.push(e))}return fr(t,u),r},Ot.rest=function(t,n){if(typeof t!=\"function\")throw new Hu(\"Expected a function\");return n=n===F?n:ju(n),lr(t,n)},Ot.reverse=Pe,Ot.sampleSize=function(t,n,r){\nreturn n=(r?we(t,n,r):n===F)?1:ju(n),(tf(t)?fn:hr)(t,n)},Ot.set=function(t,n,r){return null==t?t:pr(t,n,r)},Ot.setWith=function(t,n,r,e){return e=typeof e==\"function\"?e:F,null==t?t:pr(t,n,r,e)},Ot.shuffle=function(t){return(tf(t)?cn:_r)(t)},Ot.slice=function(t,n,r){var e=t?t.length:0;return e?(r&&typeof r!=\"number\"&&we(t,n,r)?(n=0,r=e):(n=null==n?0:ju(n),r=r===F?e:ju(r)),vr(t,n,r)):[]},Ot.sortBy=No,Ot.sortedUniq=function(t){return t&&t.length?br(t):[]},Ot.sortedUniqBy=function(t,n){return t&&t.length?br(t,he(n,2)):[];\n},Ot.split=function(t,n,r){return r&&typeof r!=\"number\"&&we(t,n,r)&&(n=r=F),r=r===F?4294967295:r>>>0,r?(t=ku(t))&&(typeof n==\"string\"||null!=n&&!of(n))&&(n=jr(n),!n&&Wt.test(t))?Ir($(t),0,r):t.split(n,r):[]},Ot.spread=function(t,n){if(typeof t!=\"function\")throw new Hu(\"Expected a function\");return n=n===F?0:Ri(ju(n),0),lr(function(e){var u=e[n];return e=Ir(e,0,n),u&&s(e,u),r(t,this,e)})},Ot.tail=function(t){var n=t?t.length:0;return n?vr(t,1,n):[]},Ot.take=function(t,n,r){return t&&t.length?(n=r||n===F?1:ju(n),\nvr(t,0,0>n?0:n)):[]},Ot.takeRight=function(t,n,r){var e=t?t.length:0;return e?(n=r||n===F?1:ju(n),n=e-n,vr(t,0>n?0:n,e)):[]},Ot.takeRightWhile=function(t,n){return t&&t.length?mr(t,he(n,3),false,true):[]},Ot.takeWhile=function(t,n){return t&&t.length?mr(t,he(n,3)):[]},Ot.tap=function(t,n){return n(t),t},Ot.throttle=function(t,n,r){var e=true,u=true;if(typeof t!=\"function\")throw new Hu(\"Expected a function\");return pu(r)&&(e=\"leading\"in r?!!r.leading:e,u=\"trailing\"in r?!!r.trailing:u),ru(t,n,{leading:e,maxWait:n,\ntrailing:u})},Ot.thru=Ke,Ot.toArray=bu,Ot.toPairs=kf,Ot.toPairsIn=Ef,Ot.toPath=function(t){return tf(t)?l(t,Be):yu(t)?[t]:Ur(vo(t))},Ot.toPlainObject=Au,Ot.transform=function(t,n,r){var e=tf(t)||cf(t);if(n=he(n,4),null==r)if(e||pu(t)){var i=t.constructor;r=e?tf(t)?new i:[]:lu(i)?Xi(_i(t)):{}}else r={};return(e?u:On)(t,function(t,e,u){return n(r,t,e,u)}),r},Ot.unary=function(t){return Qe(t,1)},Ot.union=ko,Ot.unionBy=Eo,Ot.unionWith=Oo,Ot.uniq=function(t){return t&&t.length?wr(t):[]},Ot.uniqBy=function(t,n){\nreturn t&&t.length?wr(t,he(n,2)):[]},Ot.uniqWith=function(t,n){return t&&t.length?wr(t,F,n):[]},Ot.unset=function(t,n){var r;if(null==t)r=true;else{r=t;var e=n,e=me(e,r)?[e]:Sr(e);r=Ie(r,e),e=Be(Fe(e)),r=!(null!=r&&ei.call(r,e))||delete r[e]}return r},Ot.unzip=Ze,Ot.unzipWith=qe,Ot.update=function(t,n,r){return null==t?t:pr(t,n,(typeof r==\"function\"?r:Cu)(Rn(t,n)),void 0)},Ot.updateWith=function(t,n,r,e){return e=typeof e==\"function\"?e:F,null!=t&&(t=pr(t,n,(typeof r==\"function\"?r:Cu)(Rn(t,n)),e)),t;\n},Ot.values=zu,Ot.valuesIn=function(t){return null==t?[]:I(t,Iu(t))},Ot.without=So,Ot.words=Lu,Ot.wrap=function(t,n){return n=null==n?Cu:n,Jo(n,t)},Ot.xor=Io,Ot.xorBy=Ro,Ot.xorWith=zo,Ot.zip=Wo,Ot.zipObject=function(t,n){return Er(t||[],n||[],sn)},Ot.zipObjectDeep=function(t,n){return Er(t||[],n||[],pr)},Ot.zipWith=Bo,Ot.entries=kf,Ot.entriesIn=Ef,Ot.extend=hf,Ot.extendWith=pf,Du(Ot,Ot),Ot.add=Vf,Ot.attempt=Uf,Ot.camelCase=Of,Ot.capitalize=Wu,Ot.ceil=Kf,Ot.clamp=function(t,n,r){return r===F&&(r=n,\nn=F),r!==F&&(r=mu(r),r=r===r?r:0),n!==F&&(n=mu(n),n=n===n?n:0),dn(mu(t),n,r)},Ot.clone=function(t){return yn(t,false,true)},Ot.cloneDeep=function(t){return yn(t,true,true)},Ot.cloneDeepWith=function(t,n){return yn(t,true,true,n)},Ot.cloneWith=function(t,n){return yn(t,false,true,n)},Ot.conformsTo=function(t,n){return null==n||xn(t,n,Su(n))},Ot.deburr=Bu,Ot.defaultTo=function(t,n){return null==t||t!==t?n:t},Ot.divide=Gf,Ot.endsWith=function(t,n,r){t=ku(t),n=jr(n);var e=t.length,e=r=r===F?e:dn(ju(r),0,e);return r-=n.length,\n0<=r&&t.slice(r,e)==n},Ot.eq=iu,Ot.escape=function(t){return(t=ku(t))&&H.test(t)?t.replace(J,rn):t},Ot.escapeRegExp=function(t){return(t=ku(t))&&ot.test(t)?t.replace(it,\"\\\\$&\"):t},Ot.every=function(t,n,r){var e=tf(t)?o:mn;return r&&we(t,n,r)&&(n=F),e(t,he(n,3))},Ot.find=Co,Ot.findIndex=Me,Ot.findKey=function(t,n){return v(t,he(n,3),On)},Ot.findLast=Mo,Ot.findLastIndex=De,Ot.findLastKey=function(t,n){return v(t,he(n,3),Sn)},Ot.floor=Jf,Ot.forEach=Je,Ot.forEachRight=Ye,Ot.forIn=function(t,n){return null==t?t:ro(t,he(n,3),Iu);\n},Ot.forInRight=function(t,n){return null==t?t:eo(t,he(n,3),Iu)},Ot.forOwn=function(t,n){return t&&On(t,he(n,3))},Ot.forOwnRight=function(t,n){return t&&Sn(t,he(n,3))},Ot.get=Eu,Ot.gt=Qo,Ot.gte=Xo,Ot.has=function(t,n){return null!=t&&ge(t,n,Bn)},Ot.hasIn=Ou,Ot.head=$e,Ot.identity=Cu,Ot.includes=function(t,n,r,e){return t=fu(t)?t:zu(t),r=r&&!e?ju(r):0,e=t.length,0>r&&(r=Ri(e+r,0)),du(t)?r<=e&&-1<t.indexOf(n,r):!!e&&-1<d(t,n,r)},Ot.indexOf=function(t,n,r){var e=t?t.length:0;return e?(r=null==r?0:ju(r),\n0>r&&(r=Ri(e+r,0)),d(t,n,r)):-1},Ot.inRange=function(t,n,r){return n=xu(n),r===F?(r=n,n=0):r=xu(r),t=mu(t),t>=zi(n,r)&&t<Ri(n,r)},Ot.invoke=xf,Ot.isArguments=ou,Ot.isArray=tf,Ot.isArrayBuffer=nf,Ot.isArrayLike=fu,Ot.isArrayLikeObject=cu,Ot.isBoolean=function(t){return true===t||false===t||_u(t)&&\"[object Boolean]\"==oi.call(t)},Ot.isBuffer=rf,Ot.isDate=ef,Ot.isElement=function(t){return null!=t&&1===t.nodeType&&_u(t)&&!gu(t)},Ot.isEmpty=function(t){if(fu(t)&&(tf(t)||typeof t==\"string\"||typeof t.splice==\"function\"||rf(t)||ou(t)))return!t.length;\nvar n=Et(t);if(\"[object Map]\"==n||\"[object Set]\"==n)return!t.size;if(ke(t))return!Ii(t).length;for(var r in t)if(ei.call(t,r))return false;return true},Ot.isEqual=function(t,n){return $n(t,n)},Ot.isEqualWith=function(t,n,r){var e=(r=typeof r==\"function\"?r:F)?r(t,n):F;return e===F?$n(t,n,r):!!e},Ot.isError=au,Ot.isFinite=function(t){return typeof t==\"number\"&&Oi(t)},Ot.isFunction=lu,Ot.isInteger=su,Ot.isLength=hu,Ot.isMap=uf,Ot.isMatch=function(t,n){return t===n||Nn(t,n,_e(n))},Ot.isMatchWith=function(t,n,r){\nreturn r=typeof r==\"function\"?r:F,Nn(t,n,_e(n),r)},Ot.isNaN=function(t){return vu(t)&&t!=+t},Ot.isNative=function(t){if(so(t))throw new qu(\"Unsupported core-js use. Try https://github.com/es-shims.\");return Pn(t)},Ot.isNil=function(t){return null==t},Ot.isNull=function(t){return null===t},Ot.isNumber=vu,Ot.isObject=pu,Ot.isObjectLike=_u,Ot.isPlainObject=gu,Ot.isRegExp=of,Ot.isSafeInteger=function(t){return su(t)&&-9007199254740991<=t&&9007199254740991>=t},Ot.isSet=ff,Ot.isString=du,Ot.isSymbol=yu,\nOt.isTypedArray=cf,Ot.isUndefined=function(t){return t===F},Ot.isWeakMap=function(t){return _u(t)&&\"[object WeakMap]\"==Et(t)},Ot.isWeakSet=function(t){return _u(t)&&\"[object WeakSet]\"==oi.call(t)},Ot.join=function(t,n){return t?Si.call(t,n):\"\"},Ot.kebabCase=Sf,Ot.last=Fe,Ot.lastIndexOf=function(t,n,r){var e=t?t.length:0;if(!e)return-1;var u=e;if(r!==F&&(u=ju(r),u=0>u?Ri(e+u,0):zi(u,e-1)),n===n){for(r=u+1;r--&&t[r]!==n;);t=r}else t=g(t,b,u,true);return t},Ot.lowerCase=If,Ot.lowerFirst=Rf,Ot.lt=af,Ot.lte=lf,\nOt.max=function(t){return t&&t.length?An(t,Cu,Wn):F},Ot.maxBy=function(t,n){return t&&t.length?An(t,he(n,2),Wn):F},Ot.mean=function(t){return x(t,Cu)},Ot.meanBy=function(t,n){return x(t,he(n,2))},Ot.min=function(t){return t&&t.length?An(t,Cu,Yn):F},Ot.minBy=function(t,n){return t&&t.length?An(t,he(n,2),Yn):F},Ot.stubArray=Fu,Ot.stubFalse=Nu,Ot.stubObject=function(){return{}},Ot.stubString=function(){return\"\"},Ot.stubTrue=function(){return true},Ot.multiply=Yf,Ot.nth=function(t,n){return t&&t.length?nr(t,ju(n)):F;\n},Ot.noConflict=function(){return Pt._===this&&(Pt._=fi),this},Ot.noop=Tu,Ot.now=Po,Ot.pad=function(t,n,r){t=ku(t);var e=(n=ju(n))?T(t):0;return!n||e>=n?t:(n=(n-e)/2,Xr(Ai(n),r)+t+Xr(mi(n),r))},Ot.padEnd=function(t,n,r){t=ku(t);var e=(n=ju(n))?T(t):0;return n&&e<n?t+Xr(n-e,r):t},Ot.padStart=function(t,n,r){t=ku(t);var e=(n=ju(n))?T(t):0;return n&&e<n?Xr(n-e,r)+t:t},Ot.parseInt=function(t,n,r){return r||null==n?n=0:n&&(n=+n),Bi(ku(t).replace(ct,\"\"),n||0)},Ot.random=function(t,n,r){if(r&&typeof r!=\"boolean\"&&we(t,n,r)&&(n=r=F),\nr===F&&(typeof n==\"boolean\"?(r=n,n=F):typeof t==\"boolean\"&&(r=t,t=F)),t===F&&n===F?(t=0,n=1):(t=xu(t),n===F?(n=t,t=0):n=xu(n)),t>n){var e=t;t=n,n=e}return r||t%1||n%1?(r=Li(),zi(t+r*(n-t+Tt(\"1e-\"+((r+\"\").length-1))),n)):cr(t,n)},Ot.reduce=function(t,n,r){var e=tf(t)?h:m,u=3>arguments.length;return e(t,he(n,4),r,u,to)},Ot.reduceRight=function(t,n,r){var e=tf(t)?p:m,u=3>arguments.length;return e(t,he(n,4),r,u,no)},Ot.repeat=function(t,n,r){return n=(r?we(t,n,r):n===F)?1:ju(n),ar(ku(t),n)},Ot.replace=function(){\nvar t=arguments,n=ku(t[0]);return 3>t.length?n:n.replace(t[1],t[2])},Ot.result=function(t,n,r){n=me(n,t)?[n]:Sr(n);var e=-1,u=n.length;for(u||(t=F,u=1);++e<u;){var i=null==t?F:t[Be(n[e])];i===F&&(e=u,i=r),t=lu(i)?i.call(t):i}return t},Ot.round=Hf,Ot.runInContext=w,Ot.sample=function(t){return(tf(t)?on:sr)(t)},Ot.size=function(t){if(null==t)return 0;if(fu(t))return du(t)?T(t):t.length;var n=Et(t);return\"[object Map]\"==n||\"[object Set]\"==n?t.size:Gn(t).length},Ot.snakeCase=zf,Ot.some=function(t,n,r){\nvar e=tf(t)?_:gr;return r&&we(t,n,r)&&(n=F),e(t,he(n,3))},Ot.sortedIndex=function(t,n){return dr(t,n)},Ot.sortedIndexBy=function(t,n,r){return yr(t,n,he(r,2))},Ot.sortedIndexOf=function(t,n){var r=t?t.length:0;if(r){var e=dr(t,n);if(e<r&&iu(t[e],n))return e}return-1},Ot.sortedLastIndex=function(t,n){return dr(t,n,true)},Ot.sortedLastIndexBy=function(t,n,r){return yr(t,n,he(r,2),true)},Ot.sortedLastIndexOf=function(t,n){if(t&&t.length){var r=dr(t,n,true)-1;if(iu(t[r],n))return r}return-1},Ot.startCase=Wf,\nOt.startsWith=function(t,n,r){return t=ku(t),r=dn(ju(r),0,t.length),n=jr(n),t.slice(r,r+n.length)==n},Ot.subtract=Qf,Ot.sum=function(t){return t&&t.length?k(t,Cu):0},Ot.sumBy=function(t,n){return t&&t.length?k(t,he(n,2)):0},Ot.template=function(t,n,r){var e=Ot.templateSettings;r&&we(t,n,r)&&(n=F),t=ku(t),n=pf({},n,e,an),r=pf({},n.imports,e.imports,an);var u,i,o=Su(r),f=I(r,o),c=0;r=n.interpolate||mt;var a=\"__p+='\";r=Ju((n.escape||mt).source+\"|\"+r.source+\"|\"+(r===tt?vt:mt).source+\"|\"+(n.evaluate||mt).source+\"|$\",\"g\");\nvar l=\"sourceURL\"in n?\"//# sourceURL=\"+n.sourceURL+\"\\n\":\"\";if(t.replace(r,function(n,r,e,o,f,l){return e||(e=o),a+=t.slice(c,l).replace(At,B),r&&(u=true,a+=\"'+__e(\"+r+\")+'\"),f&&(i=true,a+=\"';\"+f+\";\\n__p+='\"),e&&(a+=\"'+((__t=(\"+e+\"))==null?'':__t)+'\"),c=l+n.length,n}),a+=\"';\",(n=n.variable)||(a=\"with(obj){\"+a+\"}\"),a=(i?a.replace(q,\"\"):a).replace(V,\"$1\").replace(K,\"$1;\"),a=\"function(\"+(n||\"obj\")+\"){\"+(n?\"\":\"obj||(obj={});\")+\"var __t,__p=''\"+(u?\",__e=_.escape\":\"\")+(i?\",__j=Array.prototype.join;function print(){__p+=__j.call(arguments,'')}\":\";\")+a+\"return __p}\",\nn=Uf(function(){return Vu(o,l+\"return \"+a).apply(F,f)}),n.source=a,au(n))throw n;return n},Ot.times=function(t,n){if(t=ju(t),1>t||9007199254740991<t)return[];var r=4294967295,e=zi(t,4294967295);for(n=he(n),t-=4294967295,e=E(e,n);++r<t;)n(r);return e},Ot.toFinite=xu,Ot.toInteger=ju,Ot.toLength=wu,Ot.toLower=function(t){return ku(t).toLowerCase()},Ot.toNumber=mu,Ot.toSafeInteger=function(t){return dn(ju(t),-9007199254740991,9007199254740991)},Ot.toString=ku,Ot.toUpper=function(t){return ku(t).toUpperCase();\n},Ot.trim=function(t,n,r){return(t=ku(t))&&(r||n===F)?t.replace(ft,\"\"):t&&(n=jr(n))?(t=$(t),r=$(n),n=z(t,r),r=W(t,r)+1,Ir(t,n,r).join(\"\")):t},Ot.trimEnd=function(t,n,r){return(t=ku(t))&&(r||n===F)?t.replace(at,\"\"):t&&(n=jr(n))?(t=$(t),n=W(t,$(n))+1,Ir(t,0,n).join(\"\")):t},Ot.trimStart=function(t,n,r){return(t=ku(t))&&(r||n===F)?t.replace(ct,\"\"):t&&(n=jr(n))?(t=$(t),n=z(t,$(n)),Ir(t,n).join(\"\")):t},Ot.truncate=function(t,n){var r=30,e=\"...\";if(pu(n))var u=\"separator\"in n?n.separator:u,r=\"length\"in n?ju(n.length):r,e=\"omission\"in n?jr(n.omission):e;\nt=ku(t);var i=t.length;if(Wt.test(t))var o=$(t),i=o.length;if(r>=i)return t;if(i=r-T(e),1>i)return e;if(r=o?Ir(o,0,i).join(\"\"):t.slice(0,i),u===F)return r+e;if(o&&(i+=r.length-i),of(u)){if(t.slice(i).search(u)){var f=r;for(u.global||(u=Ju(u.source,ku(gt.exec(u))+\"g\")),u.lastIndex=0;o=u.exec(f);)var c=o.index;r=r.slice(0,c===F?i:c)}}else t.indexOf(jr(u),i)!=i&&(u=r.lastIndexOf(u),-1<u&&(r=r.slice(0,u)));return r+e},Ot.unescape=function(t){return(t=ku(t))&&Y.test(t)?t.replace(G,en):t},Ot.uniqueId=function(t){\nvar n=++ui;return ku(t)+n},Ot.upperCase=Bf,Ot.upperFirst=Lf,Ot.each=Je,Ot.eachRight=Ye,Ot.first=$e,Du(Ot,function(){var t={};return On(Ot,function(n,r){ei.call(Ot.prototype,r)||(t[r]=n)}),t}(),{chain:false}),Ot.VERSION=\"4.16.2\",u(\"bind bindKey curry curryRight partial partialRight\".split(\" \"),function(t){Ot[t].placeholder=Ot}),u([\"drop\",\"take\"],function(t,n){Dt.prototype[t]=function(r){var e=this.__filtered__;if(e&&!n)return new Dt(this);r=r===F?1:Ri(ju(r),0);var u=this.clone();return e?u.__takeCount__=zi(r,u.__takeCount__):u.__views__.push({\nsize:zi(r,4294967295),type:t+(0>u.__dir__?\"Right\":\"\")}),u},Dt.prototype[t+\"Right\"]=function(n){return this.reverse()[t](n).reverse()}}),u([\"filter\",\"map\",\"takeWhile\"],function(t,n){var r=n+1,e=1==r||3==r;Dt.prototype[t]=function(t){var n=this.clone();return n.__iteratees__.push({iteratee:he(t,3),type:r}),n.__filtered__=n.__filtered__||e,n}}),u([\"head\",\"last\"],function(t,n){var r=\"take\"+(n?\"Right\":\"\");Dt.prototype[t]=function(){return this[r](1).value()[0]}}),u([\"initial\",\"tail\"],function(t,n){var r=\"drop\"+(n?\"\":\"Right\");\nDt.prototype[t]=function(){return this.__filtered__?new Dt(this):this[r](1)}}),Dt.prototype.compact=function(){return this.filter(Cu)},Dt.prototype.find=function(t){return this.filter(t).head()},Dt.prototype.findLast=function(t){return this.reverse().find(t)},Dt.prototype.invokeMap=lr(function(t,n){return typeof t==\"function\"?new Dt(this):this.map(function(r){return Mn(r,t,n)})}),Dt.prototype.reject=function(t){return this.filter(uu(he(t)))},Dt.prototype.slice=function(t,n){t=ju(t);var r=this;return r.__filtered__&&(0<t||0>n)?new Dt(r):(0>t?r=r.takeRight(-t):t&&(r=r.drop(t)),\nn!==F&&(n=ju(n),r=0>n?r.dropRight(-n):r.take(n-t)),r)},Dt.prototype.takeRightWhile=function(t){return this.reverse().takeWhile(t).reverse()},Dt.prototype.toArray=function(){return this.take(4294967295)},On(Dt.prototype,function(t,n){var r=/^(?:filter|find|map|reject)|While$/.test(n),e=/^(?:head|last)$/.test(n),u=Ot[e?\"take\"+(\"last\"==n?\"Right\":\"\"):n],i=e||/^find/.test(n);u&&(Ot.prototype[n]=function(){function n(t){return t=u.apply(Ot,s([t],f)),e&&h?t[0]:t}var o=this.__wrapped__,f=e?[1]:arguments,c=o instanceof Dt,a=f[0],l=c||tf(o);\nl&&r&&typeof a==\"function\"&&1!=a.length&&(c=l=false);var h=this.__chain__,p=!!this.__actions__.length,a=i&&!h,c=c&&!p;return!i&&l?(o=c?o:new Dt(this),o=t.apply(o,f),o.__actions__.push({func:Ke,args:[n],thisArg:F}),new Mt(o,h)):a&&c?t.apply(this,f):(o=this.thru(n),a?e?o.value()[0]:o.value():o)})}),u(\"pop push shift sort splice unshift\".split(\" \"),function(t){var n=Qu[t],r=/^(?:push|sort|unshift)$/.test(t)?\"tap\":\"thru\",e=/^(?:pop|shift)$/.test(t);Ot.prototype[t]=function(){var t=arguments;if(e&&!this.__chain__){\nvar u=this.value();return n.apply(tf(u)?u:[],t)}return this[r](function(r){return n.apply(tf(r)?r:[],t)})}}),On(Dt.prototype,function(t,n){var r=Ot[n];if(r){var e=r.name+\"\";(Zi[e]||(Zi[e]=[])).push({name:n,func:r})}}),Zi[Jr(F,2).name]=[{name:\"wrapper\",func:F}],Dt.prototype.clone=function(){var t=new Dt(this.__wrapped__);return t.__actions__=Ur(this.__actions__),t.__dir__=this.__dir__,t.__filtered__=this.__filtered__,t.__iteratees__=Ur(this.__iteratees__),t.__takeCount__=this.__takeCount__,t.__views__=Ur(this.__views__),\nt},Dt.prototype.reverse=function(){if(this.__filtered__){var t=new Dt(this);t.__dir__=-1,t.__filtered__=true}else t=this.clone(),t.__dir__*=-1;return t},Dt.prototype.value=function(){var t,n=this.__wrapped__.value(),r=this.__dir__,e=tf(n),u=0>r,i=e?n.length:0;t=i;for(var o=this.__views__,f=0,c=-1,a=o.length;++c<a;){var l=o[c],s=l.size;switch(l.type){case\"drop\":f+=s;break;case\"dropRight\":t-=s;break;case\"take\":t=zi(t,f+s);break;case\"takeRight\":f=Ri(f,t-s)}}if(t={start:f,end:t},o=t.start,f=t.end,t=f-o,\nu=u?f:o-1,o=this.__iteratees__,f=o.length,c=0,a=zi(t,this.__takeCount__),!e||200>i||i==t&&a==t)return Ar(n,this.__actions__);e=[];t:for(;t--&&c<a;){for(u+=r,i=-1,l=n[u];++i<f;){var h=o[i],s=h.type,h=(0,h.iteratee)(l);if(2==s)l=h;else if(!h){if(1==s)continue t;break t}}e[c++]=l}return e},Ot.prototype.at=Lo,Ot.prototype.chain=function(){return Ve(this)},Ot.prototype.commit=function(){return new Mt(this.value(),this.__chain__)},Ot.prototype.next=function(){this.__values__===F&&(this.__values__=bu(this.value()));\nvar t=this.__index__>=this.__values__.length;return{done:t,value:t?F:this.__values__[this.__index__++]}},Ot.prototype.plant=function(t){for(var n,r=this;r instanceof Rt;){var e=Ce(r);e.__index__=0,e.__values__=F,n?u.__wrapped__=e:n=e;var u=e,r=r.__wrapped__}return u.__wrapped__=t,n},Ot.prototype.reverse=function(){var t=this.__wrapped__;return t instanceof Dt?(this.__actions__.length&&(t=new Dt(this)),t=t.reverse(),t.__actions__.push({func:Ke,args:[Pe],thisArg:F}),new Mt(t,this.__chain__)):this.thru(Pe);\n},Ot.prototype.toJSON=Ot.prototype.valueOf=Ot.prototype.value=function(){return Ar(this.__wrapped__,this.__actions__)},Ot.prototype.first=Ot.prototype.head,vi&&(Ot.prototype[vi]=Ge),Ot}();typeof define==\"function\"&&typeof define.amd==\"object\"&&define.amd?(Pt._=un, define(function(){return un})):qt?((qt.exports=un)._=un,Zt._=un):Pt._=un}).call(this);\n"
  },
  {
    "path": "public/themes/pterodactyl/vendor/mousewheel/jquery.mousewheel-min.js",
    "content": "(function(c){function g(a){var b=a||window.event,i=[].slice.call(arguments,1),e=0,h=0,f=0;a=c.event.fix(b);a.type=\"mousewheel\";if(b.wheelDelta)e=b.wheelDelta/120;if(b.detail)e=-b.detail/3;f=e;if(b.axis!==undefined&&b.axis===b.HORIZONTAL_AXIS){f=0;h=-1*e}if(b.wheelDeltaY!==undefined)f=b.wheelDeltaY/120;if(b.wheelDeltaX!==undefined)h=-1*b.wheelDeltaX/120;i.unshift(a,e,h,f);return(c.event.dispatch||c.event.handle).apply(this,i)}var d=[\"DOMMouseScroll\",\"mousewheel\"];if(c.event.fixHooks)for(var j=d.length;j;)c.event.fixHooks[d[--j]]=\nc.event.mouseHooks;c.event.special.mousewheel={setup:function(){if(this.addEventListener)for(var a=d.length;a;)this.addEventListener(d[--a],g,false);else this.onmousewheel=g},teardown:function(){if(this.removeEventListener)for(var a=d.length;a;)this.removeEventListener(d[--a],g,false);else this.onmousewheel=null}};c.fn.extend({mousewheel:function(a){return a?this.bind(\"mousewheel\",a):this.trigger(\"mousewheel\")},unmousewheel:function(a){return this.unbind(\"mousewheel\",a)}})})(jQuery);\n"
  },
  {
    "path": "public/themes/pterodactyl/vendor/particlesjs/particles.json",
    "content": "{\n  \"particles\": {\n    \"number\": {\n      \"value\": 80,\n      \"density\": {\n        \"enable\": true,\n        \"value_area\": 800\n      }\n    },\n    \"color\": {\n      \"value\": \"#ffffff\"\n    },\n    \"shape\": {\n      \"type\": \"circle\",\n      \"stroke\": {\n        \"width\": 0,\n        \"color\": \"#000000\"\n      },\n      \"polygon\": {\n        \"nb_sides\": 5\n      },\n      \"image\": {\n        \"src\": \"img/github.svg\",\n        \"width\": 100,\n        \"height\": 100\n      }\n    },\n    \"opacity\": {\n      \"value\": 0.40246529723245905,\n      \"random\": false,\n      \"anim\": {\n        \"enable\": false,\n        \"speed\": 1,\n        \"opacity_min\": 0.1,\n        \"sync\": false\n      }\n    },\n    \"size\": {\n      \"value\": 1,\n      \"random\": true,\n      \"anim\": {\n        \"enable\": false,\n        \"speed\": 40,\n        \"size_min\": 0.1,\n        \"sync\": false\n      }\n    },\n    \"line_linked\": {\n      \"enable\": true,\n      \"distance\": 150,\n      \"color\": \"#ffffff\",\n      \"opacity\": 0.4,\n      \"width\": 1\n    },\n    \"move\": {\n      \"enable\": true,\n      \"speed\": 5,\n      \"direction\": \"none\",\n      \"random\": false,\n      \"straight\": false,\n      \"out_mode\": \"out\",\n      \"bounce\": false,\n      \"attract\": {\n        \"enable\": false,\n        \"rotateX\": 600,\n        \"rotateY\": 1200\n      }\n    }\n  },\n  \"interactivity\": {\n    \"detect_on\": \"window\",\n    \"events\": {\n      \"onhover\": {\n        \"enable\": true,\n        \"mode\": \"repulse\"\n      },\n      \"onclick\": {\n        \"enable\": false,\n        \"mode\": \"repulse\"\n      },\n      \"resize\": true\n    },\n    \"modes\": {\n      \"grab\": {\n        \"distance\": 400,\n        \"line_linked\": {\n          \"opacity\": 1\n        }\n      },\n      \"bubble\": {\n        \"distance\": 400,\n        \"size\": 40,\n        \"duration\": 2,\n        \"opacity\": 8,\n        \"speed\": 3\n      },\n      \"repulse\": {\n        \"distance\": 200,\n        \"duration\": 0.4\n      },\n      \"push\": {\n        \"particles_nb\": 4\n      },\n      \"remove\": {\n        \"particles_nb\": 2\n      }\n    }\n  },\n  \"retina_detect\": true\n}\n"
  },
  {
    "path": "resources/lang/en/activity.php",
    "content": "<?php\n\n/**\n * Contains all of the translation strings for different activity log\n * events. These should be keyed by the value in front of the colon (:)\n * in the event name. If there is no colon present, they should live at\n * the top level.\n */\nreturn [\n    'auth' => [\n        'fail' => 'Failed log in',\n        'success' => 'Logged in',\n        'password-reset' => 'Password reset',\n        'reset-password' => 'Requested password reset',\n        'checkpoint' => 'Two-factor authentication requested',\n        'recovery-token' => 'Used two-factor recovery token',\n        'token' => 'Solved two-factor challenge',\n        'ip-blocked' => 'Blocked request from unlisted IP address for :identifier',\n        'sftp' => [\n            'fail' => 'Failed SFTP log in',\n        ],\n    ],\n    'user' => [\n        'account' => [\n            'email-changed' => 'Changed email from :old to :new',\n            'password-changed' => 'Changed password',\n        ],\n        'api-key' => [\n            'create' => 'Created new API key :identifier',\n            'delete' => 'Deleted API key :identifier',\n        ],\n        'ssh-key' => [\n            'create' => 'Added SSH key :fingerprint to account',\n            'delete' => 'Removed SSH key :fingerprint from account',\n        ],\n        'two-factor' => [\n            'create' => 'Enabled two-factor auth',\n            'delete' => 'Disabled two-factor auth',\n        ],\n    ],\n    'server' => [\n        'reinstall' => 'Reinstalled server',\n        'console' => [\n            'command' => 'Executed \":command\" on the server',\n        ],\n        'power' => [\n            'start' => 'Started the server',\n            'stop' => 'Stopped the server',\n            'restart' => 'Restarted the server',\n            'kill' => 'Killed the server process',\n        ],\n        'backup' => [\n            'download' => 'Downloaded the :name backup',\n            'delete' => 'Deleted the :name backup',\n            'restore' => 'Restored the :name backup (deleted files: :truncate)',\n            'restore-complete' => 'Completed restoration of the :name backup',\n            'restore-failed' => 'Failed to complete restoration of the :name backup',\n            'start' => 'Started a new backup :name',\n            'complete' => 'Marked the :name backup as complete',\n            'fail' => 'Marked the :name backup as failed',\n            'lock' => 'Locked the :name backup',\n            'unlock' => 'Unlocked the :name backup',\n        ],\n        'database' => [\n            'create' => 'Created new database :name',\n            'rotate-password' => 'Password rotated for database :name',\n            'delete' => 'Deleted database :name',\n        ],\n        'file' => [\n            'compress_one' => 'Compressed :directory:file',\n            'compress_other' => 'Compressed :count files in :directory',\n            'read' => 'Viewed the contents of :file',\n            'copy' => 'Created a copy of :file',\n            'create-directory' => 'Created directory :directory:name',\n            'decompress' => 'Decompressed :files in :directory',\n            'delete_one' => 'Deleted :directory:files.0',\n            'delete_other' => 'Deleted :count files in :directory',\n            'download' => 'Downloaded :file',\n            'pull' => 'Downloaded a remote file from :url to :directory',\n            'rename_one' => 'Renamed :directory:files.0.from to :directory:files.0.to',\n            'rename_other' => 'Renamed :count files in :directory',\n            'write' => 'Wrote new content to :file',\n            'upload' => 'Began a file upload',\n            'uploaded' => 'Uploaded :directory:file',\n        ],\n        'sftp' => [\n            'denied' => 'Blocked SFTP access due to permissions',\n            'create_one' => 'Created :files.0',\n            'create_other' => 'Created :count new files',\n            'write_one' => 'Modified the contents of :files.0',\n            'write_other' => 'Modified the contents of :count files',\n            'delete_one' => 'Deleted :files.0',\n            'delete_other' => 'Deleted :count files',\n            'create-directory_one' => 'Created the :files.0 directory',\n            'create-directory_other' => 'Created :count directories',\n            'rename_one' => 'Renamed :files.0.from to :files.0.to',\n            'rename_other' => 'Renamed or moved :count files',\n        ],\n        'allocation' => [\n            'create' => 'Added :allocation to the server',\n            'notes' => 'Updated the notes for :allocation from \":old\" to \":new\"',\n            'primary' => 'Set :allocation as the primary server allocation',\n            'delete' => 'Deleted the :allocation allocation',\n        ],\n        'schedule' => [\n            'create' => 'Created the :name schedule',\n            'update' => 'Updated the :name schedule',\n            'execute' => 'Manually executed the :name schedule',\n            'delete' => 'Deleted the :name schedule',\n        ],\n        'task' => [\n            'create' => 'Created a new \":action\" task for the :name schedule',\n            'update' => 'Updated the \":action\" task for the :name schedule',\n            'delete' => 'Deleted a task for the :name schedule',\n        ],\n        'settings' => [\n            'rename' => 'Renamed the server from :old to :new',\n            'description' => 'Changed the server description from :old to :new',\n        ],\n        'startup' => [\n            'edit' => 'Changed the :variable variable from \":old\" to \":new\"',\n            'image' => 'Updated the Docker Image for the server from :old to :new',\n            'egg-change' => 'Changed the server preset from :old to :new',\n        ],\n        'subuser' => [\n            'create' => 'Added :email as a subuser',\n            'update' => 'Updated the subuser permissions for :email',\n            'delete' => 'Removed :email as a subuser',\n        ],\n    ],\n];\n"
  },
  {
    "path": "resources/lang/en/admin/nests.php",
    "content": "<?php\n\nreturn [\n    'notices' => [\n        'created' => 'A new nest, :name, has been successfully created.',\n        'deleted' => 'Successfully deleted the requested nest from the Panel.',\n        'updated' => 'Successfully updated the nest configuration options.',\n    ],\n    'eggs' => [\n        'notices' => [\n            'imported' => 'Successfully imported this Egg and its associated variables.',\n            'updated_via_import' => 'This Egg has been updated using the file provided.',\n            'deleted' => 'Successfully deleted the requested egg from the Panel.',\n            'updated' => 'Egg configuration has been updated successfully.',\n            'script_updated' => 'Egg install script has been updated and will run whenever servers are installed.',\n            'egg_created' => 'A new egg was laid successfully. You will need to restart any running daemons to apply this new egg.',\n        ],\n    ],\n    'variables' => [\n        'notices' => [\n            'variable_deleted' => 'The variable \":variable\" has been deleted and will no longer be available to servers once rebuilt.',\n            'variable_updated' => 'The variable \":variable\" has been updated. You will need to rebuild any servers using this variable in order to apply changes.',\n            'variable_created' => 'New variable has successfully been created and assigned to this egg.',\n        ],\n    ],\n];\n"
  },
  {
    "path": "resources/lang/en/admin/node.php",
    "content": "<?php\n\nreturn [\n    'validation' => [\n        'fqdn_not_resolvable' => 'The FQDN or IP address provided does not resolve to a valid IP address.',\n        'fqdn_required_for_ssl' => 'A fully qualified domain name that resolves to a public IP address is required in order to use SSL for this node.',\n    ],\n    'notices' => [\n        'allocations_added' => 'Allocations have successfully been added to this node.',\n        'node_deleted' => 'Node has been successfully removed from the panel.',\n        'location_required' => 'You must have at least one location configured before you can add a node to this panel.',\n        'node_created' => 'Successfully created new node. You can automatically configure the daemon on this machine by visiting the \\'Configuration\\' tab. Before you can add any servers you must first allocate at least one IP address and port.',\n        'node_updated' => 'Node information has been updated. If any daemon settings were changed you will need to reboot it for those changes to take effect.',\n        'unallocated_deleted' => 'Deleted all un-allocated ports for <code>:ip</code>.',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/en/admin/server.php",
    "content": "<?php\n\nreturn [\n    'exceptions' => [\n        'no_new_default_allocation' => 'You are attempting to delete the default allocation for this server but there is no fallback allocation to use.',\n        'marked_as_failed' => 'This server was marked as having failed a previous installation. Current status cannot be toggled in this state.',\n        'bad_variable' => 'There was a validation error with the :name variable.',\n        'daemon_exception' => 'There was an exception while attempting to communicate with the daemon resulting in a HTTP/:code response code. This exception has been logged. (request id: :request_id)',\n        'default_allocation_not_found' => 'The requested default allocation was not found in this server\\'s allocations.',\n    ],\n    'alerts' => [\n        'startup_changed' => 'The startup configuration for this server has been updated. If this server\\'s nest or egg was changed a reinstall will be occurring now.',\n        'server_deleted' => 'Server has successfully been deleted from the system.',\n        'server_created' => 'Server was successfully created on the panel. Please allow the daemon a few minutes to completely install this server.',\n        'build_updated' => 'The build details for this server have been updated. Some changes may require a restart to take effect.',\n        'suspension_toggled' => 'Server suspension status has been changed to :status.',\n        'rebuild_on_boot' => 'This server has been marked as requiring a Docker Container rebuild. This will happen the next time the server is started.',\n        'install_toggled' => 'The installation status for this server has been toggled.',\n        'server_reinstalled' => 'This server has been queued for a reinstallation beginning now.',\n        'details_updated' => 'Server details have been successfully updated.',\n        'docker_image_updated' => 'Successfully changed the default Docker image to use for this server. A reboot is required to apply this change.',\n        'node_required' => 'You must have at least one node configured before you can add a server to this panel.',\n        'transfer_nodes_required' => 'You must have at least two nodes configured before you can transfer servers.',\n        'transfer_started' => 'Server transfer has been started.',\n        'transfer_not_viable' => 'The node you selected does not have the required disk space or memory available to accommodate this server.',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/en/admin/user.php",
    "content": "<?php\n\nreturn [\n    'exceptions' => [\n        'delete_self' => 'You cannot delete your own account.',\n        'user_has_servers' => 'Cannot delete a user with active servers attached to their account. Please delete their servers before continuing.',\n    ],\n    'notices' => [\n        'account_created' => 'Account has been created successfully.',\n        'account_updated' => 'Account has been successfully updated.',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/en/auth.php",
    "content": "<?php\n\nreturn [\n    'sign_in' => 'Sign In',\n    'go_to_login' => 'Go to Login',\n    'failed' => 'No account matching those credentials could be found.',\n\n    'forgot_password' => [\n        'label' => 'Forgot Password?',\n        'label_help' => 'Enter your account email address to receive instructions on resetting your password.',\n        'button' => 'Recover Account',\n    ],\n\n    'reset_password' => [\n        'button' => 'Reset and Sign In',\n    ],\n\n    'two_factor' => [\n        'label' => '2-Factor Token',\n        'label_help' => 'This account requires a second layer of authentication in order to continue. Please enter the code generated by your device to complete this login.',\n        'checkpoint_failed' => 'The two-factor authentication token was invalid.',\n    ],\n\n    'throttle' => 'Too many login attempts. Please try again in :seconds seconds.',\n    'password_requirements' => 'Password must be at least 8 characters in length and should be unique to this site.',\n    '2fa_must_be_enabled' => 'The administrator has required that 2-Factor Authentication be enabled for your account in order to use the Panel.',\n];\n"
  },
  {
    "path": "resources/lang/en/command/messages.php",
    "content": "<?php\n\nreturn [\n    'location' => [\n        'no_location_found' => 'Could not locate a record matching the provided short code.',\n        'ask_short' => 'Location Short Code',\n        'ask_long' => 'Location Description',\n        'created' => 'Successfully created a new location (:name) with an ID of :id.',\n        'deleted' => 'Successfully deleted the requested location.',\n    ],\n    'user' => [\n        'search_users' => 'Enter a Username, User ID, or Email Address',\n        'select_search_user' => 'ID of user to delete (Enter \\'0\\' to re-search)',\n        'deleted' => 'User successfully deleted from the Panel.',\n        'confirm_delete' => 'Are you sure you want to delete this user from the Panel?',\n        'no_users_found' => 'No users were found for the search term provided.',\n        'multiple_found' => 'Multiple accounts were found for the user provided, unable to delete a user because of the --no-interaction flag.',\n        'ask_admin' => 'Is this user an administrator?',\n        'ask_email' => 'Email Address',\n        'ask_username' => 'Username',\n        'ask_name_first' => 'First Name',\n        'ask_name_last' => 'Last Name',\n        'ask_password' => 'Password',\n        'ask_password_tip' => 'If you would like to create an account with a random password emailed to the user, re-run this command (CTRL+C) and pass the `--no-password` flag.',\n        'ask_password_help' => 'Passwords must be at least 8 characters in length and contain at least one capital letter and number.',\n        '2fa_help_text' => [\n            'This command will disable 2-factor authentication for a user\\'s account if it is enabled. This should only be used as an account recovery command if the user is locked out of their account.',\n            'If this is not what you wanted to do, press CTRL+C to exit this process.',\n        ],\n        '2fa_disabled' => '2-Factor authentication has been disabled for :email.',\n    ],\n    'schedule' => [\n        'output_line' => 'Dispatching job for first task in `:schedule` (:hash).',\n    ],\n    'maintenance' => [\n        'deleting_service_backup' => 'Deleting service backup file :file.',\n    ],\n    'server' => [\n        'rebuild_failed' => 'Rebuild request for \":name\" (#:id) on node \":node\" failed with error: :message',\n        'reinstall' => [\n            'failed' => 'Reinstall request for \":name\" (#:id) on node \":node\" failed with error: :message',\n            'confirm' => 'You are about to reinstall against a group of servers. Do you wish to continue?',\n        ],\n        'power' => [\n            'confirm' => 'You are about to perform a :action against :count servers. Do you wish to continue?',\n            'action_failed' => 'Power action request for \":name\" (#:id) on node \":node\" failed with error: :message',\n        ],\n    ],\n    'environment' => [\n        'mail' => [\n            'ask_smtp_host' => 'SMTP Host (e.g. smtp.gmail.com)',\n            'ask_smtp_port' => 'SMTP Port',\n            'ask_smtp_username' => 'SMTP Username',\n            'ask_smtp_password' => 'SMTP Password',\n            'ask_mailgun_domain' => 'Mailgun Domain',\n            'ask_mailgun_endpoint' => 'Mailgun Endpoint',\n            'ask_mailgun_secret' => 'Mailgun Secret',\n            'ask_mandrill_secret' => 'Mandrill Secret',\n            'ask_postmark_username' => 'Postmark API Key',\n            'ask_driver' => 'Which driver should be used for sending emails?',\n            'ask_mail_from' => 'Email address emails should originate from',\n            'ask_mail_name' => 'Name that emails should appear from',\n            'ask_encryption' => 'Encryption method to use',\n        ],\n    ],\n];\n"
  },
  {
    "path": "resources/lang/en/dashboard/account.php",
    "content": "<?php\n\nreturn [\n    'email' => [\n        'title' => 'Update your email',\n        'updated' => 'Your email address has been updated.',\n    ],\n    'password' => [\n        'title' => 'Change your password',\n        'requirements' => 'Your new password should be at least 8 characters in length.',\n        'updated' => 'Your password has been updated.',\n    ],\n    'two_factor' => [\n        'button' => 'Configure 2-Factor Authentication',\n        'disabled' => 'Two-factor authentication has been disabled on your account. You will no longer be prompted to provide a token when logging in.',\n        'enabled' => 'Two-factor authentication has been enabled on your account! From now on, when logging in, you will be required to provide the code generated by your device.',\n        'invalid' => 'The token provided was invalid.',\n        'setup' => [\n            'title' => 'Setup two-factor authentication',\n            'help' => 'Can\\'t scan the code? Enter the code below into your application:',\n            'field' => 'Enter token',\n        ],\n        'disable' => [\n            'title' => 'Disable two-factor authentication',\n            'field' => 'Enter token',\n        ],\n    ],\n];\n"
  },
  {
    "path": "resources/lang/en/dashboard/index.php",
    "content": "<?php\n\nreturn [\n    'search' => 'Search for servers...',\n    'no_matches' => 'There were no servers found matching the search criteria provided.',\n    'cpu_title' => 'CPU',\n    'memory_title' => 'Memory',\n];\n"
  },
  {
    "path": "resources/lang/en/exceptions.php",
    "content": "<?php\n\nreturn [\n    'daemon_connection_failed' => 'There was an exception while attempting to communicate with the daemon resulting in a HTTP/:code response code. This exception has been logged.',\n    'node' => [\n        'servers_attached' => 'A node must have no servers linked to it in order to be deleted.',\n        'daemon_off_config_updated' => 'The daemon configuration has been updated, however there was an error encountered while attempting to automatically update the configuration file on the Daemon. You will need to manually update the configuration file (config.yml) for the daemon to apply these changes.',\n    ],\n    'allocations' => [\n        'server_using' => 'A server is currently assigned to this allocation. An allocation can only be deleted if no server is currently assigned.',\n        'too_many_ports' => 'Adding more than 1000 ports in a single range at once is not supported.',\n        'invalid_mapping' => 'The mapping provided for :port was invalid and could not be processed.',\n        'cidr_out_of_range' => 'CIDR notation only allows masks between /25 and /32.',\n        'port_out_of_range' => 'Ports in an allocation must be greater than 1024 and less than or equal to 65535.',\n    ],\n    'nest' => [\n        'delete_has_servers' => 'A Nest with active servers attached to it cannot be deleted from the Panel.',\n        'egg' => [\n            'delete_has_servers' => 'An Egg with active servers attached to it cannot be deleted from the Panel.',\n            'invalid_copy_id' => 'The Egg selected for copying a script from either does not exist, or is copying a script itself.',\n            'must_be_child' => 'The \"Copy Settings From\" directive for this Egg must be a child option for the selected Nest.',\n            'has_children' => 'This Egg is a parent to one or more other Eggs. Please delete those Eggs before deleting this Egg.',\n        ],\n        'variables' => [\n            'env_not_unique' => 'The environment variable :name must be unique to this Egg.',\n            'reserved_name' => 'The environment variable :name is protected and cannot be assigned to a variable.',\n            'bad_validation_rule' => 'The validation rule \":rule\" is not a valid rule for this application.',\n        ],\n        'importer' => [\n            'json_error' => 'There was an error while attempting to parse the JSON file: :error.',\n            'file_error' => 'The JSON file provided was not valid.',\n            'invalid_json_provided' => 'The JSON file provided is not in a format that can be recognized.',\n        ],\n    ],\n    'subusers' => [\n        'editing_self' => 'Editing your own subuser account is not permitted.',\n        'user_is_owner' => 'You cannot add the server owner as a subuser for this server.',\n        'subuser_exists' => 'A user with that email address is already assigned as a subuser for this server.',\n    ],\n    'databases' => [\n        'delete_has_databases' => 'Cannot delete a database host server that has active databases linked to it.',\n    ],\n    'tasks' => [\n        'chain_interval_too_long' => 'The maximum interval time for a chained task is 15 minutes.',\n    ],\n    'locations' => [\n        'has_nodes' => 'Cannot delete a location that has active nodes attached to it.',\n    ],\n    'users' => [\n        'node_revocation_failed' => 'Failed to revoke keys on <a href=\":link\">Node #:node</a>. :error',\n    ],\n    'deployment' => [\n        'no_viable_nodes' => 'No nodes satisfying the requirements specified for automatic deployment could be found.',\n        'no_viable_allocations' => 'No allocations satisfying the requirements for automatic deployment were found.',\n    ],\n    'api' => [\n        'resource_not_found' => 'The requested resource does not exist on this server.',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/en/pagination.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Pagination Language Lines\n    |--------------------------------------------------------------------------\n    |\n    | The following language lines are used by the paginator library to build\n    | the simple pagination links. You are free to change them to anything\n    | you want to customize your views to better match your application.\n    |\n    */\n\n    'previous' => '&laquo; Previous',\n    'next' => 'Next &raquo;',\n];\n"
  },
  {
    "path": "resources/lang/en/passwords.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Password Reset Language Lines\n    |--------------------------------------------------------------------------\n    |\n    | The following language lines are the default lines which match reasons\n    | that are given by the password broker for a password update attempt\n    | has failed, such as for an invalid token or invalid new password.\n    |\n    */\n    'password' => 'Passwords must be at least six characters and match the confirmation.',\n    'reset' => 'Your password has been reset!',\n    'sent' => 'We have e-mailed your password reset link!',\n    'token' => 'This password reset token is invalid.',\n    'user' => \"We can't find a user with that e-mail address.\",\n];\n"
  },
  {
    "path": "resources/lang/en/server/users.php",
    "content": "<?php\n\nreturn [\n    'permissions' => [\n        'websocket_*' => 'Allows access to the websocket for this server.',\n        'control_console' => 'Allows the user to send data to the server console.',\n        'control_start' => 'Allows the user to start the server instance.',\n        'control_stop' => 'Allows the user to stop the server instance.',\n        'control_restart' => 'Allows the user to restart the server instance.',\n        'control_kill' => 'Allows the user to kill the server instance.',\n        'user_create' => 'Allows the user to create new user accounts for the server.',\n        'user_read' => 'Allows the user permission to view users associated with this server.',\n        'user_update' => 'Allows the user to modify other users associated with this server.',\n        'user_delete' => 'Allows the user to delete other users associated with this server.',\n        'file_create' => 'Allows the user permission to create new files and directories.',\n        'file_read' => 'Allows the user to see files and folders associated with this server instance, as well as view their contents.',\n        'file_update' => 'Allows the user to update files and folders associated with the server.',\n        'file_delete' => 'Allows the user to delete files and directories.',\n        'file_archive' => 'Allows the user to create file archives and decompress existing archives.',\n        'file_sftp' => 'Allows the user to perform the above file actions using a SFTP client.',\n        'allocation_read' => 'Allows access to the server allocation management pages.',\n        'allocation_update' => 'Allows user permission to make modifications to the server\\'s allocations.',\n        'database_create' => 'Allows user permission to create a new database for the server.',\n        'database_read' => 'Allows user permission to view the server databases.',\n        'database_update' => 'Allows a user permission to make modifications to a database. If the user does not have the \"View Password\" permission as well they will not be able to modify the password.',\n        'database_delete' => 'Allows a user permission to delete a database instance.',\n        'database_view_password' => 'Allows a user permission to view a database password in the system.',\n        'schedule_create' => 'Allows a user to create a new schedule for the server.',\n        'schedule_read' => 'Allows a user permission to view schedules for a server.',\n        'schedule_update' => 'Allows a user permission to make modifications to an existing server schedule.',\n        'schedule_delete' => 'Allows a user to delete a schedule for the server.',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/en/strings.php",
    "content": "<?php\n\nreturn [\n    'email' => 'Email',\n    'email_address' => 'Email address',\n    'user_identifier' => 'Username or Email',\n    'password' => 'Password',\n    'new_password' => 'New password',\n    'confirm_password' => 'Confirm new password',\n    'login' => 'Login',\n    'home' => 'Home',\n    'servers' => 'Servers',\n    'id' => 'ID',\n    'name' => 'Name',\n    'node' => 'Node',\n    'connection' => 'Connection',\n    'memory' => 'Memory',\n    'cpu' => 'CPU',\n    'disk' => 'Disk',\n    'status' => 'Status',\n    'search' => 'Search',\n    'suspended' => 'Suspended',\n    'account' => 'Account',\n    'security' => 'Security',\n    'ip' => 'IP Address',\n    'last_activity' => 'Last Activity',\n    'revoke' => 'Revoke',\n    '2fa_token' => 'Authentication Token',\n    'submit' => 'Submit',\n    'close' => 'Close',\n    'settings' => 'Settings',\n    'configuration' => 'Configuration',\n    'sftp' => 'SFTP',\n    'databases' => 'Databases',\n    'memo' => 'Memo',\n    'created' => 'Created',\n    'expires' => 'Expires',\n    'public_key' => 'Token',\n    'api_access' => 'Api Access',\n    'never' => 'never',\n    'sign_out' => 'Sign out',\n    'admin_control' => 'Admin Control',\n    'required' => 'Required',\n    'port' => 'Port',\n    'username' => 'Username',\n    'database' => 'Database',\n    'new' => 'New',\n    'danger' => 'Danger',\n    'create' => 'Create',\n    'select_all' => 'Select All',\n    'select_none' => 'Select None',\n    'alias' => 'Alias',\n    'primary' => 'Primary',\n    'make_primary' => 'Make Primary',\n    'none' => 'None',\n    'cancel' => 'Cancel',\n    'created_at' => 'Created At',\n    'action' => 'Action',\n    'data' => 'Data',\n    'queued' => 'Queued',\n    'last_run' => 'Last Run',\n    'next_run' => 'Next Run',\n    'not_run_yet' => 'Not Run Yet',\n    'yes' => 'Yes',\n    'no' => 'No',\n    'delete' => 'Delete',\n    '2fa' => '2FA',\n    'logout' => 'Logout',\n    'admin_cp' => 'Admin Control Panel',\n    'optional' => 'Optional',\n    'read_only' => 'Read Only',\n    'relation' => 'Relation',\n    'owner' => 'Owner',\n    'admin' => 'Admin',\n    'subuser' => 'Subuser',\n    'captcha_invalid' => 'The provided captcha is invalid.',\n    'tasks' => 'Tasks',\n    'seconds' => 'Seconds',\n    'minutes' => 'Minutes',\n    'under_maintenance' => 'Under Maintenance',\n    'days' => [\n        'sun' => 'Sunday',\n        'mon' => 'Monday',\n        'tues' => 'Tuesday',\n        'wed' => 'Wednesday',\n        'thurs' => 'Thursday',\n        'fri' => 'Friday',\n        'sat' => 'Saturday',\n    ],\n    'last_used' => 'Last Used',\n    'enable' => 'Enable',\n    'disable' => 'Disable',\n    'save' => 'Save',\n    'copyright' => '&copy; 2015 - :year Pterodactyl Software',\n];\n"
  },
  {
    "path": "resources/lang/en/validation.php",
    "content": "<?php\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Validation Language Lines\n    |--------------------------------------------------------------------------\n    |\n    | The following language lines contain the default error messages used by\n    | the validator class. Some of these rules have multiple versions such\n    | as the size rules. Feel free to tweak each of these messages here.\n    |\n    */\n\n    'accepted' => 'The :attribute must be accepted.',\n    'active_url' => 'The :attribute is not a valid URL.',\n    'after' => 'The :attribute must be a date after :date.',\n    'after_or_equal' => 'The :attribute must be a date after or equal to :date.',\n    'alpha' => 'The :attribute may only contain letters.',\n    'alpha_dash' => 'The :attribute may only contain letters, numbers, and dashes.',\n    'alpha_num' => 'The :attribute may only contain letters and numbers.',\n    'array' => 'The :attribute must be an array.',\n    'before' => 'The :attribute must be a date before :date.',\n    'before_or_equal' => 'The :attribute must be a date before or equal to :date.',\n    'between' => [\n        'numeric' => 'The :attribute must be between :min and :max.',\n        'file' => 'The :attribute must be between :min and :max kilobytes.',\n        'string' => 'The :attribute must be between :min and :max characters.',\n        'array' => 'The :attribute must have between :min and :max items.',\n    ],\n    'boolean' => 'The :attribute field must be true or false.',\n    'confirmed' => 'The :attribute confirmation does not match.',\n    'date' => 'The :attribute is not a valid date.',\n    'date_format' => 'The :attribute does not match the format :format.',\n    'different' => 'The :attribute and :other must be different.',\n    'digits' => 'The :attribute must be :digits digits.',\n    'digits_between' => 'The :attribute must be between :min and :max digits.',\n    'dimensions' => 'The :attribute has invalid image dimensions.',\n    'distinct' => 'The :attribute field has a duplicate value.',\n    'email' => 'The :attribute must be a valid email address.',\n    'exists' => 'The selected :attribute is invalid.',\n    'file' => 'The :attribute must be a file.',\n    'filled' => 'The :attribute field is required.',\n    'image' => 'The :attribute must be an image.',\n    'in' => 'The selected :attribute is invalid.',\n    'in_array' => 'The :attribute field does not exist in :other.',\n    'integer' => 'The :attribute must be an integer.',\n    'ip' => 'The :attribute must be a valid IP address.',\n    'json' => 'The :attribute must be a valid JSON string.',\n    'max' => [\n        'numeric' => 'The :attribute may not be greater than :max.',\n        'file' => 'The :attribute may not be greater than :max kilobytes.',\n        'string' => 'The :attribute may not be greater than :max characters.',\n        'array' => 'The :attribute may not have more than :max items.',\n    ],\n    'mimes' => 'The :attribute must be a file of type: :values.',\n    'mimetypes' => 'The :attribute must be a file of type: :values.',\n    'min' => [\n        'numeric' => 'The :attribute must be at least :min.',\n        'file' => 'The :attribute must be at least :min kilobytes.',\n        'string' => 'The :attribute must be at least :min characters.',\n        'array' => 'The :attribute must have at least :min items.',\n    ],\n    'not_in' => 'The selected :attribute is invalid.',\n    'numeric' => 'The :attribute must be a number.',\n    'present' => 'The :attribute field must be present.',\n    'regex' => 'The :attribute format is invalid.',\n    'required' => 'The :attribute field is required.',\n    'required_if' => 'The :attribute field is required when :other is :value.',\n    'required_unless' => 'The :attribute field is required unless :other is in :values.',\n    'required_with' => 'The :attribute field is required when :values is present.',\n    'required_with_all' => 'The :attribute field is required when :values is present.',\n    'required_without' => 'The :attribute field is required when :values is not present.',\n    'required_without_all' => 'The :attribute field is required when none of :values are present.',\n    'same' => 'The :attribute and :other must match.',\n    'size' => [\n        'numeric' => 'The :attribute must be :size.',\n        'file' => 'The :attribute must be :size kilobytes.',\n        'string' => 'The :attribute must be :size characters.',\n        'array' => 'The :attribute must contain :size items.',\n    ],\n    'string' => 'The :attribute must be a string.',\n    'timezone' => 'The :attribute must be a valid zone.',\n    'unique' => 'The :attribute has already been taken.',\n    'uploaded' => 'The :attribute failed to upload.',\n    'url' => 'The :attribute format is invalid.',\n\n    /*\n    |--------------------------------------------------------------------------\n    | Custom Validation Attributes\n    |--------------------------------------------------------------------------\n    |\n    | The following language lines are used to swap attribute place-holders\n    | with something more reader friendly such as E-Mail Address instead\n    | of \"email\". This simply helps us make messages a little cleaner.\n    |\n    */\n\n    'attributes' => [],\n\n    // Internal validation logic for Pterodactyl\n    'internal' => [\n        'variable_value' => ':env variable',\n        'invalid_password' => 'The password provided was invalid for this account.',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/zh/activity.php",
    "content": "<?php\n\n/**\n * Contains all of the translation strings for different activity log\n * events. These should be keyed by the value in front of the colon (:)\n * in the event name. If there is no colon present, they should live at\n * the top level.\n */\nreturn [\n    'auth' => [\n        'fail' => '登录失败',\n        'success' => '已登入',\n        'password-reset' => '重设密码',\n        'reset-password' => '请求密码重置',\n        'checkpoint' => '请求动态口令认证',\n        'recovery-token' => '使用了动态口令恢复代码',\n        'token' => '正确输入了动态口令',\n        'ip-blocked' => '阻止不在IP白名单里的请求',\n        'sftp' => [\n            'fail' => 'SFTP 登录失败',\n        ],\n    ],\n    'user' => [\n        'account' => [\n            'email-changed' => '已将电子邮箱从 :old 更改为 :new',\n            'password-changed' => '已更改密码',\n        ],\n        'api-key' => [\n            'create' => '创建新的 API 密钥 :identifier',\n            'delete' => '已删除 API 密钥 :identifier',\n        ],\n        'ssh-key' => [\n            'create' => '将 SSH 私钥 :fingerprint 添加到帐户',\n            'delete' => '从帐户中删除了 SSH 私钥 :fingerprint',\n        ],\n        'two-factor' => [\n            'create' => '启用动态口令认证',\n            'delete' => '禁用动态口令认证',\n        ],\n    ],\n    'server' => [\n        'reinstall' => '重装服务器',\n        'console' => [\n            'command' => '在服务器上执行 \":command\"',\n        ],\n        'power' => [\n            'start' => '启动了服务器',\n            'stop' => '停止了服务器',\n            'restart' => '重启了服务器',\n            'kill' => '强制停止了服务器',\n        ],\n        'backup' => [\n            'download' => '下载了 :name 备份',\n            'delete' => '删除了 :name 备份',\n            'restore' => '恢复了 :name 备份 (已删除文件: :truncate)',\n            'restore-complete' => '已成功恢复 :name 备份',\n            'restore-failed' => ':name 备份恢复失败',\n            'start' => ':name 开始了新的一轮备份',\n            'complete' => '已将 :name 备份标记为完成',\n            'fail' => '已将 :name 备份标记为失败',\n            'lock' => '锁定了 :name 备份',\n            'unlock' => '解锁了 :name 备份',\n        ],\n        'database' => [\n            'create' => '创建新数据库 :name',\n            'rotate-password' => '为数据库 :name 轮换密码',\n            'delete' => '已删除数据库 :name',\n        ],\n        'file' => [\n            'compress_one' => '压缩了 :directory:file',\n            'compress_other' => '在 :directory 路径下压缩了 :count 个文件',\n            'read' => '查看了 :file 的内容',\n            'copy' => '创建了 :file 的副本',\n            'create-directory' => '已创建目录 :directory:name',\n            'decompress' => '解压了 :directory 路径下的 :files',\n            'delete_one' => '删除了 :directory:files.0',\n            'delete_other' => '删除了 :directory 路径下的 :count 个文件',\n            'download' => '下载 :file',\n            'pull' => '从 :url 下载远程文件到 :directory 路径下',\n            'rename_one' => '将 :directory:files.0.from 重命名为 :directory:files.0.to',\n            'rename_other' => '在 :directory 路径下重命名了 :count 个文件',\n            'write' => '写了一些新内容到 :file 中',\n            'upload' => '上传了一些文件',\n            'uploaded' => '已上传 :directory:file',\n        ],\n        'sftp' => [\n            'denied' => '由于权限原因阻止了 SFTP 访问',\n            'create_one' => '创建了 :files.0',\n            'create_other' => '创建了新的 :count 文件',\n            'write_one' => '修改了 :files.0 的内容',\n            'write_other' => '修改了 :count 文件的内容',\n            'delete_one' => '删除了 :files.0',\n            'delete_other' => '删除了 :count 文件',\n            'create-directory_one' => '创建了 :files.0 目录',\n            'create-directory_other' => '创建了 :count 个目录',\n            'rename_one' => '将 :files.0.from 重命名为 :files.0.to',\n            'rename_other' => '重命名或移动了 :count 个文件',\n        ],\n        'allocation' => [\n            'create' => '添加 :allocation 到服务器',\n            'notes' => '将 :allocation 的备注从 \":old\" 更新为 \":new\"',\n            'primary' => '将 :allocation 设置为服务器首选',\n            'delete' => '删除了 :allocation 分配',\n        ],\n        'schedule' => [\n            'create' => '创建了 :name 计划',\n            'update' => '更新了 :name 计划',\n            'execute' => '手动执行了 :name 计划',\n            'delete' => '删除了 :name 计划',\n        ],\n        'task' => [\n            'create' => '为 :name 计划创建了一个新的 \":action\" 任务',\n            'update' => '更新了 :name 计划的 \":action\" 任务',\n            'delete' => '删除了 :name 计划的一个任务',\n        ],\n        'settings' => [\n            'rename' => '将服务器从 :old 重命名为 :new',\n            'description' => '将服务器描述从 :old 更改为 :new',\n        ],\n        'startup' => [\n            'edit' => '将 :variable 变量从 \":old\" 更改为 \":new\"',\n            'image' => '将服务器的 Docker 映像从 :old 更新为 :new',\n            'egg-change' => '将服务器预设从 :old 更改为 :new',\n        ],\n        'subuser' => [\n            'create' => '将 :email 添加为子用户',\n            'update' => '更新了 :email 的子用户权限',\n            'delete' => '将 :email 从子用户中删除',\n        ],\n    ],\n];\n"
  },
  {
    "path": "resources/lang/zh/admin/nests.php",
    "content": "<?php\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    'notices' => [\n        'created' => '已成功创建一个新的 :name 预设组。',\n        'deleted' => '已成功响应面板请求，删除该预设组。',\n        'updated' => '已成功更新预设组配置选项。',\n    ],\n    'eggs' => [\n        'notices' => [\n            'imported' => '已成功导入此预设及其相关变量。',\n            'updated_via_import' => '此预设已使用提供的文件进行了更新。',\n            'deleted' => '已成功响应面板请求，删除该预设。',\n            'updated' => '预设配置已成功更新。',\n            'script_updated' => '预设的安装脚本已更新，并将在安装服务器时运行。',\n            'egg_created' => '一个新的预设成功出炉啦。如果你要应用此新预设，记得将需要应用的服务器重新启动哦，包括运行中或未运行的。',\n        ],\n    ],\n    'variables' => [\n        'notices' => [\n            'variable_deleted' => '变量 \":variable\" 已被删除，一旦重建将不再为服务器所用。',\n            'variable_updated' => '变量 \":variable\" 已更新。您需要重建使用此变量的服务器才能应用更改。',\n            'variable_created' => '已成功创建新变量并将其分配给此预设。',\n        ],\n    ],\n];\n"
  },
  {
    "path": "resources/lang/zh/admin/node.php",
    "content": "<?php\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    'validation' => [\n        'fqdn_not_resolvable' => '提供的 域名(FQDN) 或 IP 地址无法解析为有效的 IP 地址。',\n        'fqdn_required_for_ssl' => '需要解析为公网 IP 地址的完全限定域名才能为此节点使用 SSL。',\n    ],\n    'notices' => [\n        'allocations_added' => '分配已成功添加到此节点。',\n        'node_deleted' => '节点已成功从面板中删除。',\n        'location_required' => '您必须至少配置一个地域，然后才能将节点添加到此面板。',\n        'node_created' => '成功创建新节点。您可以通过访问“配置”选项卡自动配置此机器上的守护程序。<strong>您必须先分配至少一个 IP 地址和端口，然后才能添加任意服务器。</strong>',\n        'node_updated' => '节点信息已更新。如果更改了任何守护程序的设置，您将需要重新启动它以使这些更改生效。',\n        'unallocated_deleted' => '删除了 <code>:ip</code> 的所有未分配端口。',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/zh/admin/server.php",
    "content": "<?php\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    'exceptions' => [\n        'no_new_default_allocation' => '您正在试图删除此服务器的默认分配，但没有可供使用的备用分配。',\n        'marked_as_failed' => '由于该服务器之前被标记为安装失败。在此状态下无法切换当前状态。',\n        'bad_variable' => ':name 变量存在验证错误。',\n        'daemon_exception' => '尝试与守护程序通信时出现异常，导致 HTTP/:code 响应代码。已记录此异常。(请求 id: :request_id)',\n        'default_allocation_not_found' => '在此服务器的分配中找不到所请求的默认分配。',\n    ],\n    'alerts' => [\n        'startup_changed' => '该服务器的启动配置已经更新。如果此服务器的预设组或预设被更改，现在将进行重新安装。',\n        'server_deleted' => '服务器已成功从系统中删除。',\n        'server_created' => '服务器已在面板上成功创建。请允许守护进程用几分钟的时间来完成安装此服务器。',\n        'build_updated' => '此服务器的构建配置已更新。某些更改可能需要重新启动才能生效。',\n        'suspension_toggled' => '服务器已从冻结状态更改为 :status。',\n        'rebuild_on_boot' => '该服务器已标记为需要 Docker 容器重建。这将在下次启动服务器时执行该操作。',\n        'install_toggled' => '该服务器的安装状态已被切换。',\n        'server_reinstalled' => '此服务器已进入等候队列，马上重新安装。',\n        'details_updated' => '服务器详细信息已成功更新。',\n        'docker_image_updated' => '已成功更改用于此服务器的默认 Docker 镜像。需要重新启动才能应用此更改。',\n        'node_required' => '您必须至少配置一个节点，然后才能将服务器添加到此面板。',\n        'transfer_nodes_required' => '您必须至少配置两个节点，然后才能转移服务器。',\n        'transfer_started' => '服务器转移已开始。',\n        'transfer_not_viable' => '您选择的节点没有足够的存储空间或内存来容纳此服务器。',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/zh/admin/user.php",
    "content": "<?php\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    'exceptions' => [\n        'delete_self' => '您不能删除自己的账户。',\n        'user_has_servers' => '无法删除账户下有服务器的用户，请将其全部删除，然后再继续此操作。',\n    ],\n    'notices' => [\n        'account_created' => '已成功创建帐户。',\n        'account_updated' => '帐户已成功更新。',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/zh/auth.php",
    "content": "<?php\n\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    'sign_in' => '登入',\n    'go_to_login' => '前往登录',\n    'failed' => '用户名或密码错误。',\n\n    'forgot_password' => [\n        'label' => '忘记密码？',\n        'label_help' => '输入您帐户的电子邮箱地址用来接收重置密码的说明。',\n        'button' => '找回账户',\n    ],\n\n    'reset_password' => [\n        'button' => '重置并登录',\n    ],\n\n    'two_factor' => [\n        'label' => '动态口令',\n        'label_help' => '此帐户需要进行动态口令认证才能继续。请输入您设备生成的验证码以完成此登录。',\n        'checkpoint_failed' => '动态口令无效。',\n    ],\n\n    'throttle' => '登录尝试次数过多。请在 :seconds 秒后重试。',\n    'password_requirements' => '密码长度必须至少为 8 个字符，并且对于本站来说应该是独一无二的。',\n    '2fa_must_be_enabled' => '管理员要求您的帐户必须启用动态口令认证才能正常使用面板',\n];\n"
  },
  {
    "path": "resources/lang/zh/command/messages.php",
    "content": "<?php\n\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    'location' => [\n        'no_location_found' => '找不到与提供的标识码匹配的记录。',\n        'ask_short' => '地域标识码',\n        'ask_long' => '地域描述',\n        'created' => '已成功创建 ID 为 :id 的新地域 (:name)。',\n        'deleted' => '已成功删除请求的地域。',\n    ],\n    'user' => [\n        'search_users' => '输入用户名、用户 ID 或电子邮箱地址',\n        'select_search_user' => '要删除的用户ID (输入\\'0\\'重新搜索)',\n        'deleted' => '已成功将该用户从面板中删除。',\n        'confirm_delete' => '您确定要从面板中删除此用户吗？',\n        'no_users_found' => '提供的搜索词未能找到相符的用户。',\n        'multiple_found' => '提供的搜索词找到多个帐户，由于 --no-interaction 标签而无法删除用户。',\n        'ask_admin' => '此用户是否为管理员？',\n        'ask_email' => '电子邮箱地址',\n        'ask_username' => '用户名',\n        'ask_name_first' => '名字',\n        'ask_name_last' => '姓氏',\n        'ask_password' => '密码',\n        'ask_password_tip' => '如果您想使用通过电子邮件发送给用户的随机密码创建一个帐户，请重新运行此命令 (CTRL+C) 并传递 `--no-password` 标签。',\n        'ask_password_help' => '密码长度必须至少为 8 个字符，并且至少包含一个大写字母和数字。',\n        '2fa_help_text' => [\n            '如果启用，此命令将禁用用户帐户的动态口令认证。仅当用户被锁定在其帐户之外时，才应将其用作帐户恢复命令。',\n            '如果这不是您想要执行的操作，请按 CTRL+C 退出此过程。',\n        ],\n        '2fa_disabled' => '已为 :email 禁用动态口令认证。',\n    ],\n    'schedule' => [\n        'output_line' => '为 `:schedule` (:hash) 中的第一个任务分配作业。',\n    ],\n    'maintenance' => [\n        'deleting_service_backup' => '删除服务备份文件 :file。',\n    ],\n    'server' => [\n        'rebuild_failed' => '在节点 \":node\" 上对 \":name\" (#:id) 的重建请求失败并出现错误：:message',\n        'reinstall' => [\n            'failed' => '在节点 \":node\" 上重新安装 \":name\" (#:id) 请求失败并出现错误: :message',\n            'confirm' => '您即将针对一组服务器重新安装。你想继续吗？',\n        ],\n        'power' => [\n            'confirm' => '您即将对 :count 服务器执行 :action。你想继续吗？',\n            'action_failed' => '节点 \":node\" 上 \":name\" (#:id) 的电源操作请求失败并出现错误: :message',\n        ],\n    ],\n    'environment' => [\n        'mail' => [\n            'ask_smtp_host' => 'SMTP 主机 (例如 smtp.gmail.com)',\n            'ask_smtp_port' => 'SMTP 端口',\n            'ask_smtp_username' => 'SMTP 用户名',\n            'ask_smtp_password' => 'SMTP 密码',\n            'ask_mailgun_domain' => 'Mailgun 域名',\n            'ask_mailgun_endpoint' => 'Mailgun 节点',\n            'ask_mailgun_secret' => 'Mailgun 密钥',\n            'ask_mandrill_secret' => 'Mandrill 密钥',\n            'ask_postmark_username' => 'Postmark API 密钥',\n            'ask_driver' => '应该使用哪个驱动程序来发送电子邮件?',\n            'ask_mail_from' => '发件人地址',\n            'ask_mail_name' => '发件人',\n            'ask_encryption' => '加密方式',\n        ],\n    ],\n];\n"
  },
  {
    "path": "resources/lang/zh/dashboard/account.php",
    "content": "<?php\n\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    'email' => [\n        'title' => '更新您的电子邮箱地址',\n        'updated' => '您的电子邮箱地址已更新。',\n    ],\n    'password' => [\n        'title' => '更改您的密码',\n        'requirements' => '您的新密码长度应至少为 8 个字符。',\n        'updated' => '您的密码已更新。',\n    ],\n    'two_factor' => [\n        'button' => '配置动态口令认证',\n        'disabled' => '您的帐户已禁用动态口令认证。登录时将不再提示您提供口令。',\n        'enabled' => '您的帐户已启用动态口令认证！ 从现在开始，登录时，您将需要提供您设备上生成的口令。',\n        'invalid' => '提供的口令无效。',\n        'setup' => [\n            'title' => '设置动态口令认证',\n            'help' => '无法扫码？ 将以下代码输入到您的应用程序中：',\n            'field' => '输入口令',\n        ],\n        'disable' => [\n            'title' => '禁用动态口令认证',\n            'field' => '输入口令',\n        ],\n    ],\n];\n"
  },
  {
    "path": "resources/lang/zh/dashboard/index.php",
    "content": "<?php\n\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    'search' => '搜索服务器...',\n    'no_matches' => '没有找到与提供的搜索条件相匹配的服务器。',\n    'cpu_title' => 'CPU',\n    'memory_title' => '内存',\n];\n"
  },
  {
    "path": "resources/lang/zh/exceptions.php",
    "content": "<?php\n\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    'daemon_connection_failed' => '尝试与守护程序通信时出现异常，导致 HTTP/:code 响应代码。已记录此异常。',\n    'node' => [\n        'servers_attached' => '一个节点必须没有关联任何服务器时才能被删除。',\n        'daemon_off_config_updated' => '守护程序配置<strong>已更新</strong>，但是在尝试自动更新守护程序上的配置文件时遇到错误。您需要手动更新配置文件 (config.yml) 以使守护程序应用这些更改。',\n    ],\n    'allocations' => [\n        'server_using' => '此分配正在被一台服务器使用，只有此分配未被服务器使用时才能删除此分配。',\n        'too_many_ports' => '不支持一次在单个范围内添加超过 1000 个端口。',\n        'invalid_mapping' => '为 :port 提供的映射无效并且无法处理。',\n        'cidr_out_of_range' => 'CIDR 表示法只允许 /25 于 /32 之间的掩码。',\n        'port_out_of_range' => '分配中的端口必须大于 1024 且小于或等于 65535。',\n    ],\n    'nest' => [\n        'delete_has_servers' => '无法从面板中删除关联了服务器的预设组。',\n        'egg' => [\n            'delete_has_servers' => '无法从面板中删除关联了服务器的预设。',\n            'invalid_copy_id' => '选择用于复制脚本的预设不存在，或正在复制脚本本身。',\n            'must_be_child' => '此预设的 \"复制设置自\" 指令必须是选定预设组的子选项。',\n            'has_children' => '此预设是一个或多个其他预设的父级。请在删除此预设之前删除这些预设。',\n        ],\n        'variables' => [\n            'env_not_unique' => '环境变量 :name 对于此预设必须是独一无二的。',\n            'reserved_name' => '环境变量 :name 是受保护的，不能给分配变量。',\n            'bad_validation_rule' => '验证规则 \":rule\" 不是此应用程序的有效规则。',\n        ],\n        'importer' => [\n            'json_error' => '尝试解析 JSON 文件时出错：:error。',\n            'file_error' => '提供的 JSON 文件无效。',\n            'invalid_json_provided' => '提供的 JSON 文件是不可识别的格式。',\n        ],\n    ],\n    'subusers' => [\n        'editing_self' => '不允许您修改自己的子用户帐户。',\n        'user_is_owner' => '您不能将服务器所有者添加为此服务器的子用户。',\n        'subuser_exists' => '具有该电子邮箱地址的用户已被指定为该服务器的子用户。',\n    ],\n    'databases' => [\n        'delete_has_databases' => '无法删除关联了数据库的数据库主机服务器。',\n    ],\n    'tasks' => [\n        'chain_interval_too_long' => '链式任务的最大间隔时间是 15 分钟。',\n    ],\n    'locations' => [\n        'has_nodes' => '无法删除关联了节点的地域。',\n    ],\n    'users' => [\n        'node_revocation_failed' => '无法撤销 <a href=\":link\">节点 #:node</a> 上的密钥。:error',\n    ],\n    'deployment' => [\n        'no_viable_nodes' => '找不到满足自动部署要求的节点。',\n        'no_viable_allocations' => '未找到满足自动部署要求的分配。',\n    ],\n    'api' => [\n        'resource_not_found' => '请求的资源在此服务器上不存在。',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/zh/pagination.php",
    "content": "<?php\n\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Pagination Language Lines\n    |--------------------------------------------------------------------------\n    |\n    | The following language lines are used by the paginator library to build\n    | the simple pagination links. You are free to change them to anything\n    | you want to customize your views to better match your application.\n    |\n    */\n\n    'previous' => '&laquo; 上一页',\n    'next' => '下一页 &raquo;',\n];\n"
  },
  {
    "path": "resources/lang/zh/passwords.php",
    "content": "<?php\n\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Password Reset Language Lines\n    |--------------------------------------------------------------------------\n    |\n    | The following language lines are the default lines which match reasons\n    | that are given by the password broker for a password update attempt\n    | has failed, such as for an invalid token or invalid new password.\n    |\n    */\n    'password' => '密码必须至少为六个字符并与确认信息一致。',\n    'reset' => '密码重置成功！',\n    'sent' => '密码重置邮件已发送给您！',\n    'token' => '密码重置令牌无效。',\n    'user' => '请检查邮箱是否正确，我们找不到该邮箱对应的用户。',\n];\n"
  },
  {
    "path": "resources/lang/zh/server/users.php",
    "content": "<?php\n\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    'permissions' => [\n        'websocket_*' => '允许访问此服务器的 websocket。',\n        'control_console' => '允许用户通过控制台向服务器实例发送命令。',\n        'control_start' => '允许用户在服务器停止时启动它。',\n        'control_stop' => '允许用户停止正在运行的服务器。',\n        'control_restart' => '允许用户重新启动服务器实例。',\n        'control_kill' => '允许用户强制停止服务器实例。',\n        'user_create' => '允许用户为服务器创建新的子用户。',\n        'user_read' => '允许用户查看与此服务器关联的子用户权限。',\n        'user_update' => '允许用户修改与此服务器关联的子用户。',\n        'user_delete' => '允许用户删除与此服务器关联的子用户。',\n        'file_create' => '允许用户通过面板或直接上传、创建其他文件和文件夹。',\n        'file_read' => '允许用户查看目录的内容，但不能查看或下载文件的内容。',\n        'file_update' => '允许用户更新现有文件或目录的内容。',\n        'file_delete' => '允许用户删除文件或目录。',\n        'file_archive' => '允许用户压缩系统上的的文件以及解压系统上的现有压缩文件。',\n        'file_sftp' => '允许用户使用其他分配的文件权限连接到 SFTP 并管理服务器文件。',\n        'allocation_read' => '允许访问服务器分配管理页面。',\n        'allocation_update' => '允许用户修改服务器分配的权限。',\n        'database_create' => '允许用户为服务器创建新数据库的权限。',\n        'database_read' => '允许用户查看服务器数据库的权限。',\n        'database_update' => '允许用户修改数据库的权限。如果用户没有 \"VIEW_PASSWORD\" 权限，那么他将无法修改密码。',\n        'database_delete' => '允许用户删除数据库实例的权限。',\n        'database_view_password' => '允许用户在系统中查看数据库密码。',\n        'schedule_create' => '允许用户为此服务器创建新计划。',\n        'schedule_read' => '允许用户查看此服务器的计划和与其关联的任务。',\n        'schedule_update' => '允许用户更新此服务器的计划和计划中的任务。',\n        'schedule_delete' => '允许用户删除此服务器的计划。',\n    ],\n];\n"
  },
  {
    "path": "resources/lang/zh/strings.php",
    "content": "<?php\n\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\nreturn [\n    'email' => '电子邮箱',\n    'email_address' => '电子邮箱地址',\n    'user_identifier' => '用户名或电子邮箱',\n    'password' => '密码',\n    'new_password' => '新密码',\n    'confirm_password' => '确认新密码',\n    'login' => '登录',\n    'home' => '主页',\n    'servers' => '服务器',\n    'id' => 'ID',\n    'name' => '名称',\n    'node' => '节点',\n    'connection' => '连接地址',\n    'memory' => '内存',\n    'cpu' => 'CPU',\n    'disk' => '存储空间',\n    'status' => '状态',\n    'search' => '搜索',\n    'suspended' => '已冻结',\n    'account' => '账户',\n    'security' => '安全性',\n    'ip' => 'IP 地址',\n    'last_activity' => '上次运行',\n    'revoke' => '撤销',\n    '2fa_token' => '动态口令',\n    'submit' => '提交',\n    'close' => '关闭',\n    'settings' => '设置',\n    'configuration' => '配置',\n    'sftp' => 'SFTP',\n    'databases' => '数据库',\n    'memo' => '备忘录',\n    'created' => '已创建',\n    'expires' => '已过期',\n    'public_key' => '令牌',\n    'api_access' => 'API 访问',\n    'never' => '从来没有',\n    'sign_out' => '登出',\n    'admin_control' => '管理员控制台',\n    'required' => '必需',\n    'port' => '端口',\n    'username' => '用户名',\n    'database' => '数据库',\n    'new' => '新建',\n    'danger' => '危险',\n    'create' => '创建',\n    'select_all' => '全选',\n    'select_none' => '取消全选',\n    'alias' => '别名',\n    'primary' => '首选',\n    'make_primary' => '设为首选',\n    'none' => '无',\n    'cancel' => '取消',\n    'created_at' => '创建于',\n    'action' => '动作',\n    'data' => '数据',\n    'queued' => '队列',\n    'last_run' => '上次运行于',\n    'next_run' => '下次运行于',\n    'not_run_yet' => '从未运行',\n    'yes' => '是',\n    'no' => '否',\n    'delete' => '删除',\n    '2fa' => '动态口令认证',\n    'logout' => '登出',\n    'admin_cp' => '管理员控制面板',\n    'optional' => '可选',\n    'read_only' => '只读',\n    'relation' => '关联',\n    'owner' => '所有者',\n    'admin' => '管理员',\n    'subuser' => '子用户',\n    'captcha_invalid' => '提供的验证码无效。',\n    'tasks' => '任务',\n    'seconds' => '秒',\n    'minutes' => '分钟',\n    'under_maintenance' => '正在维护中',\n    'days' => [\n        'sun' => '星期天',\n        'mon' => '星期一',\n        'tues' => '星期二',\n        'wed' => '星期三',\n        'thurs' => '星期四',\n        'fri' => '星期五',\n        'sat' => '星期六',\n    ],\n    'last_used' => '上次使用',\n    'enable' => '启用',\n    'disable' => '禁用',\n    'save' => '保存',\n    'copyright' => '&copy; 2015 - :year Pterodactyl Software',\n];\n"
  },
  {
    "path": "resources/lang/zh/validation.php",
    "content": "<?php\n\n/**\n * Pterodactyl CHINA - Panel\n * Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com>.\n *\n * This software is licensed under the terms of the MIT license.\n * https://opensource.org/licenses/MIT\n */\n\nreturn [\n    /*\n    |--------------------------------------------------------------------------\n    | Validation Language Lines\n    |--------------------------------------------------------------------------\n    |\n    | The following language lines contain the default error messages used by\n    | the validator class. Some of these rules have multiple versions such\n    | as the size rules. Feel free to tweak each of these messages here.\n    |\n    */\n\n    'accepted' => '您必须接受 :attribute。',\n    'active_url' => ':attribute 不是一个有效的网址。',\n    'after' => ':attribute 必须要晚于 :date。',\n    'after_or_equal' => ':attribute 必须要等于 :date 或更晚。',\n    'alpha' => ':attribute 只能由字母组成。',\n    'alpha_dash' => ':attribute 只能由字母、数字、短划线(-)和下划线(_)组成。',\n    'alpha_num' => ':attribute 只能由字母和数字组成。',\n    'array' => ':attribute 必须是一个数组。',\n    'before' => ':attribute 必须要早于 :date。',\n    'before_or_equal' => ':attribute 必须要等于 :date 或更早。',\n    'between' => [\n        'numeric' => ':attribute 必须介于 :min - :max 之间。',\n        'file' => ':attribute 必须介于 :min - :max KB 之间。',\n        'string' => ':attribute 必须介于 :min - :max 个字符之间。',\n        'array' => ':attribute 必须只有 :min - :max 个单元。',\n    ],\n    'boolean' => ':attribute 必须为布尔值。',\n    'confirmed' => ':attribute 两次输入不一致。',\n    'date' => ':attribute 不是一个有效的日期。',\n    'date_format' => ':attribute 的格式必须为 :format。',\n    'different' => ':attribute 和 :other 必须不同。',\n    'digits' => ':attribute 必须是 :digits 位数字。',\n    'digits_between' => ':attribute 必须是介于 :min 和 :max 位的数字。',\n    'dimensions' => ':attribute 图片尺寸不正确。',\n    'distinct' => ':attribute 已经存在。',\n    'email' => ':attribute 不是一个合法的邮箱。',\n    'exists' => ':attribute 不存在。',\n    'file' => ':attribute 必须是文件。',\n    'filled' => ':attribute 不能为空。',\n    'image' => ':attribute 必须是图片。',\n    'in' => '已选的属性 :attribute 无效。',\n    'in_array' => ':attribute 必须在 :other 中。',\n    'integer' => ':attribute 必须是整数。',\n    'ip' => ':attribute 必须是有效的 IP 地址。',\n    'json' => ':attribute 必须是正确的 JSON 格式。',\n    'max' => [\n        'numeric' => ':attribute 不能大于 :max。',\n        'file' => ':attribute 不能大于 :max KB。',\n        'string' => ':attribute 不能大于 :max 个字符。',\n        'array' => ':attribute 最多只有 :max 个单元。',\n    ],\n    'mimes' => ':attribute 必须是一个 :values 类型的文件。',\n    'mimetypes' => ':attribute 必须是一个 :values 类型的文件。',\n    'min' => [\n        'numeric' => ':attribute 必须大于等于 :min。',\n        'file' => ':attribute 大小不能小于 :min KB。',\n        'string' => ':attribute 至少为 :min 个字符。',\n        'array' => ':attribute 至少有 :min 个单元。',\n    ],\n    'not_in' => '已选的属性 :attribute 非法。',\n    'numeric' => ':attribute 必须是一个数字。',\n    'present' => ':attribute 必须存在。',\n    'regex' => ':attribute 格式不正确。',\n    'required' => ':attribute 不能为空。',\n    'required_if' => '当 :other 为 :value 时 :attribute 不能为空。',\n    'required_unless' => '当 :other 不为 :values 时 :attribute 不能为空。',\n    'required_with' => '当 :values 存在时 :attribute 不能为空。',\n    'required_with_all' => '当 :values 存在时 :attribute 不能为空。',\n    'required_without' => '当 :values 不存在时 :attribute 不能为空。',\n    'required_without_all' => '当 :values 都不存在时 :attribute 不能为空。',\n    'same' => ':attribute 和 :other 必须相同。',\n    'size' => [\n        'numeric' => ':attribute 大小必须为 :size。',\n        'file' => ':attribute 大小必须为 :size KB。',\n        'string' => ':attribute 必须是 :size 个字符。',\n        'array' => ':attribute 必须为 :size 个单元。',\n    ],\n    'string' => ':attribute 必须是一个字符串。',\n    'timezone' => ':attribute 必须是一个合法的时区值。',\n    'unique' => ':attribute 已经存在。',\n    'uploaded' => ':attribute 上传失败。',\n    'url' => ':attribute 格式不正确。',\n\n    /*\n    |--------------------------------------------------------------------------\n    | Custom Validation Attributes\n    |--------------------------------------------------------------------------\n    |\n    | The following language lines are used to swap attribute place-holders\n    | with something more reader friendly such as E-Mail Address instead\n    | of \"email\". This simply helps us make messages a little cleaner.\n    |\n    */\n\n    'attributes' => [],\n\n    // Internal validation logic for Pterodactyl\n    'internal' => [\n        'variable_value' => ':env 变量',\n        'invalid_password' => '提供的密码对此帐户无效。',\n    ],\n];\n"
  },
  {
    "path": "resources/scripts/TransitionRouter.tsx",
    "content": "import React from 'react';\nimport { Route } from 'react-router';\nimport { SwitchTransition } from 'react-transition-group';\nimport Fade from '@/components/elements/Fade';\nimport styled from 'styled-components/macro';\nimport tw from 'twin.macro';\n\nconst StyledSwitchTransition = styled(SwitchTransition)`\n    ${tw`relative`};\n\n    & section {\n        ${tw`absolute w-full top-0 left-0`};\n    }\n`;\n\nconst TransitionRouter: React.FC = ({ children }) => {\n    return (\n        <Route\n            render={({ location }) => (\n                <StyledSwitchTransition>\n                    <Fade timeout={150} key={location.pathname + location.search} in appear unmountOnExit>\n                        <section>{children}</section>\n                    </Fade>\n                </StyledSwitchTransition>\n            )}\n        />\n    );\n};\n\nexport default TransitionRouter;\n"
  },
  {
    "path": "resources/scripts/__mocks__/file.ts",
    "content": "module.exports = 'test-file-stub';\n"
  },
  {
    "path": "resources/scripts/api/account/activity.ts",
    "content": "import useSWR, { ConfigInterface, responseInterface } from 'swr';\nimport { ActivityLog, Transformers } from '@definitions/user';\nimport { AxiosError } from 'axios';\nimport http, { PaginatedResult, QueryBuilderParams, withQueryBuilderParams } from '@/api/http';\nimport { toPaginatedSet } from '@definitions/helpers';\nimport useFilteredObject from '@/plugins/useFilteredObject';\nimport { useUserSWRKey } from '@/plugins/useSWRKey';\n\nexport type ActivityLogFilters = QueryBuilderParams<'ip' | 'event', 'timestamp'>;\n\nconst useActivityLogs = (\n    filters?: ActivityLogFilters,\n    config?: ConfigInterface<PaginatedResult<ActivityLog>, AxiosError>\n): responseInterface<PaginatedResult<ActivityLog>, AxiosError> => {\n    const key = useUserSWRKey(['account', 'activity', JSON.stringify(useFilteredObject(filters || {}))]);\n\n    return useSWR<PaginatedResult<ActivityLog>>(\n        key,\n        async () => {\n            const { data } = await http.get('/api/client/account/activity', {\n                params: {\n                    ...withQueryBuilderParams(filters),\n                    include: ['actor'],\n                },\n            });\n\n            return toPaginatedSet(data, Transformers.toActivityLog);\n        },\n        { revalidateOnMount: false, ...(config || {}) }\n    );\n};\n\nexport { useActivityLogs };\n"
  },
  {
    "path": "resources/scripts/api/account/createApiKey.ts",
    "content": "import http from '@/api/http';\nimport { ApiKey, rawDataToApiKey } from '@/api/account/getApiKeys';\n\nexport default (description: string, allowedIps: string): Promise<ApiKey & { secretToken: string }> => {\n    return new Promise((resolve, reject) => {\n        http.post('/api/client/account/api-keys', {\n            description,\n            allowed_ips: allowedIps.length > 0 ? allowedIps.split('\\n') : [],\n        })\n            .then(({ data }) =>\n                resolve({\n                    ...rawDataToApiKey(data.attributes),\n                    // eslint-disable-next-line camelcase\n                    secretToken: data.meta?.secret_token ?? '',\n                })\n            )\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/account/deleteApiKey.ts",
    "content": "import http from '@/api/http';\n\nexport default (identifier: string): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.delete(`/api/client/account/api-keys/${identifier}`)\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/account/disableAccountTwoFactor.ts",
    "content": "import http from '@/api/http';\n\nfunction disableAccountTwoFactor(password: string): Promise<void> {\n    return new Promise((resolve, reject) => {\n        http.post('/api/client/account/two-factor/disable', { password })\n            .then(() => resolve())\n            .catch(reject);\n    });\n}\n\nexport default disableAccountTwoFactor;\n"
  },
  {
    "path": "resources/scripts/api/account/enableAccountTwoFactor.ts",
    "content": "import http from '@/api/http';\n\nexport default async (code: string, password: string): Promise<string[]> => {\n    const { data } = await http.post('/api/client/account/two-factor', { code, password });\n\n    return data.attributes.tokens;\n};\n"
  },
  {
    "path": "resources/scripts/api/account/getApiKeys.ts",
    "content": "import http from '@/api/http';\n\nexport interface ApiKey {\n    identifier: string;\n    description: string;\n    allowedIps: string[];\n    createdAt: Date | null;\n    lastUsedAt: Date | null;\n}\n\nexport const rawDataToApiKey = (data: any): ApiKey => ({\n    identifier: data.identifier,\n    description: data.description,\n    allowedIps: data.allowed_ips,\n    createdAt: data.created_at ? new Date(data.created_at) : null,\n    lastUsedAt: data.last_used_at ? new Date(data.last_used_at) : null,\n});\n\nexport default (): Promise<ApiKey[]> => {\n    return new Promise((resolve, reject) => {\n        http.get('/api/client/account/api-keys')\n            .then(({ data }) => resolve((data.data || []).map((d: any) => rawDataToApiKey(d.attributes))))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/account/getTwoFactorTokenData.ts",
    "content": "import http from '@/api/http';\n\nexport interface TwoFactorTokenData {\n    // eslint-disable-next-line camelcase\n    image_url_data: string;\n    secret: string;\n}\n\nexport default (): Promise<TwoFactorTokenData> => {\n    return new Promise((resolve, reject) => {\n        http.get('/api/client/account/two-factor')\n            .then(({ data }) => resolve(data.data))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/account/ssh-keys.ts",
    "content": "import useSWR, { ConfigInterface } from 'swr';\nimport http, { FractalResponseList } from '@/api/http';\nimport { SSHKey, Transformers } from '@definitions/user';\nimport { AxiosError } from 'axios';\nimport { useUserSWRKey } from '@/plugins/useSWRKey';\n\nconst useSSHKeys = (config?: ConfigInterface<SSHKey[], AxiosError>) => {\n    const key = useUserSWRKey(['account', 'ssh-keys']);\n\n    return useSWR(\n        key,\n        async () => {\n            const { data } = await http.get('/api/client/account/ssh-keys');\n\n            return (data as FractalResponseList).data.map((datum: any) => {\n                return Transformers.toSSHKey(datum.attributes);\n            });\n        },\n        { revalidateOnMount: false, ...(config || {}) }\n    );\n};\n\nconst createSSHKey = async (name: string, publicKey: string): Promise<SSHKey> => {\n    const { data } = await http.post('/api/client/account/ssh-keys', { name, public_key: publicKey });\n\n    return Transformers.toSSHKey(data.attributes);\n};\n\nconst deleteSSHKey = async (fingerprint: string): Promise<void> =>\n    await http.post('/api/client/account/ssh-keys/remove', { fingerprint });\n\nexport { useSSHKeys, createSSHKey, deleteSSHKey };\n"
  },
  {
    "path": "resources/scripts/api/account/updateAccountEmail.ts",
    "content": "import http from '@/api/http';\n\nexport default (email: string, password: string): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.put('/api/client/account/email', { email, password })\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/account/updateAccountPassword.ts",
    "content": "import http from '@/api/http';\n\ninterface Data {\n    current: string;\n    password: string;\n    confirmPassword: string;\n}\n\nexport default ({ current, password, confirmPassword }: Data): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.put('/api/client/account/password', {\n            current_password: current,\n            password: password,\n            password_confirmation: confirmPassword,\n        })\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/auth/login.ts",
    "content": "import http from '@/api/http';\n\nexport interface LoginResponse {\n    complete: boolean;\n    intended?: string;\n    confirmationToken?: string;\n}\n\nexport interface LoginData {\n    username: string;\n    password: string;\n    recaptchaData?: string | null;\n}\n\nexport default ({ username, password, recaptchaData }: LoginData): Promise<LoginResponse> => {\n    return new Promise((resolve, reject) => {\n        http.get('/sanctum/csrf-cookie')\n            .then(() =>\n                http.post('/auth/login', {\n                    user: username,\n                    password,\n                    'g-recaptcha-response': recaptchaData,\n                })\n            )\n            .then((response) => {\n                if (!(response.data instanceof Object)) {\n                    return reject(new Error('An error occurred while processing the login request.'));\n                }\n\n                return resolve({\n                    complete: response.data.data.complete,\n                    intended: response.data.data.intended || undefined,\n                    confirmationToken: response.data.data.confirmation_token || undefined,\n                });\n            })\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/auth/loginCheckpoint.ts",
    "content": "import http from '@/api/http';\nimport { LoginResponse } from '@/api/auth/login';\n\nexport default (token: string, code: string, recoveryToken?: string): Promise<LoginResponse> => {\n    return new Promise((resolve, reject) => {\n        http.post('/auth/login/checkpoint', {\n            confirmation_token: token,\n            authentication_code: code,\n            recovery_token: recoveryToken && recoveryToken.length > 0 ? recoveryToken : undefined,\n        })\n            .then((response) =>\n                resolve({\n                    complete: response.data.data.complete,\n                    intended: response.data.data.intended || undefined,\n                })\n            )\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/auth/performPasswordReset.ts",
    "content": "import http from '@/api/http';\n\ninterface Data {\n    token: string;\n    password: string;\n    passwordConfirmation: string;\n}\n\ninterface PasswordResetResponse {\n    redirectTo?: string | null;\n    sendToLogin: boolean;\n}\n\nexport default (email: string, data: Data): Promise<PasswordResetResponse> => {\n    return new Promise((resolve, reject) => {\n        http.post('/auth/password/reset', {\n            email,\n            token: data.token,\n            password: data.password,\n            password_confirmation: data.passwordConfirmation,\n        })\n            .then((response) =>\n                resolve({\n                    redirectTo: response.data.redirect_to,\n                    sendToLogin: response.data.send_to_login,\n                })\n            )\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/auth/requestPasswordResetEmail.ts",
    "content": "import http from '@/api/http';\n\nexport default (email: string, recaptchaData?: string): Promise<string> => {\n    return new Promise((resolve, reject) => {\n        http.post('/auth/password', { email, 'g-recaptcha-response': recaptchaData })\n            .then((response) => resolve(response.data.status || ''))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/definitions/helpers.ts",
    "content": "import {\n    FractalPaginatedResponse,\n    FractalResponseData,\n    FractalResponseList,\n    getPaginationSet,\n    PaginatedResult,\n} from '@/api/http';\nimport { Model } from '@definitions/index';\n\ntype TransformerFunc<T> = (callback: FractalResponseData) => T;\n\nconst isList = (data: FractalResponseList | FractalResponseData): data is FractalResponseList => data.object === 'list';\n\nfunction transform<T, M>(data: null | undefined, transformer: TransformerFunc<T>, missing?: M): M;\nfunction transform<T, M>(\n    data: FractalResponseData | null | undefined,\n    transformer: TransformerFunc<T>,\n    missing?: M\n): T | M;\nfunction transform<T, M>(\n    data: FractalResponseList | FractalPaginatedResponse | null | undefined,\n    transformer: TransformerFunc<T>,\n    missing?: M\n): T[] | M;\nfunction transform<T>(\n    data: FractalResponseData | FractalResponseList | FractalPaginatedResponse | null | undefined,\n    transformer: TransformerFunc<T>,\n    missing = undefined\n) {\n    if (data === undefined || data === null) {\n        return missing;\n    }\n\n    if (isList(data)) {\n        return data.data.map(transformer);\n    }\n\n    if (!data || !data.attributes || data.object === 'null_resource') {\n        return missing;\n    }\n\n    return transformer(data);\n}\n\nfunction toPaginatedSet<T extends TransformerFunc<Model>>(\n    response: FractalPaginatedResponse,\n    transformer: T\n): PaginatedResult<ReturnType<T>> {\n    return {\n        items: transform(response, transformer) as ReturnType<T>[],\n        pagination: getPaginationSet(response.meta.pagination),\n    };\n}\n\nexport { transform, toPaginatedSet };\n"
  },
  {
    "path": "resources/scripts/api/definitions/index.d.ts",
    "content": "import { MarkRequired } from 'ts-essentials';\nimport { FractalResponseData, FractalResponseList } from '../http';\n\nexport type UUID = string;\nexport type Identifier<P extends string = string> = `${P}_${string}`;\n\n// eslint-disable-next-line @typescript-eslint/no-empty-interface\nexport interface Model {}\n\ninterface ModelWithRelationships extends Model {\n    relationships: Record<string, FractalResponseData | FractalResponseList | undefined>;\n}\n\n/**\n * Allows a model to have optional relationships that are marked as being\n * present in a given pathway. This allows different API calls to specify the\n * \"completeness\" of a response object without having to make every API return\n * the same information, or every piece of logic do explicit null checking.\n *\n * Example:\n *  >> const user: WithLoaded<User, 'servers'> = {};\n *  >> // \"user.servers\" is no longer potentially undefined.\n */\ntype WithLoaded<M extends ModelWithRelationships, R extends keyof M['relationships']> = M & {\n    relationships: MarkRequired<M['relationships'], R>;\n};\n\n/**\n * Helper type that allows you to infer the type of an object by giving\n * it the specific API request function with a return type. For example:\n *\n * type Egg = InferModel<typeof getEgg>;\n */\nexport type InferModel<T extends (...args: any) => any> = ReturnType<T> extends Promise<infer U> ? U : T;\n"
  },
  {
    "path": "resources/scripts/api/definitions/user/index.ts",
    "content": "export * from './models.d';\nexport { default as Transformers, MetaTransformers } from './transformers';\n"
  },
  {
    "path": "resources/scripts/api/definitions/user/models.d.ts",
    "content": "import { Model, UUID } from '@/api/definitions';\nimport { SubuserPermission } from '@/state/server/subusers';\n\ninterface User extends Model {\n    uuid: string;\n    username: string;\n    email: string;\n    image: string;\n    twoFactorEnabled: boolean;\n    createdAt: Date;\n    permissions: SubuserPermission[];\n    can(permission: SubuserPermission): boolean;\n}\n\ninterface SSHKey extends Model {\n    name: string;\n    publicKey: string;\n    fingerprint: string;\n    createdAt: Date;\n}\n\ninterface ActivityLog extends Model<'actor'> {\n    id: string;\n    batch: UUID | null;\n    event: string;\n    ip: string | null;\n    isApi: boolean;\n    description: string | null;\n    properties: Record<string, string | unknown>;\n    hasAdditionalMetadata: boolean;\n    timestamp: Date;\n    relationships: {\n        actor: User | null;\n    };\n}\n"
  },
  {
    "path": "resources/scripts/api/definitions/user/transformers.ts",
    "content": "import * as Models from '@definitions/user/models';\nimport { FractalResponseData } from '@/api/http';\nimport { transform } from '@definitions/helpers';\n\nexport default class Transformers {\n    static toSSHKey = (data: Record<any, any>): Models.SSHKey => {\n        return {\n            name: data.name,\n            publicKey: data.public_key,\n            fingerprint: data.fingerprint,\n            createdAt: new Date(data.created_at),\n        };\n    };\n\n    static toUser = ({ attributes }: FractalResponseData): Models.User => {\n        return {\n            uuid: attributes.uuid,\n            username: attributes.username,\n            email: attributes.email,\n            image: attributes.image,\n            twoFactorEnabled: attributes['2fa_enabled'],\n            permissions: attributes.permissions || [],\n            createdAt: new Date(attributes.created_at),\n            can(permission): boolean {\n                return this.permissions.includes(permission);\n            },\n        };\n    };\n\n    static toActivityLog = ({ attributes }: FractalResponseData): Models.ActivityLog => {\n        const { actor } = attributes.relationships || {};\n\n        return {\n            id: attributes.id,\n            batch: attributes.batch,\n            event: attributes.event,\n            ip: attributes.ip,\n            isApi: attributes.is_api,\n            description: attributes.description,\n            properties: attributes.properties,\n            hasAdditionalMetadata: attributes.has_additional_metadata ?? false,\n            timestamp: new Date(attributes.timestamp),\n            relationships: {\n                actor: transform(actor as FractalResponseData, this.toUser, null),\n            },\n        };\n    };\n}\n\nexport class MetaTransformers {}\n"
  },
  {
    "path": "resources/scripts/api/getServers.ts",
    "content": "import { rawDataToServerObject, Server } from '@/api/server/getServer';\nimport http, { getPaginationSet, PaginatedResult } from '@/api/http';\n\ninterface QueryParams {\n    query?: string;\n    page?: number;\n    type?: string;\n}\n\nexport default ({ query, ...params }: QueryParams): Promise<PaginatedResult<Server>> => {\n    return new Promise((resolve, reject) => {\n        http.get('/api/client', {\n            params: {\n                'filter[*]': query,\n                ...params,\n            },\n        })\n            .then(({ data }) =>\n                resolve({\n                    items: (data.data || []).map((datum: any) => rawDataToServerObject(datum)),\n                    pagination: getPaginationSet(data.meta.pagination),\n                })\n            )\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/getSystemPermissions.ts",
    "content": "import { PanelPermissions } from '@/state/permissions';\nimport http from '@/api/http';\n\nexport default (): Promise<PanelPermissions> => {\n    return new Promise((resolve, reject) => {\n        http.get('/api/client/permissions')\n            .then(({ data }) => resolve(data.attributes.permissions))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/http.ts",
    "content": "import axios, { AxiosInstance } from 'axios';\nimport { store } from '@/state';\n\nconst http: AxiosInstance = axios.create({\n    withCredentials: true,\n    timeout: 20000,\n    headers: {\n        'X-Requested-With': 'XMLHttpRequest',\n        Accept: 'application/json',\n        'Content-Type': 'application/json',\n    },\n});\n\nhttp.interceptors.request.use((req) => {\n    if (!req.url?.endsWith('/resources')) {\n        store.getActions().progress.startContinuous();\n    }\n\n    return req;\n});\n\nhttp.interceptors.response.use(\n    (resp) => {\n        if (!resp.request?.url?.endsWith('/resources')) {\n            store.getActions().progress.setComplete();\n        }\n\n        return resp;\n    },\n    (error) => {\n        store.getActions().progress.setComplete();\n\n        throw error;\n    }\n);\n\nexport default http;\n\n/**\n * Converts an error into a human readable response. Mostly just a generic helper to\n * make sure we display the message from the server back to the user if we can.\n */\nexport function httpErrorToHuman(error: any): string {\n    if (error.response && error.response.data) {\n        let { data } = error.response;\n\n        // Some non-JSON requests can still return the error as a JSON block. In those cases, attempt\n        // to parse it into JSON so we can display an actual error.\n        if (typeof data === 'string') {\n            try {\n                data = JSON.parse(data);\n            } catch (e) {\n                // do nothing, bad json\n            }\n        }\n\n        if (data.errors && data.errors[0] && data.errors[0].detail) {\n            return data.errors[0].detail;\n        }\n\n        // Errors from wings directory, mostly just for file uploads.\n        if (data.error && typeof data.error === 'string') {\n            return data.error;\n        }\n    }\n\n    return error.message;\n}\n\nexport interface FractalResponseData {\n    object: string;\n    attributes: {\n        [k: string]: any;\n        relationships?: Record<string, FractalResponseData | FractalResponseList | null | undefined>;\n    };\n}\n\nexport interface FractalResponseList {\n    object: 'list';\n    data: FractalResponseData[];\n}\n\nexport interface FractalPaginatedResponse extends FractalResponseList {\n    meta: {\n        pagination: {\n            total: number;\n            count: number;\n            /* eslint-disable camelcase */\n            per_page: number;\n            current_page: number;\n            total_pages: number;\n            /* eslint-enable camelcase */\n        };\n    };\n}\n\nexport interface PaginatedResult<T> {\n    items: T[];\n    pagination: PaginationDataSet;\n}\n\nexport interface PaginationDataSet {\n    total: number;\n    count: number;\n    perPage: number;\n    currentPage: number;\n    totalPages: number;\n}\n\nexport function getPaginationSet(data: any): PaginationDataSet {\n    return {\n        total: data.total,\n        count: data.count,\n        perPage: data.per_page,\n        currentPage: data.current_page,\n        totalPages: data.total_pages,\n    };\n}\n\ntype QueryBuilderFilterValue = string | number | boolean | null;\n\nexport interface QueryBuilderParams<FilterKeys extends string = string, SortKeys extends string = string> {\n    page?: number;\n    filters?: {\n        [K in FilterKeys]?: QueryBuilderFilterValue | Readonly<QueryBuilderFilterValue[]>;\n    };\n    sorts?: {\n        [K in SortKeys]?: -1 | 0 | 1 | 'asc' | 'desc' | null;\n    };\n}\n\n/**\n * Helper function that parses a data object provided and builds query parameters\n * for the Laravel Query Builder package automatically. This will apply sorts and\n * filters deterministically based on the provided values.\n */\nexport const withQueryBuilderParams = (data?: QueryBuilderParams): Record<string, unknown> => {\n    if (!data) return {};\n\n    const filters = Object.keys(data.filters || {}).reduce((obj, key) => {\n        const value = data.filters?.[key];\n\n        return !value || value === '' ? obj : { ...obj, [`filter[${key}]`]: value };\n    }, {} as NonNullable<QueryBuilderParams['filters']>);\n\n    const sorts = Object.keys(data.sorts || {}).reduce((arr, key) => {\n        const value = data.sorts?.[key];\n        if (!value || !['asc', 'desc', 1, -1].includes(value)) {\n            return arr;\n        }\n\n        return [...arr, (value === -1 || value === 'desc' ? '-' : '') + key];\n    }, [] as string[]);\n\n    return {\n        ...filters,\n        sort: !sorts.length ? undefined : sorts.join(','),\n        page: data.page,\n    };\n};\n"
  },
  {
    "path": "resources/scripts/api/interceptors.ts",
    "content": "import http from '@/api/http';\nimport { AxiosError } from 'axios';\nimport { History } from 'history';\n\nexport const setupInterceptors = (history: History) => {\n    http.interceptors.response.use(\n        (resp) => resp,\n        (error: AxiosError) => {\n            if (error.response?.status === 400) {\n                if (\n                    (error.response?.data as Record<string, any>).errors?.[0].code === 'TwoFactorAuthRequiredException'\n                ) {\n                    if (!window.location.pathname.startsWith('/account')) {\n                        history.replace('/account', { twoFactorRedirect: true });\n                    }\n                }\n            }\n            throw error;\n        }\n    );\n};\n"
  },
  {
    "path": "resources/scripts/api/server/activity.ts",
    "content": "import useSWR, { ConfigInterface, responseInterface } from 'swr';\nimport { ActivityLog, Transformers } from '@definitions/user';\nimport { AxiosError } from 'axios';\nimport http, { PaginatedResult, QueryBuilderParams, withQueryBuilderParams } from '@/api/http';\nimport { toPaginatedSet } from '@definitions/helpers';\nimport useFilteredObject from '@/plugins/useFilteredObject';\nimport { useServerSWRKey } from '@/plugins/useSWRKey';\nimport { ServerContext } from '@/state/server';\n\nexport type ActivityLogFilters = QueryBuilderParams<'ip' | 'event', 'timestamp'>;\n\nconst useActivityLogs = (\n    filters?: ActivityLogFilters,\n    config?: ConfigInterface<PaginatedResult<ActivityLog>, AxiosError>\n): responseInterface<PaginatedResult<ActivityLog>, AxiosError> => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data?.uuid);\n    const key = useServerSWRKey(['activity', useFilteredObject(filters || {})]);\n\n    return useSWR<PaginatedResult<ActivityLog>>(\n        key,\n        async () => {\n            const { data } = await http.get(`/api/client/servers/${uuid}/activity`, {\n                params: {\n                    ...withQueryBuilderParams(filters),\n                    include: ['actor'],\n                },\n            });\n\n            return toPaginatedSet(data, Transformers.toActivityLog);\n        },\n        { revalidateOnMount: false, ...(config || {}) }\n    );\n};\n\nexport { useActivityLogs };\n"
  },
  {
    "path": "resources/scripts/api/server/backups/createServerBackup.ts",
    "content": "import http from '@/api/http';\nimport { ServerBackup } from '@/api/server/types';\nimport { rawDataToServerBackup } from '@/api/transformers';\n\ninterface RequestParameters {\n    name?: string;\n    ignored?: string;\n    isLocked: boolean;\n}\n\nexport default async (uuid: string, params: RequestParameters): Promise<ServerBackup> => {\n    const { data } = await http.post(`/api/client/servers/${uuid}/backups`, {\n        name: params.name,\n        ignored: params.ignored,\n        is_locked: params.isLocked,\n    });\n\n    return rawDataToServerBackup(data);\n};\n"
  },
  {
    "path": "resources/scripts/api/server/backups/deleteBackup.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, backup: string): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.delete(`/api/client/servers/${uuid}/backups/${backup}`)\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/backups/getBackupDownloadUrl.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, backup: string): Promise<string> => {\n    return new Promise((resolve, reject) => {\n        http.get(`/api/client/servers/${uuid}/backups/${backup}/download`)\n            .then(({ data }) => resolve(data.attributes.url))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/backups/index.ts",
    "content": "import http from '@/api/http';\n\nexport const restoreServerBackup = async (uuid: string, backup: string, truncate?: boolean): Promise<void> => {\n    await http.post(`/api/client/servers/${uuid}/backups/${backup}/restore`, {\n        truncate,\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/databases/createServerDatabase.ts",
    "content": "import { rawDataToServerDatabase, ServerDatabase } from '@/api/server/databases/getServerDatabases';\nimport http from '@/api/http';\n\nexport default (uuid: string, data: { connectionsFrom: string; databaseName: string }): Promise<ServerDatabase> => {\n    return new Promise((resolve, reject) => {\n        http.post(\n            `/api/client/servers/${uuid}/databases`,\n            {\n                database: data.databaseName,\n                remote: data.connectionsFrom,\n            },\n            {\n                params: { include: 'password' },\n            }\n        )\n            .then((response) => resolve(rawDataToServerDatabase(response.data.attributes)))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/databases/deleteServerDatabase.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, database: string): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.delete(`/api/client/servers/${uuid}/databases/${database}`)\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/databases/getServerDatabases.ts",
    "content": "import http from '@/api/http';\n\nexport interface ServerDatabase {\n    id: string;\n    name: string;\n    username: string;\n    connectionString: string;\n    allowConnectionsFrom: string;\n    password?: string;\n}\n\nexport const rawDataToServerDatabase = (data: any): ServerDatabase => ({\n    id: data.id,\n    name: data.name,\n    username: data.username,\n    connectionString: `${data.host.address}:${data.host.port}`,\n    allowConnectionsFrom: data.connections_from,\n    password: data.relationships.password?.attributes?.password,\n});\n\nexport default (uuid: string, includePassword = true): Promise<ServerDatabase[]> => {\n    return new Promise((resolve, reject) => {\n        http.get(`/api/client/servers/${uuid}/databases`, {\n            params: includePassword ? { include: 'password' } : undefined,\n        })\n            .then((response) =>\n                resolve((response.data.data || []).map((item: any) => rawDataToServerDatabase(item.attributes)))\n            )\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/databases/rotateDatabasePassword.ts",
    "content": "import { rawDataToServerDatabase, ServerDatabase } from '@/api/server/databases/getServerDatabases';\nimport http from '@/api/http';\n\nexport default (uuid: string, database: string): Promise<ServerDatabase> => {\n    return new Promise((resolve, reject) => {\n        http.post(`/api/client/servers/${uuid}/databases/${database}/rotate-password`)\n            .then((response) => resolve(rawDataToServerDatabase(response.data.attributes)))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/chmodFiles.ts",
    "content": "import http from '@/api/http';\n\ninterface Data {\n    file: string;\n    mode: string;\n}\n\nexport default (uuid: string, directory: string, files: Data[]): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.post(`/api/client/servers/${uuid}/files/chmod`, { root: directory, files })\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/compressFiles.ts",
    "content": "import { FileObject } from '@/api/server/files/loadDirectory';\nimport http from '@/api/http';\nimport { rawDataToFileObject } from '@/api/transformers';\n\nexport default async (uuid: string, directory: string, files: string[]): Promise<FileObject> => {\n    const { data } = await http.post(\n        `/api/client/servers/${uuid}/files/compress`,\n        { root: directory, files },\n        {\n            timeout: 60000,\n            timeoutErrorMessage: '打包成压缩包可能需要一些时间，一旦完成，您将能够看到生成的压缩文件。',\n        }\n    );\n\n    return rawDataToFileObject(data);\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/copyFile.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, location: string): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.post(`/api/client/servers/${uuid}/files/copy`, { location })\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/createDirectory.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, root: string, name: string): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.post(`/api/client/servers/${uuid}/files/create-folder`, { root, name })\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/decompressFiles.ts",
    "content": "import http from '@/api/http';\n\nexport default async (uuid: string, directory: string, file: string): Promise<void> => {\n    await http.post(\n        `/api/client/servers/${uuid}/files/decompress`,\n        { root: directory, file },\n        {\n            timeout: 10000,\n            timeoutErrorMessage: '解压这个压缩包需要较长时间，一旦完成，您将能够看到解压后的文件。',\n        }\n    );\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/deleteFiles.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, directory: string, files: string[]): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.post(`/api/client/servers/${uuid}/files/delete`, { root: directory, files })\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/getFileContents.ts",
    "content": "import http from '@/api/http';\n\nexport default (server: string, file: string): Promise<string> => {\n    return new Promise((resolve, reject) => {\n        http.get(`/api/client/servers/${server}/files/contents`, {\n            params: { file },\n            transformResponse: (res) => res,\n            responseType: 'text',\n        })\n            .then(({ data }) => resolve(data))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/getFileDownloadUrl.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, file: string): Promise<string> => {\n    return new Promise((resolve, reject) => {\n        http.get(`/api/client/servers/${uuid}/files/download`, { params: { file } })\n            .then(({ data }) => resolve(data.attributes.url))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/getFileUploadUrl.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string): Promise<string> => {\n    return new Promise((resolve, reject) => {\n        http.get(`/api/client/servers/${uuid}/files/upload`)\n            .then(({ data }) => resolve(data.attributes.url))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/loadDirectory.ts",
    "content": "import http from '@/api/http';\nimport { rawDataToFileObject } from '@/api/transformers';\n\nexport interface FileObject {\n    key: string;\n    name: string;\n    mode: string;\n    modeBits: string;\n    size: number;\n    isFile: boolean;\n    isSymlink: boolean;\n    mimetype: string;\n    createdAt: Date;\n    modifiedAt: Date;\n    isArchiveType: () => boolean;\n    isEditable: () => boolean;\n}\n\nexport default async (uuid: string, directory?: string): Promise<FileObject[]> => {\n    const { data } = await http.get(`/api/client/servers/${uuid}/files/list`, {\n        params: { directory: directory ?? '/' },\n    });\n\n    return (data.data || []).map(rawDataToFileObject);\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/renameFiles.ts",
    "content": "import http from '@/api/http';\n\ninterface Data {\n    to: string;\n    from: string;\n}\n\nexport default (uuid: string, directory: string, files: Data[]): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.put(`/api/client/servers/${uuid}/files/rename`, { root: directory, files })\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/files/saveFileContents.ts",
    "content": "import http from '@/api/http';\n\nexport default async (uuid: string, file: string, content: string): Promise<void> => {\n    await http.post(`/api/client/servers/${uuid}/files/write`, content, {\n        params: { file },\n        headers: {\n            'Content-Type': 'text/plain',\n        },\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/getServer.ts",
    "content": "import http, { FractalResponseData, FractalResponseList } from '@/api/http';\nimport { rawDataToServerAllocation, rawDataToServerEggVariable } from '@/api/transformers';\nimport { ServerEggVariable, ServerStatus } from '@/api/server/types';\nimport { Identifier } from '@/api/definitions';\n\nexport interface Allocation {\n    id: number;\n    ip: string;\n    alias: string | null;\n    port: number;\n    notes: string | null;\n    isDefault: boolean;\n}\n\nexport interface Server {\n    /**\n     * This value is determined by the presence of the `PTERODACTYL_USE_SERVER_IDENTIFIERS` environment\n     * variable which changes what the API can respond with. It will eventually be removed and referenced\n     * as the \"identifier\" key, but this allows users to slowly opt-in to these new URLs and trial it\n     * as they wish.\n     *\n     * @deprecated this is the \"uuid_short\" which will be removed in 2.0, prefer use of \"identifier\"\n     */\n    id: string | Identifier<'serv'>;\n    identifier: Identifier<'serv'>; // Set from \"server_identifier\" and should be used moving forward to reference a server.\n    internalId: number | string;\n    /**\n     * Exists only to maintain support in cases where the short-uuid is necessary for server reference\n     * and cannot be easily replaced with \"identifier\".\n     *\n     * @deprecated\n     */\n    __deprecatedUuidShort: string;\n    uuid: string;\n    name: string;\n    node: string;\n    isNodeUnderMaintenance: boolean;\n    status: ServerStatus;\n    sftpDetails: {\n        ip: string;\n        port: number;\n    };\n    invocation: string;\n    dockerImage: string;\n    description: string;\n    limits: {\n        memory: number;\n        swap: number;\n        disk: number;\n        io: number;\n        cpu: number;\n        threads: string;\n    };\n    eggFeatures: string[];\n    featureLimits: {\n        databases: number;\n        allocations: number;\n        backups: number;\n    };\n    isTransferring: boolean;\n    variables: ServerEggVariable[];\n    allocations: Allocation[];\n}\n\nexport const rawDataToServerObject = ({ attributes: data }: FractalResponseData): Server => ({\n    id: data.identifier,\n    identifier: data.server_identifier,\n    internalId: data.internal_id,\n    __deprecatedUuidShort: data.__deprecated_uuid_short,\n    uuid: data.uuid,\n    name: data.name,\n    node: data.node,\n    isNodeUnderMaintenance: data.is_node_under_maintenance,\n    status: data.status,\n    invocation: data.invocation,\n    dockerImage: data.docker_image,\n    sftpDetails: {\n        ip: data.sftp_details.ip,\n        port: data.sftp_details.port,\n    },\n    description: data.description ? (data.description.length > 0 ? data.description : null) : null,\n    limits: { ...data.limits },\n    eggFeatures: data.egg_features || [],\n    featureLimits: { ...data.feature_limits },\n    isTransferring: data.is_transferring,\n    variables: ((data.relationships?.variables as FractalResponseList | undefined)?.data || []).map(\n        rawDataToServerEggVariable\n    ),\n    allocations: ((data.relationships?.allocations as FractalResponseList | undefined)?.data || []).map(\n        rawDataToServerAllocation\n    ),\n});\n\nexport default (uuid: string): Promise<[Server, string[]]> => {\n    return new Promise((resolve, reject) => {\n        http.get(`/api/client/servers/${uuid}`)\n            .then(({ data }) =>\n                resolve([\n                    rawDataToServerObject(data),\n                    // eslint-disable-next-line camelcase\n                    data.meta?.is_server_owner ? ['*'] : data.meta?.user_permissions || [],\n                ])\n            )\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/getServerResourceUsage.ts",
    "content": "import http from '@/api/http';\n\nexport type ServerPowerState = 'offline' | 'starting' | 'running' | 'stopping';\n\nexport interface ServerStats {\n    status: ServerPowerState;\n    isSuspended: boolean;\n    memoryUsageInBytes: number;\n    cpuUsagePercent: number;\n    diskUsageInBytes: number;\n    networkRxInBytes: number;\n    networkTxInBytes: number;\n    uptime: number;\n}\n\nexport default (server: string): Promise<ServerStats> => {\n    return new Promise((resolve, reject) => {\n        http.get(`/api/client/servers/${server}/resources`)\n            .then(({ data: { attributes } }) =>\n                resolve({\n                    status: attributes.current_state,\n                    isSuspended: attributes.is_suspended,\n                    memoryUsageInBytes: attributes.resources.memory_bytes,\n                    cpuUsagePercent: attributes.resources.cpu_absolute,\n                    diskUsageInBytes: attributes.resources.disk_bytes,\n                    networkRxInBytes: attributes.resources.network_rx_bytes,\n                    networkTxInBytes: attributes.resources.network_tx_bytes,\n                    uptime: attributes.resources.uptime,\n                })\n            )\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/getWebsocketToken.ts",
    "content": "import http from '@/api/http';\n\ninterface Response {\n    token: string;\n    socket: string;\n}\n\nexport default (server: string): Promise<Response> => {\n    return new Promise((resolve, reject) => {\n        http.get(`/api/client/servers/${server}/websocket`)\n            .then(({ data }) =>\n                resolve({\n                    token: data.data.token,\n                    socket: data.data.socket,\n                })\n            )\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/network/createServerAllocation.ts",
    "content": "import { Allocation } from '@/api/server/getServer';\nimport http, { FractalResponseList } from '@/api/http';\nimport { rawDataToServerAllocation } from '@/api/transformers';\n\nexport default async (uuid: string, count?: number): Promise<Allocation[]> => {\n    const { data } = await http.post(\n        `/api/client/servers/${uuid}/network/allocations`,\n        count && count > 1 ? { count } : {}\n    );\n\n    if (data.object === 'list') {\n        return (data as FractalResponseList).data.map(rawDataToServerAllocation);\n    }\n\n    return [rawDataToServerAllocation(data)];\n};\n"
  },
  {
    "path": "resources/scripts/api/server/network/deleteServerAllocation.ts",
    "content": "import { Allocation } from '@/api/server/getServer';\nimport http from '@/api/http';\n\nexport default async (uuid: string, id: number): Promise<Allocation> =>\n    await http.delete(`/api/client/servers/${uuid}/network/allocations/${id}`);\n"
  },
  {
    "path": "resources/scripts/api/server/network/setPrimaryServerAllocation.ts",
    "content": "import { Allocation } from '@/api/server/getServer';\nimport http from '@/api/http';\nimport { rawDataToServerAllocation } from '@/api/transformers';\n\nexport default async (uuid: string, id: number): Promise<Allocation> => {\n    const { data } = await http.post(`/api/client/servers/${uuid}/network/allocations/${id}/primary`);\n\n    return rawDataToServerAllocation(data);\n};\n"
  },
  {
    "path": "resources/scripts/api/server/network/setServerAllocationNotes.ts",
    "content": "import { Allocation } from '@/api/server/getServer';\nimport http from '@/api/http';\nimport { rawDataToServerAllocation } from '@/api/transformers';\n\nexport default async (uuid: string, id: number, notes: string | null): Promise<Allocation> => {\n    const { data } = await http.post(`/api/client/servers/${uuid}/network/allocations/${id}`, { notes });\n\n    return rawDataToServerAllocation(data);\n};\n"
  },
  {
    "path": "resources/scripts/api/server/reinstallServer.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.post(`/api/client/servers/${uuid}/settings/reinstall`)\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/renameServer.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, name: string, description?: string): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.post(`/api/client/servers/${uuid}/settings/rename`, { name, description })\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/schedules/createOrUpdateSchedule.ts",
    "content": "import { rawDataToServerSchedule, Schedule } from '@/api/server/schedules/getServerSchedules';\nimport http from '@/api/http';\n\ntype Data = Pick<Schedule, 'cron' | 'name' | 'onlyWhenOnline' | 'isActive'> & { id?: number };\n\nexport default async (uuid: string, schedule: Data): Promise<Schedule> => {\n    const { data } = await http.post(`/api/client/servers/${uuid}/schedules${schedule.id ? `/${schedule.id}` : ''}`, {\n        is_active: schedule.isActive,\n        only_when_online: schedule.onlyWhenOnline,\n        name: schedule.name,\n        minute: schedule.cron.minute,\n        hour: schedule.cron.hour,\n        day_of_month: schedule.cron.dayOfMonth,\n        month: schedule.cron.month,\n        day_of_week: schedule.cron.dayOfWeek,\n    });\n\n    return rawDataToServerSchedule(data.attributes);\n};\n"
  },
  {
    "path": "resources/scripts/api/server/schedules/createOrUpdateScheduleTask.ts",
    "content": "import { rawDataToServerTask, Task } from '@/api/server/schedules/getServerSchedules';\nimport http from '@/api/http';\n\ninterface Data {\n    action: string;\n    payload: string;\n    timeOffset: string | number;\n    continueOnFailure: boolean;\n}\n\nexport default async (uuid: string, schedule: number, task: number | undefined, data: Data): Promise<Task> => {\n    const { data: response } = await http.post(\n        `/api/client/servers/${uuid}/schedules/${schedule}/tasks${task ? `/${task}` : ''}`,\n        {\n            action: data.action,\n            payload: data.payload,\n            continue_on_failure: data.continueOnFailure,\n            time_offset: data.timeOffset,\n        }\n    );\n\n    return rawDataToServerTask(response.attributes);\n};\n"
  },
  {
    "path": "resources/scripts/api/server/schedules/deleteSchedule.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, schedule: number): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.delete(`/api/client/servers/${uuid}/schedules/${schedule}`)\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/schedules/deleteScheduleTask.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, scheduleId: number, taskId: number): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.delete(`/api/client/servers/${uuid}/schedules/${scheduleId}/tasks/${taskId}`)\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/schedules/getServerSchedule.ts",
    "content": "import http from '@/api/http';\nimport { rawDataToServerSchedule, Schedule } from '@/api/server/schedules/getServerSchedules';\n\nexport default (uuid: string, schedule: number): Promise<Schedule> => {\n    return new Promise((resolve, reject) => {\n        http.get(`/api/client/servers/${uuid}/schedules/${schedule}`, {\n            params: {\n                include: ['tasks'],\n            },\n        })\n            .then(({ data }) => resolve(rawDataToServerSchedule(data.attributes)))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/schedules/getServerSchedules.ts",
    "content": "import http from '@/api/http';\n\nexport interface Schedule {\n    id: number;\n    name: string;\n    cron: {\n        dayOfWeek: string;\n        month: string;\n        dayOfMonth: string;\n        hour: string;\n        minute: string;\n    };\n    isActive: boolean;\n    isProcessing: boolean;\n    onlyWhenOnline: boolean;\n    lastRunAt: Date | null;\n    nextRunAt: Date | null;\n    createdAt: Date;\n    updatedAt: Date;\n\n    tasks: Task[];\n}\n\nexport interface Task {\n    id: number;\n    sequenceId: number;\n    action: string;\n    payload: string;\n    timeOffset: number;\n    isQueued: boolean;\n    continueOnFailure: boolean;\n    createdAt: Date;\n    updatedAt: Date;\n}\n\nexport const rawDataToServerTask = (data: any): Task => ({\n    id: data.id,\n    sequenceId: data.sequence_id,\n    action: data.action,\n    payload: data.payload,\n    timeOffset: data.time_offset,\n    isQueued: data.is_queued,\n    continueOnFailure: data.continue_on_failure,\n    createdAt: new Date(data.created_at),\n    updatedAt: new Date(data.updated_at),\n});\n\nexport const rawDataToServerSchedule = (data: any): Schedule => ({\n    id: data.id,\n    name: data.name,\n    cron: {\n        dayOfWeek: data.cron.day_of_week,\n        month: data.cron.month,\n        dayOfMonth: data.cron.day_of_month,\n        hour: data.cron.hour,\n        minute: data.cron.minute,\n    },\n    isActive: data.is_active,\n    isProcessing: data.is_processing,\n    onlyWhenOnline: data.only_when_online,\n    lastRunAt: data.last_run_at ? new Date(data.last_run_at) : null,\n    nextRunAt: data.next_run_at ? new Date(data.next_run_at) : null,\n    createdAt: new Date(data.created_at),\n    updatedAt: new Date(data.updated_at),\n\n    tasks: (data.relationships?.tasks?.data || []).map((row: any) => rawDataToServerTask(row.attributes)),\n});\n\nexport default async (uuid: string): Promise<Schedule[]> => {\n    const { data } = await http.get(`/api/client/servers/${uuid}/schedules`, {\n        params: {\n            include: ['tasks'],\n        },\n    });\n\n    return (data.data || []).map((row: any) => rawDataToServerSchedule(row.attributes));\n};\n"
  },
  {
    "path": "resources/scripts/api/server/schedules/triggerScheduleExecution.ts",
    "content": "import http from '@/api/http';\n\nexport default async (server: string, schedule: number): Promise<void> =>\n    await http.post(`/api/client/servers/${server}/schedules/${schedule}/execute`);\n"
  },
  {
    "path": "resources/scripts/api/server/setSelectedDockerImage.ts",
    "content": "import http from '@/api/http';\n\nexport default async (uuid: string, image: string): Promise<void> => {\n    await http.put(`/api/client/servers/${uuid}/settings/docker-image`, { docker_image: image });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/types.d.ts",
    "content": "export type ServerStatus =\n    | 'installing'\n    | 'install_failed'\n    | 'reinstall_failed'\n    | 'suspended'\n    | 'restoring_backup'\n    | null;\n\nexport interface ServerBackup {\n    uuid: string;\n    isSuccessful: boolean;\n    isLocked: boolean;\n    name: string;\n    ignoredFiles: string;\n    checksum: string;\n    bytes: number;\n    createdAt: Date;\n    completedAt: Date | null;\n}\n\nexport interface ServerEggVariable {\n    name: string;\n    description: string;\n    envVariable: string;\n    defaultValue: string;\n    serverValue: string | null;\n    isEditable: boolean;\n    rules: string[];\n}\n"
  },
  {
    "path": "resources/scripts/api/server/updateStartupEgg.ts",
    "content": "import http, { FractalResponseList } from '@/api/http';\nimport { rawDataToServerEggVariable } from '@/api/transformers';\nimport { ServerEggVariable } from '@/api/server/types';\nimport { EggChangeMode, NestData } from '@/api/swr/getServerStartup';\n\nexport interface EggChangeResponse {\n    variables: ServerEggVariable[];\n    invocation: string;\n    dockerImages: Record<string, string>;\n    eggChangeMode: EggChangeMode;\n    nests: NestData[];\n    currentEggId: number;\n    currentNestId: number;\n}\n\nexport default async (uuid: string, eggId: number): Promise<EggChangeResponse> => {\n    const { data } = await http.put(`/api/client/servers/${uuid}/startup/egg`, { egg_id: eggId });\n\n    const variables = ((data as FractalResponseList).data || []).map(rawDataToServerEggVariable);\n\n    return {\n        variables,\n        invocation: data.meta.startup_command,\n        dockerImages: data.meta.docker_images || {},\n        // The backend always returns a non-disabled mode here since it would have rejected the request otherwise\n        eggChangeMode: data.meta.egg_change_mode as EggChangeMode,\n        nests: data.meta.nests || [],\n        currentEggId: data.meta.current_egg_id,\n        currentNestId: data.meta.current_nest_id,\n    };\n};\n"
  },
  {
    "path": "resources/scripts/api/server/updateStartupVariable.ts",
    "content": "import http from '@/api/http';\nimport { ServerEggVariable } from '@/api/server/types';\nimport { rawDataToServerEggVariable } from '@/api/transformers';\n\nexport default async (uuid: string, key: string, value: string): Promise<[ServerEggVariable, string]> => {\n    const { data } = await http.put(`/api/client/servers/${uuid}/startup/variable`, { key, value });\n\n    return [rawDataToServerEggVariable(data), data.meta.startup_command];\n};\n"
  },
  {
    "path": "resources/scripts/api/server/users/createOrUpdateSubuser.ts",
    "content": "import http from '@/api/http';\nimport { rawDataToServerSubuser } from '@/api/server/users/getServerSubusers';\nimport { Subuser } from '@/state/server/subusers';\n\ninterface Params {\n    email: string;\n    permissions: string[];\n}\n\nexport default (uuid: string, params: Params, subuser?: Subuser): Promise<Subuser> => {\n    return new Promise((resolve, reject) => {\n        http.post(`/api/client/servers/${uuid}/users${subuser ? `/${subuser.uuid}` : ''}`, {\n            ...params,\n        })\n            .then((data) => resolve(rawDataToServerSubuser(data.data)))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/users/deleteSubuser.ts",
    "content": "import http from '@/api/http';\n\nexport default (uuid: string, userId: string): Promise<void> => {\n    return new Promise((resolve, reject) => {\n        http.delete(`/api/client/servers/${uuid}/users/${userId}`)\n            .then(() => resolve())\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/server/users/getServerSubusers.ts",
    "content": "import http, { FractalResponseData } from '@/api/http';\nimport { Subuser } from '@/state/server/subusers';\n\nexport const rawDataToServerSubuser = (data: FractalResponseData): Subuser => ({\n    uuid: data.attributes.uuid,\n    username: data.attributes.username,\n    email: data.attributes.email,\n    image: data.attributes.image,\n    twoFactorEnabled: data.attributes['2fa_enabled'],\n    createdAt: new Date(data.attributes.created_at),\n    permissions: data.attributes.permissions || [],\n    can: (permission) => (data.attributes.permissions || []).indexOf(permission) >= 0,\n});\n\nexport default (uuid: string): Promise<Subuser[]> => {\n    return new Promise((resolve, reject) => {\n        http.get(`/api/client/servers/${uuid}/users`)\n            .then(({ data }) => resolve((data.data || []).map(rawDataToServerSubuser)))\n            .catch(reject);\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/swr/getServerAllocations.ts",
    "content": "import { ServerContext } from '@/state/server';\nimport useSWR from 'swr';\nimport http from '@/api/http';\nimport { rawDataToServerAllocation } from '@/api/transformers';\nimport { Allocation } from '@/api/server/getServer';\n\nexport default () => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n\n    return useSWR<Allocation[]>(\n        ['server:allocations', uuid],\n        async () => {\n            const { data } = await http.get(`/api/client/servers/${uuid}/network/allocations`);\n\n            return (data.data || []).map(rawDataToServerAllocation);\n        },\n        { revalidateOnFocus: false, revalidateOnMount: false }\n    );\n};\n"
  },
  {
    "path": "resources/scripts/api/swr/getServerBackups.ts",
    "content": "import useSWR from 'swr';\nimport http, { getPaginationSet, PaginatedResult } from '@/api/http';\nimport { ServerBackup } from '@/api/server/types';\nimport { rawDataToServerBackup } from '@/api/transformers';\nimport { ServerContext } from '@/state/server';\nimport { createContext, useContext } from 'react';\n\ninterface ctx {\n    page: number;\n    setPage: (value: number | ((s: number) => number)) => void;\n}\n\nexport const Context = createContext<ctx>({ page: 1, setPage: () => 1 });\n\ntype BackupResponse = PaginatedResult<ServerBackup> & { backupCount: number };\n\nexport default () => {\n    const { page } = useContext(Context);\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n\n    return useSWR<BackupResponse>(['server:backups', uuid, page], async () => {\n        const { data } = await http.get(`/api/client/servers/${uuid}/backups`, { params: { page } });\n\n        return {\n            items: (data.data || []).map(rawDataToServerBackup),\n            pagination: getPaginationSet(data.meta.pagination),\n            backupCount: data.meta.backup_count,\n        };\n    });\n};\n"
  },
  {
    "path": "resources/scripts/api/swr/getServerStartup.ts",
    "content": "import useSWR, { ConfigInterface } from 'swr';\nimport http, { FractalResponseList } from '@/api/http';\nimport { rawDataToServerEggVariable } from '@/api/transformers';\nimport { ServerEggVariable } from '@/api/server/types';\n\n// 'disabled' is intentionally excluded: undefined represents the disabled state in the frontend.\nexport type EggChangeMode = 'egg_only' | 'both';\n\nconst VALID_EGG_CHANGE_MODES: readonly string[] = ['egg_only', 'both'];\n\nfunction toEggChangeMode(value: unknown): EggChangeMode | undefined {\n    if (typeof value === 'string' && VALID_EGG_CHANGE_MODES.includes(value)) {\n        return value as EggChangeMode;\n    }\n    return undefined;\n}\n\nexport interface NestData {\n    id: number;\n    name: string;\n    eggs: Array<{ id: number; name: string }>;\n}\n\ninterface Response {\n    invocation: string;\n    variables: ServerEggVariable[];\n    dockerImages: Record<string, string>;\n    eggChangeMode?: EggChangeMode;\n    nests?: NestData[];\n    currentEggId?: number;\n    currentNestId?: number;\n}\n\nexport default (uuid: string, initialData?: Response | null, config?: ConfigInterface<Response>) =>\n    useSWR(\n        [uuid, '/startup'],\n        async (): Promise<Response> => {\n            const { data } = await http.get(`/api/client/servers/${uuid}/startup`);\n\n            const variables = ((data as FractalResponseList).data || []).map(rawDataToServerEggVariable);\n\n            return {\n                variables,\n                invocation: data.meta.startup_command,\n                dockerImages: data.meta.docker_images || {},\n                eggChangeMode: toEggChangeMode(data.meta.egg_change_mode),\n                nests: data.meta.nests || undefined,\n                currentEggId: data.meta.current_egg_id || undefined,\n                currentNestId: data.meta.current_nest_id || undefined,\n            };\n        },\n        { initialData: initialData || undefined, errorRetryCount: 3, ...(config || {}) }\n    );\n"
  },
  {
    "path": "resources/scripts/api/transformers.ts",
    "content": "import { Allocation } from '@/api/server/getServer';\nimport { FractalResponseData } from '@/api/http';\nimport { FileObject } from '@/api/server/files/loadDirectory';\nimport { ServerBackup, ServerEggVariable } from '@/api/server/types';\n\nexport const rawDataToServerAllocation = (data: FractalResponseData): Allocation => ({\n    id: data.attributes.id,\n    ip: data.attributes.ip,\n    alias: data.attributes.ip_alias,\n    port: data.attributes.port,\n    notes: data.attributes.notes,\n    isDefault: data.attributes.is_default,\n});\n\nexport const rawDataToFileObject = (data: FractalResponseData): FileObject => ({\n    key: `${data.attributes.is_file ? 'file' : 'dir'}_${data.attributes.name}`,\n    name: data.attributes.name,\n    mode: data.attributes.mode,\n    modeBits: data.attributes.mode_bits,\n    size: Number(data.attributes.size),\n    isFile: data.attributes.is_file,\n    isSymlink: data.attributes.is_symlink,\n    mimetype: data.attributes.mimetype,\n    createdAt: new Date(data.attributes.created_at),\n    modifiedAt: new Date(data.attributes.modified_at),\n\n    isArchiveType: function () {\n        return (\n            this.isFile &&\n            [\n                'application/vnd.rar', // .rar\n                'application/x-rar-compressed', // .rar (2)\n                'application/x-tar', // .tar\n                'application/x-br', // .tar.br\n                'application/x-bzip2', // .tar.bz2, .bz2\n                'application/gzip', // .tar.gz, .gz\n                'application/x-gzip',\n                'application/x-lzip', // .tar.lz4, .lz4 (not sure if this mime type is correct)\n                'application/x-sz', // .tar.sz, .sz (not sure if this mime type is correct)\n                'application/x-xz', // .tar.xz, .xz\n                'application/zstd', // .tar.zst, .zst\n                'application/zip', // .zip\n                'application/x-7z-compressed', // .7z\n            ].indexOf(this.mimetype) >= 0\n        );\n    },\n\n    isEditable: function () {\n        if (this.isArchiveType() || !this.isFile) return false;\n\n        const matches = ['application/jar', 'application/octet-stream', 'inode/directory', /^image\\/(?!svg\\+xml)/];\n\n        return matches.every((m) => !this.mimetype.match(m));\n    },\n});\n\nexport const rawDataToServerBackup = ({ attributes }: FractalResponseData): ServerBackup => ({\n    uuid: attributes.uuid,\n    isSuccessful: attributes.is_successful,\n    isLocked: attributes.is_locked,\n    name: attributes.name,\n    ignoredFiles: attributes.ignored_files,\n    checksum: attributes.checksum,\n    bytes: attributes.bytes,\n    createdAt: new Date(attributes.created_at),\n    completedAt: attributes.completed_at ? new Date(attributes.completed_at) : null,\n});\n\nexport const rawDataToServerEggVariable = ({ attributes }: FractalResponseData): ServerEggVariable => ({\n    name: attributes.name,\n    description: attributes.description,\n    envVariable: attributes.env_variable,\n    defaultValue: attributes.default_value,\n    serverValue: attributes.server_value,\n    isEditable: attributes.is_editable,\n    rules: attributes.rules.split('|'),\n});\n"
  },
  {
    "path": "resources/scripts/assets/css/GlobalStylesheet.ts",
    "content": "import tw from 'twin.macro';\nimport { createGlobalStyle } from 'styled-components/macro';\n// @ts-expect-error untyped font file\nimport font from '@fontsource-variable/ibm-plex-sans/files/ibm-plex-sans-latin-wght-normal.woff2';\n\nexport default createGlobalStyle`\n    @font-face {\n        font-family: 'IBM Plex Sans';\n        font-style: normal;\n        font-display: swap;\n        font-weight: 100 700;\n        src: url(${font}) format('woff2-variations');\n        unicode-range: U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD;\n    }\n\n    body {\n        ${tw`font-sans bg-neutral-800 text-neutral-200`};\n        letter-spacing: 0.015em;\n    }\n\n    h1, h2, h3, h4, h5, h6 {\n        ${tw`font-medium tracking-normal font-header`};\n    }\n\n    p {\n        ${tw`text-neutral-200 leading-snug font-sans`};\n    }\n\n    form {\n        ${tw`m-0`};\n    }\n\n    textarea, select, input, button, button:focus, button:focus-visible {\n        ${tw`outline-none`};\n    }\n\n    input[type=number]::-webkit-outer-spin-button,\n    input[type=number]::-webkit-inner-spin-button {\n        -webkit-appearance: none !important;\n        margin: 0;\n    }\n\n    input[type=number] {\n        -moz-appearance: textfield !important;\n    }\n\n    /* Scroll Bar Style */\n    ::-webkit-scrollbar {\n        background: none;\n        width: 16px;\n        height: 16px;\n    }\n\n    ::-webkit-scrollbar-thumb {\n        border: solid 0 rgb(0 0 0 / 0%);\n        border-right-width: 4px;\n        border-left-width: 4px;\n        -webkit-border-radius: 9px 4px;\n        -webkit-box-shadow: inset 0 0 0 1px hsl(211, 10%, 53%), inset 0 0 0 4px hsl(209deg 18% 30%);\n    }\n\n    ::-webkit-scrollbar-track-piece {\n        margin: 4px 0;\n    }\n\n    ::-webkit-scrollbar-thumb:horizontal {\n        border-right-width: 0;\n        border-left-width: 0;\n        border-top-width: 4px;\n        border-bottom-width: 4px;\n        -webkit-border-radius: 4px 9px;\n    }\n\n    ::-webkit-scrollbar-corner {\n        background: transparent;\n    }\n`;\n"
  },
  {
    "path": "resources/scripts/assets/tailwind.css",
    "content": "@tailwind base;\n@tailwind components;\n@tailwind utilities;\n"
  },
  {
    "path": "resources/scripts/components/App.tsx",
    "content": "import React, { lazy } from 'react';\nimport { hot } from 'react-hot-loader/root';\nimport { Route, Router, Switch } from 'react-router-dom';\nimport { StoreProvider } from 'easy-peasy';\nimport { store } from '@/state';\nimport { SiteSettings } from '@/state/settings';\nimport ProgressBar from '@/components/elements/ProgressBar';\nimport { NotFound } from '@/components/elements/ScreenBlock';\nimport tw from 'twin.macro';\nimport GlobalStylesheet from '@/assets/css/GlobalStylesheet';\nimport { history } from '@/components/history';\nimport { setupInterceptors } from '@/api/interceptors';\nimport AuthenticatedRoute from '@/components/elements/AuthenticatedRoute';\nimport { ServerContext } from '@/state/server';\nimport '@/assets/tailwind.css';\nimport Spinner from '@/components/elements/Spinner';\n\nconst DashboardRouter = lazy(() => import(/* webpackChunkName: \"dashboard\" */ '@/routers/DashboardRouter'));\nconst ServerRouter = lazy(() => import(/* webpackChunkName: \"server\" */ '@/routers/ServerRouter'));\nconst AuthenticationRouter = lazy(() => import(/* webpackChunkName: \"auth\" */ '@/routers/AuthenticationRouter'));\n\ninterface ExtendedWindow extends Window {\n    SiteConfiguration?: SiteSettings;\n    PterodactylUser?: {\n        uuid: string;\n        username: string;\n        email: string;\n        /* eslint-disable camelcase */\n        root_admin: boolean;\n        use_totp: boolean;\n        language: string;\n        updated_at: string;\n        created_at: string;\n        /* eslint-enable camelcase */\n    };\n}\n\nsetupInterceptors(history);\n\nconst App = () => {\n    const { PterodactylUser, SiteConfiguration } = window as ExtendedWindow;\n    if (PterodactylUser && !store.getState().user.data) {\n        store.getActions().user.setUserData({\n            uuid: PterodactylUser.uuid,\n            username: PterodactylUser.username,\n            email: PterodactylUser.email,\n            language: PterodactylUser.language,\n            rootAdmin: PterodactylUser.root_admin,\n            useTotp: PterodactylUser.use_totp,\n            createdAt: new Date(PterodactylUser.created_at),\n            updatedAt: new Date(PterodactylUser.updated_at),\n        });\n    }\n\n    if (!store.getState().settings.data) {\n        store.getActions().settings.setSettings(SiteConfiguration!);\n    }\n\n    return (\n        <>\n            <GlobalStylesheet />\n            <StoreProvider store={store}>\n                <ProgressBar />\n                <div css={tw`mx-auto w-auto`}>\n                    <Router history={history}>\n                        <Switch>\n                            <Route path={'/auth'}>\n                                <Spinner.Suspense>\n                                    <AuthenticationRouter />\n                                </Spinner.Suspense>\n                            </Route>\n                            <AuthenticatedRoute path={'/server/:id'}>\n                                <Spinner.Suspense>\n                                    <ServerContext.Provider>\n                                        <ServerRouter />\n                                    </ServerContext.Provider>\n                                </Spinner.Suspense>\n                            </AuthenticatedRoute>\n                            <AuthenticatedRoute path={'/'}>\n                                <Spinner.Suspense>\n                                    <DashboardRouter />\n                                </Spinner.Suspense>\n                            </AuthenticatedRoute>\n                            <Route path={'*'}>\n                                <NotFound />\n                            </Route>\n                        </Switch>\n                    </Router>\n                </div>\n            </StoreProvider>\n        </>\n    );\n};\n\nexport default hot(App);\n"
  },
  {
    "path": "resources/scripts/components/Avatar.tsx",
    "content": "import React from 'react';\nimport BoringAvatar, { AvatarProps } from 'boring-avatars';\nimport { useStoreState } from '@/state/hooks';\n\nconst palette = ['#FFAD08', '#EDD75A', '#73B06F', '#0C8F8F', '#587291'];\n\ntype Props = Omit<AvatarProps, 'colors'>;\n\nconst _Avatar = ({ variant = 'beam', ...props }: AvatarProps) => (\n    <BoringAvatar colors={palette} variant={variant} {...props} />\n);\n\nconst _UserAvatar = ({ variant = 'beam', ...props }: Omit<Props, 'name'>) => {\n    const uuid = useStoreState((state) => state.user.data?.uuid);\n\n    return <BoringAvatar colors={palette} name={uuid || 'system'} variant={variant} {...props} />;\n};\n\n_Avatar.displayName = 'Avatar';\n_UserAvatar.displayName = 'Avatar.User';\n\nconst Avatar = Object.assign(_Avatar, {\n    User: _UserAvatar,\n});\n\nexport default Avatar;\n"
  },
  {
    "path": "resources/scripts/components/FlashMessageRender.tsx",
    "content": "import React from 'react';\nimport MessageBox from '@/components/MessageBox';\nimport { useStoreState } from 'easy-peasy';\nimport tw from 'twin.macro';\n\ntype Props = Readonly<{\n    byKey?: string;\n    className?: string;\n}>;\n\nconst FlashMessageRender = ({ byKey, className }: Props) => {\n    const flashes = useStoreState((state) =>\n        state.flashes.items.filter((flash) => (byKey ? flash.key === byKey : true))\n    );\n\n    return flashes.length ? (\n        <div className={className}>\n            {flashes.map((flash, index) => (\n                <React.Fragment key={flash.id || flash.type + flash.message}>\n                    {index > 0 && <div css={tw`mt-2`}></div>}\n                    <MessageBox type={flash.type} title={flash.title}>\n                        {flash.message}\n                    </MessageBox>\n                </React.Fragment>\n            ))}\n        </div>\n    ) : null;\n};\n\nexport default FlashMessageRender;\n"
  },
  {
    "path": "resources/scripts/components/MessageBox.tsx",
    "content": "import * as React from 'react';\nimport tw, { TwStyle } from 'twin.macro';\nimport styled from 'styled-components/macro';\n\nexport type FlashMessageType = 'success' | 'info' | 'warning' | 'error';\n\ninterface Props {\n    title?: string;\n    children: string;\n    type?: FlashMessageType;\n}\n\nconst styling = (type?: FlashMessageType): TwStyle | string => {\n    switch (type) {\n        case 'error':\n            return tw`bg-red-600 border-red-800`;\n        case 'info':\n            return tw`bg-primary-600 border-primary-800`;\n        case 'success':\n            return tw`bg-green-600 border-green-800`;\n        case 'warning':\n            return tw`bg-yellow-600 border-yellow-800`;\n        default:\n            return '';\n    }\n};\n\nconst getBackground = (type?: FlashMessageType): TwStyle | string => {\n    switch (type) {\n        case 'error':\n            return tw`bg-red-500`;\n        case 'info':\n            return tw`bg-primary-500`;\n        case 'success':\n            return tw`bg-green-500`;\n        case 'warning':\n            return tw`bg-yellow-500`;\n        default:\n            return '';\n    }\n};\n\nconst Container = styled.div<{ $type?: FlashMessageType }>`\n    ${tw`p-2 border items-center leading-normal rounded flex w-full text-sm text-white`};\n    ${(props) => styling(props.$type)};\n`;\nContainer.displayName = 'MessageBox.Container';\n\nconst MessageBox = ({ title, children, type }: Props) => (\n    <Container css={tw`lg:inline-flex`} $type={type} role={'alert'}>\n        {title && (\n            <span\n                className={'title'}\n                css={[\n                    tw`flex rounded-full uppercase px-2 py-1 text-xs font-bold mr-3 leading-none`,\n                    getBackground(type),\n                ]}\n            >\n                {title}\n            </span>\n        )}\n        <span css={tw`mr-2 text-left flex-auto`}>{children}</span>\n    </Container>\n);\nMessageBox.displayName = 'MessageBox';\n\nexport default MessageBox;\n"
  },
  {
    "path": "resources/scripts/components/NavigationBar.tsx",
    "content": "import * as React from 'react';\nimport { useState } from 'react';\nimport { Link, NavLink } from 'react-router-dom';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faCogs, faLayerGroup, faSignOutAlt } from '@fortawesome/free-solid-svg-icons';\nimport { useStoreState } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport SearchContainer from '@/components/dashboard/search/SearchContainer';\nimport tw, { theme } from 'twin.macro';\nimport styled from 'styled-components/macro';\nimport http from '@/api/http';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport Tooltip from '@/components/elements/tooltip/Tooltip';\nimport Avatar from '@/components/Avatar';\n\nconst RightNavigation = styled.div`\n    & > a,\n    & > button,\n    & > .navigation-link {\n        ${tw`flex items-center h-full no-underline text-neutral-300 px-6 cursor-pointer transition-all duration-150`};\n\n        &:active,\n        &:hover {\n            ${tw`text-neutral-100 bg-black`};\n        }\n\n        &:active,\n        &:hover,\n        &.active {\n            box-shadow: inset 0 -2px ${theme`colors.cyan.600`.toString()};\n        }\n    }\n`;\n\nexport default () => {\n    const name = useStoreState((state: ApplicationStore) => state.settings.data!.name);\n    const rootAdmin = useStoreState((state: ApplicationStore) => state.user.data!.rootAdmin);\n    const [isLoggingOut, setIsLoggingOut] = useState(false);\n\n    const onTriggerLogout = () => {\n        setIsLoggingOut(true);\n        http.post('/auth/logout').finally(() => {\n            // @ts-expect-error this is valid\n            window.location = '/';\n        });\n    };\n\n    return (\n        <div className={'w-full bg-neutral-900 shadow-md overflow-x-auto'}>\n            <SpinnerOverlay visible={isLoggingOut} />\n            <div className={'mx-auto w-full flex items-center h-[3.5rem] max-w-[1200px]'}>\n                <div id={'logo'} className={'flex flex-1'}>\n                    <Link\n                        to={'/'}\n                        className={\n                            'text-2xl font-header font-medium px-4 no-underline text-neutral-200 hover:text-neutral-100 transition-colors duration-150'\n                        }\n                    >\n                        {useStoreState((state) => {\n                            const logoTitle = state.settings.data?.logo.title;\n                            return logoTitle ? <img src={logoTitle} /> : name;\n                        })}\n                    </Link>\n                </div>\n                <RightNavigation className={'flex h-full items-center justify-center'}>\n                    <SearchContainer />\n                    <Tooltip placement={'bottom'} content={'仪表盘'}>\n                        <NavLink to={'/'} exact>\n                            <FontAwesomeIcon icon={faLayerGroup} />\n                        </NavLink>\n                    </Tooltip>\n                    {rootAdmin && (\n                        <Tooltip placement={'bottom'} content={'管理员后台'}>\n                            <a href={'/admin'} rel={'noreferrer'}>\n                                <FontAwesomeIcon icon={faCogs} />\n                            </a>\n                        </Tooltip>\n                    )}\n                    <Tooltip placement={'bottom'} content={'账号设置'}>\n                        <NavLink to={'/account'}>\n                            <span className={'flex items-center w-5 h-5'}>\n                                <Avatar.User />\n                            </span>\n                        </NavLink>\n                    </Tooltip>\n                    <Tooltip placement={'bottom'} content={'登出'}>\n                        <button onClick={onTriggerLogout}>\n                            <FontAwesomeIcon icon={faSignOutAlt} />\n                        </button>\n                    </Tooltip>\n                </RightNavigation>\n            </div>\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/auth/ForgotPasswordContainer.tsx",
    "content": "import * as React from 'react';\nimport { useEffect, useRef, useState } from 'react';\nimport { Link } from 'react-router-dom';\nimport requestPasswordResetEmail from '@/api/auth/requestPasswordResetEmail';\nimport { httpErrorToHuman } from '@/api/http';\nimport LoginFormContainer from '@/components/auth/LoginFormContainer';\nimport { useStoreState } from 'easy-peasy';\nimport Field from '@/components/elements/Field';\nimport { Formik, FormikHelpers } from 'formik';\nimport { object, string } from 'yup';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport Reaptcha from 'reaptcha';\nimport useFlash from '@/plugins/useFlash';\n\ninterface Values {\n    email: string;\n}\n\nexport default () => {\n    const ref = useRef<Reaptcha>(null);\n    const [token, setToken] = useState('');\n\n    const { clearFlashes, addFlash } = useFlash();\n    const { enabled: recaptchaEnabled, siteKey } = useStoreState((state) => state.settings.data!.recaptcha);\n\n    useEffect(() => {\n        clearFlashes();\n    }, []);\n\n    const handleSubmission = ({ email }: Values, { setSubmitting, resetForm }: FormikHelpers<Values>) => {\n        clearFlashes();\n\n        // If there is no token in the state yet, request the token and then abort this submit request\n        // since it will be re-submitted when the recaptcha data is returned by the component.\n        if (recaptchaEnabled && !token) {\n            ref.current!.execute().catch((error) => {\n                console.error(error);\n\n                setSubmitting(false);\n                addFlash({ type: 'error', title: '错误', message: httpErrorToHuman(error) });\n            });\n\n            return;\n        }\n\n        requestPasswordResetEmail(email, token)\n            .then((response) => {\n                resetForm();\n                addFlash({ type: 'success', title: '成功', message: response });\n            })\n            .catch((error) => {\n                console.error(error);\n                addFlash({ type: 'error', title: '错误', message: httpErrorToHuman(error) });\n            })\n            .then(() => {\n                setToken('');\n                if (ref.current) ref.current.reset();\n\n                setSubmitting(false);\n            });\n    };\n\n    return (\n        <Formik\n            onSubmit={handleSubmission}\n            initialValues={{ email: '' }}\n            validationSchema={object().shape({\n                email: string()\n                    .email('必须提供有效的电子邮箱地址才能继续。')\n                    .required('必须提供有效的电子邮箱地址才能继续。'),\n            })}\n        >\n            {({ isSubmitting, setSubmitting, submitForm }) => (\n                <LoginFormContainer title={'请求重置密码'} css={tw`w-full flex`}>\n                    <Field\n                        light\n                        label={'邮箱地址'}\n                        description={'输入您的帐户电子邮箱地址以接收有关重置密码的说明。'}\n                        name={'email'}\n                        type={'email'}\n                    />\n                    <div css={tw`mt-6`}>\n                        <Button type={'submit'} size={'xlarge'} disabled={isSubmitting} isLoading={isSubmitting}>\n                            发送邮件\n                        </Button>\n                    </div>\n                    {recaptchaEnabled && (\n                        <Reaptcha\n                            ref={ref}\n                            size={'invisible'}\n                            sitekey={siteKey || '_invalid_key'}\n                            onVerify={(response) => {\n                                setToken(response);\n                                submitForm();\n                            }}\n                            onExpire={() => {\n                                setSubmitting(false);\n                                setToken('');\n                            }}\n                        />\n                    )}\n                    <div css={tw`mt-6 text-center`}>\n                        <Link\n                            to={'/auth/login'}\n                            css={tw`text-xs text-neutral-500 tracking-wide uppercase no-underline hover:text-neutral-700`}\n                        >\n                            返回登录\n                        </Link>\n                    </div>\n                </LoginFormContainer>\n            )}\n        </Formik>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/auth/LoginCheckpointContainer.tsx",
    "content": "import React, { useState } from 'react';\nimport { Link, RouteComponentProps } from 'react-router-dom';\nimport loginCheckpoint from '@/api/auth/loginCheckpoint';\nimport LoginFormContainer from '@/components/auth/LoginFormContainer';\nimport { ActionCreator } from 'easy-peasy';\nimport { StaticContext } from 'react-router';\nimport { useFormikContext, withFormik } from 'formik';\nimport useFlash from '@/plugins/useFlash';\nimport { FlashStore } from '@/state/flashes';\nimport Field from '@/components/elements/Field';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\n\ninterface Values {\n    code: string;\n    recoveryCode: '';\n}\n\ntype OwnProps = RouteComponentProps<Record<string, string | undefined>, StaticContext, { token?: string }>;\n\ntype Props = OwnProps & {\n    clearAndAddHttpError: ActionCreator<FlashStore['clearAndAddHttpError']['payload']>;\n};\n\nconst LoginCheckpointContainer = () => {\n    const { isSubmitting, setFieldValue } = useFormikContext<Values>();\n    const [isMissingDevice, setIsMissingDevice] = useState(false);\n\n    return (\n        <LoginFormContainer title={'设备检查'} css={tw`w-full flex`}>\n            <div css={tw`mt-6`}>\n                <Field\n                    light\n                    name={isMissingDevice ? 'recoveryCode' : 'code'}\n                    title={isMissingDevice ? '恢复代码' : '登录代码'}\n                    description={\n                        isMissingDevice\n                            ? '输入在此帐户上设置动态口令认证时生成的恢复代码之一以继续。'\n                            : '输入由您的设备随机生成的动态口令。'\n                    }\n                    type={'text'}\n                    autoComplete={'one-time-code'}\n                    autoFocus\n                />\n            </div>\n            <div css={tw`mt-6`}>\n                <Button size={'xlarge'} type={'submit'} disabled={isSubmitting} isLoading={isSubmitting}>\n                    继续\n                </Button>\n            </div>\n            <div css={tw`mt-6 text-center`}>\n                <span\n                    onClick={() => {\n                        setFieldValue('code', '');\n                        setFieldValue('recoveryCode', '');\n                        setIsMissingDevice((s) => !s);\n                    }}\n                    css={tw`cursor-pointer text-xs text-neutral-500 tracking-wide uppercase no-underline hover:text-neutral-700`}\n                >\n                    {!isMissingDevice ? '我的设备丢失了' : '我的设备还在'}\n                </span>\n            </div>\n            <div css={tw`mt-6 text-center`}>\n                <Link\n                    to={'/auth/login'}\n                    css={tw`text-xs text-neutral-500 tracking-wide uppercase no-underline hover:text-neutral-700`}\n                >\n                    返回登录\n                </Link>\n            </div>\n        </LoginFormContainer>\n    );\n};\n\nconst EnhancedForm = withFormik<Props, Values>({\n    handleSubmit: ({ code, recoveryCode }, { setSubmitting, props: { clearAndAddHttpError, location } }) => {\n        loginCheckpoint(location.state?.token || '', code, recoveryCode)\n            .then((response) => {\n                if (response.complete) {\n                    // @ts-expect-error this is valid\n                    window.location = response.intended || '/';\n                    return;\n                }\n\n                setSubmitting(false);\n            })\n            .catch((error) => {\n                console.error(error);\n                setSubmitting(false);\n                clearAndAddHttpError({ error });\n            });\n    },\n\n    mapPropsToValues: () => ({\n        code: '',\n        recoveryCode: '',\n    }),\n})(LoginCheckpointContainer);\n\nexport default ({ history, location, ...props }: OwnProps) => {\n    const { clearAndAddHttpError } = useFlash();\n\n    if (!location.state?.token) {\n        history.replace('/auth/login');\n\n        return null;\n    }\n\n    return (\n        <EnhancedForm clearAndAddHttpError={clearAndAddHttpError} history={history} location={location} {...props} />\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/auth/LoginContainer.tsx",
    "content": "import React, { useEffect, useRef, useState } from 'react';\nimport { Link, RouteComponentProps } from 'react-router-dom';\nimport login from '@/api/auth/login';\nimport LoginFormContainer from '@/components/auth/LoginFormContainer';\nimport { useStoreState } from 'easy-peasy';\nimport { Formik, FormikHelpers } from 'formik';\nimport { object, string } from 'yup';\nimport Field from '@/components/elements/Field';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport Reaptcha from 'reaptcha';\nimport useFlash from '@/plugins/useFlash';\n\ninterface Values {\n    username: string;\n    password: string;\n}\n\nconst LoginContainer = ({ history }: RouteComponentProps) => {\n    const ref = useRef<Reaptcha>(null);\n    const [token, setToken] = useState('');\n\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const { enabled: recaptchaEnabled, siteKey } = useStoreState((state) => state.settings.data!.recaptcha);\n    const name = useStoreState((state) => state.settings.data?.name);\n\n    useEffect(() => {\n        clearFlashes();\n    }, []);\n\n    const onSubmit = (values: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        clearFlashes();\n\n        // If there is no token in the state yet, request the token and then abort this submit request\n        // since it will be re-submitted when the recaptcha data is returned by the component.\n        if (recaptchaEnabled && !token) {\n            ref.current!.execute().catch((error) => {\n                console.error(error);\n\n                setSubmitting(false);\n                clearAndAddHttpError({ error });\n            });\n\n            return;\n        }\n\n        login({ ...values, recaptchaData: token })\n            .then((response) => {\n                if (response.complete) {\n                    // @ts-expect-error this is valid\n                    window.location = response.intended || '/';\n                    return;\n                }\n\n                history.replace('/auth/login/checkpoint', { token: response.confirmationToken });\n            })\n            .catch((error) => {\n                console.error(error);\n\n                setToken('');\n                if (ref.current) ref.current.reset();\n\n                setSubmitting(false);\n                clearAndAddHttpError({ error });\n            });\n    };\n\n    return (\n        <Formik\n            onSubmit={onSubmit}\n            initialValues={{ username: '', password: '' }}\n            validationSchema={object().shape({\n                username: string().required('必须提供用户名或电子邮箱。'),\n                password: string().required('请输入您的帐户密码。'),\n            })}\n        >\n            {({ isSubmitting, setSubmitting, submitForm }) => (\n                <LoginFormContainer title={'登录到 ' + name} css={tw`w-full flex`}>\n                    <Field light type={'text'} label={'用户名或邮箱地址'} name={'username'} disabled={isSubmitting} />\n                    <div css={tw`mt-6`}>\n                        <Field light type={'password'} label={'密码'} name={'password'} disabled={isSubmitting} />\n                    </div>\n                    <div css={tw`mt-6`}>\n                        <Button type={'submit'} size={'xlarge'} isLoading={isSubmitting} disabled={isSubmitting}>\n                            登录\n                        </Button>\n                    </div>\n                    {recaptchaEnabled && (\n                        <Reaptcha\n                            ref={ref}\n                            size={'invisible'}\n                            sitekey={siteKey || '_invalid_key'}\n                            onVerify={(response) => {\n                                setToken(response);\n                                submitForm();\n                            }}\n                            onExpire={() => {\n                                setSubmitting(false);\n                                setToken('');\n                            }}\n                        />\n                    )}\n                    <div css={tw`mt-6 text-center`}>\n                        <Link\n                            to={'/auth/password'}\n                            css={tw`text-xs text-neutral-500 tracking-wide no-underline uppercase hover:text-neutral-600`}\n                        >\n                            忘记密码?\n                        </Link>\n                    </div>\n                </LoginFormContainer>\n            )}\n        </Formik>\n    );\n};\n\nexport default LoginContainer;\n"
  },
  {
    "path": "resources/scripts/components/auth/LoginFormContainer.tsx",
    "content": "import React, { forwardRef } from 'react';\nimport { Form } from 'formik';\nimport styled from 'styled-components/macro';\nimport { breakpoint } from '@/theme';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport tw from 'twin.macro';\nimport { useStoreState } from 'easy-peasy';\n\ntype Props = React.DetailedHTMLProps<React.FormHTMLAttributes<HTMLFormElement>, HTMLFormElement> & {\n    title?: string;\n};\n\nconst Container = styled.div`\n    ${breakpoint('sm')`\n        ${tw`w-4/5 mx-auto`}\n    `};\n\n    ${breakpoint('md')`\n        ${tw`p-10`}\n    `};\n\n    ${breakpoint('lg')`\n        ${tw`w-3/5`}\n    `};\n\n    ${breakpoint('xl')`\n        ${tw`w-full`}\n        max-width: 700px;\n    `};\n`;\n\nexport default forwardRef<HTMLFormElement, Props>(({ title, ...props }, ref) => (\n    <Container>\n        {title && <h2 css={tw`text-3xl text-center text-neutral-100 font-medium py-4`}>{title}</h2>}\n        <FlashMessageRender css={tw`mb-2 px-1`} />\n        <Form {...props} ref={ref}>\n            <div css={tw`md:flex w-full bg-white shadow-lg rounded-lg p-6 md:pl-0 mx-1`}>\n                <div css={tw`flex-none select-none mb-6 md:mb-0 self-center`}>\n                    <img\n                        src={useStoreState((state) => state.settings.data?.logo.auth) || '/assets/svgs/pterodactyl.svg'}\n                        css={tw`block w-48 md:w-64 mx-auto`}\n                    />\n                </div>\n                <div css={tw`flex-1`}>{props.children}</div>\n            </div>\n        </Form>\n        <p css={tw`text-center text-neutral-500 text-xs mt-4`}>\n            &copy; 2015 - {new Date().getFullYear()}&nbsp;\n            <a\n                rel={'noopener nofollow noreferrer'}\n                href={'https://pterodactyl.io'}\n                target={'_blank'}\n                css={tw`no-underline text-neutral-500 hover:text-neutral-300`}\n            >\n                Pterodactyl Software\n            </a>\n            &nbsp;| Sinicizated by&nbsp;\n            <a\n                rel={'noopener nofollow noreferrer'}\n                href={'https://pterodactyl.top'}\n                target={'_blank'}\n                css={tw`no-underline text-neutral-500 hover:text-neutral-300`}\n            >\n                翼龙中国\n            </a>\n        </p>\n        {useStoreState((state) => state.settings.data?.icp.enabled) && (\n            <p css={tw`text-center text-neutral-500 text-xs mt-4`}>\n                {useStoreState((state) => state.settings.data?.icp.security_record) && (\n                    <a\n                        rel={'noopener nofollow noreferrer'}\n                        href={\n                            'https://www.beian.gov.cn/portal/registerSystemInfo?recordcode=' +\n                            useStoreState((state) => state.settings.data?.icp.security_record)?.match(/\\d+/g)\n                        }\n                        target={'_blank'}\n                        css={tw`no-underline text-neutral-500 hover:text-neutral-300`}\n                    >\n                        <img src={'/assets/images/gongan.png'} css={tw`display: inline`} />\n                        &nbsp;\n                        {useStoreState((state) => state.settings.data?.icp.security_record)}\n                    </a>\n                )}\n                {useStoreState((state) => state.settings.data?.icp.security_record) && <a>&nbsp;|&nbsp;</a>}\n                <a\n                    rel={'noopener nofollow noreferrer'}\n                    href={'https://beian.miit.gov.cn'}\n                    target={'_blank'}\n                    css={tw`no-underline text-neutral-500 hover:text-neutral-300`}\n                >\n                    {useStoreState((state) => state.settings.data?.icp.record)}\n                </a>\n            </p>\n        )}\n    </Container>\n));\n"
  },
  {
    "path": "resources/scripts/components/auth/ResetPasswordContainer.tsx",
    "content": "import React, { useState } from 'react';\nimport { RouteComponentProps } from 'react-router';\nimport { Link } from 'react-router-dom';\nimport performPasswordReset from '@/api/auth/performPasswordReset';\nimport { httpErrorToHuman } from '@/api/http';\nimport LoginFormContainer from '@/components/auth/LoginFormContainer';\nimport { Actions, useStoreActions } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport { Formik, FormikHelpers } from 'formik';\nimport { object, ref, string } from 'yup';\nimport Field from '@/components/elements/Field';\nimport Input from '@/components/elements/Input';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\n\ninterface Values {\n    password: string;\n    passwordConfirmation: string;\n}\n\nexport default ({ match, location }: RouteComponentProps<{ token: string }>) => {\n    const [email, setEmail] = useState('');\n\n    const { clearFlashes, addFlash } = useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n\n    const parsed = new URLSearchParams(location.search);\n    if (email.length === 0 && parsed.get('email')) {\n        setEmail(parsed.get('email') || '');\n    }\n\n    const submit = ({ password, passwordConfirmation }: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        clearFlashes();\n        performPasswordReset(email, { token: match.params.token, password, passwordConfirmation })\n            .then(() => {\n                // @ts-expect-error this is valid\n                window.location = '/';\n            })\n            .catch((error) => {\n                console.error(error);\n\n                setSubmitting(false);\n                addFlash({ type: 'error', title: '错误', message: httpErrorToHuman(error) });\n            });\n    };\n\n    return (\n        <Formik\n            onSubmit={submit}\n            initialValues={{\n                password: '',\n                passwordConfirmation: '',\n            }}\n            validationSchema={object().shape({\n                password: string().required('需要新密码。').min(8, '您的新密码长度应至少为 8 个字符。'),\n                passwordConfirmation: string()\n                    .required('您的新密码不匹配。')\n                    // @ts-expect-error this is valid\n                    .oneOf([ref('password'), null], '您的新密码不匹配。'),\n            })}\n        >\n            {({ isSubmitting }) => (\n                <LoginFormContainer title={'重置密码'} css={tw`w-full flex`}>\n                    <div>\n                        <label>邮箱</label>\n                        <Input value={email} isLight disabled />\n                    </div>\n                    <div css={tw`mt-6`}>\n                        <Field\n                            light\n                            label={'新密码'}\n                            name={'password'}\n                            type={'password'}\n                            description={'密码长度必须至少为 8 个字符。'}\n                        />\n                    </div>\n                    <div css={tw`mt-6`}>\n                        <Field light label={'确认新密码'} name={'passwordConfirmation'} type={'password'} />\n                    </div>\n                    <div css={tw`mt-6`}>\n                        <Button size={'xlarge'} type={'submit'} disabled={isSubmitting} isLoading={isSubmitting}>\n                            重置密码\n                        </Button>\n                    </div>\n                    <div css={tw`mt-6 text-center`}>\n                        <Link\n                            to={'/auth/login'}\n                            css={tw`text-xs text-neutral-500 tracking-wide no-underline uppercase hover:text-neutral-600`}\n                        >\n                            返回登录\n                        </Link>\n                    </div>\n                </LoginFormContainer>\n            )}\n        </Formik>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/AccountApiContainer.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport ContentBox from '@/components/elements/ContentBox';\nimport CreateApiKeyForm from '@/components/dashboard/forms/CreateApiKeyForm';\nimport getApiKeys, { ApiKey } from '@/api/account/getApiKeys';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faKey, faTrashAlt } from '@fortawesome/free-solid-svg-icons';\nimport deleteApiKey from '@/api/account/deleteApiKey';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport { format } from 'date-fns';\nimport PageContentBlock from '@/components/elements/PageContentBlock';\nimport tw from 'twin.macro';\nimport GreyRowBox from '@/components/elements/GreyRowBox';\nimport { Dialog } from '@/components/elements/dialog';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport Code from '@/components/elements/Code';\n\nexport default () => {\n    const [deleteIdentifier, setDeleteIdentifier] = useState('');\n    const [keys, setKeys] = useState<ApiKey[]>([]);\n    const [loading, setLoading] = useState(true);\n    const { clearAndAddHttpError } = useFlashKey('account');\n\n    useEffect(() => {\n        getApiKeys()\n            .then((keys) => setKeys(keys))\n            .then(() => setLoading(false))\n            .catch((error) => clearAndAddHttpError(error));\n    }, []);\n\n    const doDeletion = (identifier: string) => {\n        setLoading(true);\n\n        clearAndAddHttpError();\n        deleteApiKey(identifier)\n            .then(() => setKeys((s) => [...(s || []).filter((key) => key.identifier !== identifier)]))\n            .catch((error) => clearAndAddHttpError(error))\n            .then(() => {\n                setLoading(false);\n                setDeleteIdentifier('');\n            });\n    };\n\n    return (\n        <PageContentBlock title={'账户 API'}>\n            <FlashMessageRender byKey={'account'} />\n            <div css={tw`md:flex flex-nowrap my-10`}>\n                <ContentBox title={'创建 API 密钥'} css={tw`flex-none w-full md:w-1/2`}>\n                    <CreateApiKeyForm onKeyCreated={(key) => setKeys((s) => [...s!, key])} />\n                </ContentBox>\n                <ContentBox title={'API 密钥'} css={tw`flex-1 overflow-hidden mt-8 md:mt-0 md:ml-8`}>\n                    <SpinnerOverlay visible={loading} />\n                    <Dialog.Confirm\n                        title={'确认删除秘钥'}\n                        confirm={'确认'}\n                        open={!!deleteIdentifier}\n                        onClose={() => setDeleteIdentifier('')}\n                        onConfirmed={() => doDeletion(deleteIdentifier)}\n                    >\n                        所有使用 <Code>{deleteIdentifier}</Code> 密钥的请求将立即失效！\n                    </Dialog.Confirm>\n                    {keys.length === 0 ? (\n                        <p css={tw`text-center text-sm`}>{loading ? '载入中.....' : '此账户无 API 密钥'}</p>\n                    ) : (\n                        keys.map((key, index) => (\n                            <GreyRowBox\n                                key={key.identifier}\n                                css={[tw`bg-neutral-600 flex items-center`, index > 0 && tw`mt-2`]}\n                            >\n                                <FontAwesomeIcon icon={faKey} css={tw`text-neutral-300`} />\n                                <div css={tw`ml-4 flex-1 overflow-hidden`}>\n                                    <p css={tw`text-sm break-words`}>{key.description}</p>\n                                    <p css={tw`text-2xs text-neutral-300 uppercase`}>\n                                        上次使用于:&nbsp;\n                                        {key.lastUsedAt ? format(key.lastUsedAt, 'yyyy年M月d日 HH:mm') : '从未'}\n                                    </p>\n                                </div>\n                                <p css={tw`text-sm ml-4 hidden md:block`}>\n                                    <code css={tw`font-mono py-1 px-2 bg-neutral-900 rounded`}>{key.identifier}</code>\n                                </p>\n                                <button css={tw`ml-4 p-2 text-sm`} onClick={() => setDeleteIdentifier(key.identifier)}>\n                                    <FontAwesomeIcon\n                                        icon={faTrashAlt}\n                                        css={tw`text-neutral-400 hover:text-red-400 transition-colors duration-150`}\n                                    />\n                                </button>\n                            </GreyRowBox>\n                        ))\n                    )}\n                </ContentBox>\n            </div>\n        </PageContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/AccountOverviewContainer.tsx",
    "content": "import * as React from 'react';\nimport ContentBox from '@/components/elements/ContentBox';\nimport UpdatePasswordForm from '@/components/dashboard/forms/UpdatePasswordForm';\nimport UpdateEmailAddressForm from '@/components/dashboard/forms/UpdateEmailAddressForm';\nimport ConfigureTwoFactorForm from '@/components/dashboard/forms/ConfigureTwoFactorForm';\nimport PageContentBlock from '@/components/elements/PageContentBlock';\nimport tw from 'twin.macro';\nimport { breakpoint } from '@/theme';\nimport styled from 'styled-components/macro';\nimport MessageBox from '@/components/MessageBox';\nimport { useLocation } from 'react-router-dom';\n\nconst Container = styled.div`\n    ${tw`flex flex-wrap`};\n\n    & > div {\n        ${tw`w-full`};\n\n        ${breakpoint('sm')`\n      width: calc(50% - 1rem);\n    `}\n\n        ${breakpoint('md')`\n      ${tw`w-auto flex-1`};\n    `}\n    }\n`;\n\nexport default () => {\n    const { state } = useLocation<undefined | { twoFactorRedirect?: boolean }>();\n\n    return (\n        <PageContentBlock title={'账户概况'}>\n            {state?.twoFactorRedirect && (\n                <MessageBox title={'需要启用动态口令认证'} type={'error'}>\n                    您的帐户必须启用动态口令认证才能继续使用。\n                </MessageBox>\n            )}\n\n            <Container css={[tw`lg:grid lg:grid-cols-3 mb-10`, state?.twoFactorRedirect ? tw`mt-4` : tw`mt-10`]}>\n                <ContentBox title={'更新密码'} showFlashes={'account:password'}>\n                    <UpdatePasswordForm />\n                </ContentBox>\n                <ContentBox css={tw`mt-8 sm:mt-0 sm:ml-8`} title={'更新电子邮箱地址'} showFlashes={'account:email'}>\n                    <UpdateEmailAddressForm />\n                </ContentBox>\n                <ContentBox css={tw`md:ml-8 mt-8 md:mt-0`} title={'配置动态口令认证'}>\n                    <ConfigureTwoFactorForm />\n                </ContentBox>\n            </Container>\n        </PageContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/ApiKeyModal.tsx",
    "content": "import React, { useContext } from 'react';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport asModal from '@/hoc/asModal';\nimport ModalContext from '@/context/ModalContext';\nimport CopyOnClick from '@/components/elements/CopyOnClick';\n\ninterface Props {\n    apiKey: string;\n}\n\nconst ApiKeyModal = ({ apiKey }: Props) => {\n    const { dismiss } = useContext(ModalContext);\n\n    return (\n        <>\n            <h3 css={tw`mb-6 text-2xl`}>你的 API 密钥</h3>\n            <p css={tw`text-sm mb-6`}>您请求的 API 密钥如下所示。请将其存放在安全的地方，它不会 再次显示。</p>\n            <pre css={tw`text-sm bg-neutral-900 rounded py-2 px-4 font-mono`}>\n                <CopyOnClick text={apiKey}>\n                    <code css={tw`font-mono`}>{apiKey}</code>\n                </CopyOnClick>\n            </pre>\n            <div css={tw`flex justify-end mt-6`}>\n                <Button type={'button'} onClick={() => dismiss()}>\n                    关闭\n                </Button>\n            </div>\n        </>\n    );\n};\n\nApiKeyModal.displayName = 'ApiKeyModal';\n\nexport default asModal<Props>({\n    closeOnEscape: false,\n    closeOnBackground: false,\n})(ApiKeyModal);\n"
  },
  {
    "path": "resources/scripts/components/dashboard/DashboardContainer.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { Server } from '@/api/server/getServer';\nimport getServers from '@/api/getServers';\nimport ServerRow from '@/components/dashboard/ServerRow';\nimport Spinner from '@/components/elements/Spinner';\nimport PageContentBlock from '@/components/elements/PageContentBlock';\nimport useFlash from '@/plugins/useFlash';\nimport { useStoreState } from 'easy-peasy';\nimport { usePersistedState } from '@/plugins/usePersistedState';\nimport Switch from '@/components/elements/Switch';\nimport tw from 'twin.macro';\nimport useSWR from 'swr';\nimport { PaginatedResult } from '@/api/http';\nimport Pagination from '@/components/elements/Pagination';\nimport { useLocation } from 'react-router-dom';\n\nexport default () => {\n    const { search } = useLocation();\n    const defaultPage = Number(new URLSearchParams(search).get('page') || '1');\n\n    const [page, setPage] = useState(!isNaN(defaultPage) && defaultPage > 0 ? defaultPage : 1);\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const uuid = useStoreState((state) => state.user.data!.uuid);\n    const rootAdmin = useStoreState((state) => state.user.data!.rootAdmin);\n    const [showOnlyAdmin, setShowOnlyAdmin] = usePersistedState(`${uuid}:show_all_servers`, false);\n\n    const { data: servers, error } = useSWR<PaginatedResult<Server>>(\n        ['/api/client/servers', showOnlyAdmin && rootAdmin, page],\n        () => getServers({ page, type: showOnlyAdmin && rootAdmin ? 'admin' : undefined })\n    );\n\n    useEffect(() => {\n        setPage(1);\n    }, [showOnlyAdmin]);\n\n    useEffect(() => {\n        if (!servers) return;\n        if (servers.pagination.currentPage > 1 && !servers.items.length) {\n            setPage(1);\n        }\n    }, [servers?.pagination.currentPage]);\n\n    useEffect(() => {\n        // Don't use react-router to handle changing this part of the URL, otherwise it\n        // triggers a needless re-render. We just want to track this in the URL incase the\n        // user refreshes the page.\n        window.history.replaceState(null, document.title, `/${page <= 1 ? '' : `?page=${page}`}`);\n    }, [page]);\n\n    useEffect(() => {\n        if (error) clearAndAddHttpError({ key: 'dashboard', error });\n        if (!error) clearFlashes('dashboard');\n    }, [error]);\n\n    return (\n        <PageContentBlock title={'仪表盘'} showFlashKey={'dashboard'}>\n            {rootAdmin && (\n                <div css={tw`mb-2 flex justify-end items-center`}>\n                    <p css={tw`uppercase text-xs text-neutral-400 mr-2`}>\n                        {showOnlyAdmin ? '显示其他人的服务器' : '显示你的服务器'}\n                    </p>\n                    <Switch\n                        name={'show_all_servers'}\n                        defaultChecked={showOnlyAdmin}\n                        onChange={() => setShowOnlyAdmin((s) => !s)}\n                    />\n                </div>\n            )}\n            {!servers ? (\n                <Spinner centered size={'large'} />\n            ) : (\n                <Pagination data={servers} onPageSelect={setPage}>\n                    {({ items }) =>\n                        items.length > 0 ? (\n                            items.map((server, index) => (\n                                <ServerRow key={server.uuid} server={server} css={index > 0 ? tw`mt-2` : undefined} />\n                            ))\n                        ) : (\n                            <p css={tw`text-center text-sm text-neutral-400`}>\n                                {showOnlyAdmin ? '这里没有服务器可显示。' : '你的账户下没有关联的服务器。'}\n                            </p>\n                        )\n                    }\n                </Pagination>\n            )}\n        </PageContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/ServerRow.tsx",
    "content": "import React, { memo, useEffect, useRef, useState } from 'react';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faEthernet, faHdd, faMemory, faMicrochip, faServer } from '@fortawesome/free-solid-svg-icons';\nimport { Link } from 'react-router-dom';\nimport { Server } from '@/api/server/getServer';\nimport getServerResourceUsage, { ServerPowerState, ServerStats } from '@/api/server/getServerResourceUsage';\nimport { bytesToString, ip, mbToBytes } from '@/lib/formatters';\nimport tw from 'twin.macro';\nimport GreyRowBox from '@/components/elements/GreyRowBox';\nimport Spinner from '@/components/elements/Spinner';\nimport styled from 'styled-components/macro';\nimport isEqual from 'react-fast-compare';\n\n// Determines if the current value is in an alarm threshold so we can show it in red rather\n// than the more faded default style.\nconst isAlarmState = (current: number, limit: number): boolean => limit > 0 && current / (limit * 1024 * 1024) >= 0.9;\n\nconst Icon = memo(\n    styled(FontAwesomeIcon)<{ $alarm: boolean }>`\n        ${(props) => (props.$alarm ? tw`text-red-400` : tw`text-neutral-500`)};\n    `,\n    isEqual\n);\n\nconst IconDescription = styled.p<{ $alarm: boolean }>`\n    ${tw`text-sm ml-2`};\n    ${(props) => (props.$alarm ? tw`text-white` : tw`text-neutral-400`)};\n`;\n\nconst StatusIndicatorBox = styled(GreyRowBox)<{ $status: ServerPowerState | undefined }>`\n    ${tw`grid grid-cols-12 gap-4 relative`};\n\n    & .status-bar {\n        ${tw`w-2 bg-red-500 absolute right-0 z-20 rounded-full m-1 opacity-50 transition-all duration-150`};\n        height: calc(100% - 0.5rem);\n\n        ${({ $status }) =>\n            !$status || $status === 'offline'\n                ? tw`bg-red-500`\n                : $status === 'running'\n                ? tw`bg-green-500`\n                : tw`bg-yellow-500`};\n    }\n\n    &:hover .status-bar {\n        ${tw`opacity-75`};\n    }\n`;\n\ntype Timer = ReturnType<typeof setInterval>;\n\nexport default ({ server, className }: { server: Server; className?: string }) => {\n    const interval = useRef<Timer>(null) as React.MutableRefObject<Timer>;\n    const [isSuspended, setIsSuspended] = useState(server.status === 'suspended');\n    const [stats, setStats] = useState<ServerStats | null>(null);\n\n    const getStats = () =>\n        getServerResourceUsage(server.uuid)\n            .then((data) => setStats(data))\n            .catch((error) => console.error(error));\n\n    useEffect(() => {\n        setIsSuspended(stats?.isSuspended || server.status === 'suspended');\n    }, [stats?.isSuspended, server.status]);\n\n    useEffect(() => {\n        // Don't waste a HTTP request if there is nothing important to show to the user because\n        // the server is suspended.\n        if (isSuspended) return;\n\n        getStats().then(() => {\n            interval.current = setInterval(() => getStats(), 30000);\n        });\n\n        return () => {\n            interval.current && clearInterval(interval.current);\n        };\n    }, [isSuspended]);\n\n    const alarms = { cpu: false, memory: false, disk: false };\n    if (stats) {\n        alarms.cpu = server.limits.cpu === 0 ? false : stats.cpuUsagePercent >= server.limits.cpu * 0.9;\n        alarms.memory = isAlarmState(stats.memoryUsageInBytes, server.limits.memory);\n        alarms.disk = server.limits.disk === 0 ? false : isAlarmState(stats.diskUsageInBytes, server.limits.disk);\n    }\n\n    const diskLimit = server.limits.disk !== 0 ? bytesToString(mbToBytes(server.limits.disk)) : '无限制';\n    const memoryLimit = server.limits.memory !== 0 ? bytesToString(mbToBytes(server.limits.memory)) : '无限制';\n    const cpuLimit = server.limits.cpu !== 0 ? server.limits.cpu + ' %' : '无限制';\n\n    return (\n        <StatusIndicatorBox as={Link} to={`/server/${server.id}`} className={className} $status={stats?.status}>\n            <div css={tw`flex items-center col-span-12 sm:col-span-5 lg:col-span-6`}>\n                <div className={'icon mr-4'}>\n                    <FontAwesomeIcon icon={faServer} />\n                </div>\n                <div>\n                    <p css={tw`text-lg break-words`}>{server.name}</p>\n                    {!!server.description && (\n                        <p css={tw`text-sm text-neutral-300 break-words line-clamp-2`}>{server.description}</p>\n                    )}\n                </div>\n            </div>\n            <div css={tw`flex-1 ml-4 lg:block lg:col-span-2 hidden`}>\n                <div css={tw`flex justify-center`}>\n                    <FontAwesomeIcon icon={faEthernet} css={tw`text-neutral-500`} />\n                    <p css={tw`text-sm text-neutral-400 ml-2`}>\n                        {server.allocations\n                            .filter((alloc) => alloc.isDefault)\n                            .map((allocation) => (\n                                <React.Fragment key={allocation.ip + allocation.port.toString()}>\n                                    {allocation.alias || ip(allocation.ip)}:{allocation.port}\n                                </React.Fragment>\n                            ))}\n                    </p>\n                </div>\n            </div>\n            <div css={tw`hidden col-span-7 lg:col-span-4 sm:flex items-baseline justify-center`}>\n                {!stats || isSuspended ? (\n                    isSuspended ? (\n                        <div css={tw`flex-1 text-center`}>\n                            <span css={tw`bg-red-500 rounded px-2 py-1 text-red-100 text-xs`}>\n                                {server.status === 'suspended' ? '已冻结' : '连接错误'}\n                            </span>\n                        </div>\n                    ) : server.isTransferring || server.status ? (\n                        <div css={tw`flex-1 text-center`}>\n                            <span css={tw`bg-neutral-500 rounded px-2 py-1 text-neutral-100 text-xs`}>\n                                {server.isTransferring\n                                    ? '转移中'\n                                    : server.status === 'installing'\n                                    ? '安装中'\n                                    : server.status === 'restoring_backup'\n                                    ? '正在回档'\n                                    : '不可用'}\n                            </span>\n                        </div>\n                    ) : (\n                        <Spinner size={'small'} />\n                    )\n                ) : (\n                    <React.Fragment>\n                        <div css={tw`flex-1 ml-4 sm:block hidden`}>\n                            <div css={tw`flex justify-center`}>\n                                <Icon icon={faMicrochip} $alarm={alarms.cpu} />\n                                <IconDescription $alarm={alarms.cpu}>\n                                    {stats.cpuUsagePercent.toFixed(2)} %\n                                </IconDescription>\n                            </div>\n                            <p css={tw`text-xs text-neutral-600 text-center mt-1`}>共 {cpuLimit}</p>\n                        </div>\n                        <div css={tw`flex-1 ml-4 sm:block hidden`}>\n                            <div css={tw`flex justify-center`}>\n                                <Icon icon={faMemory} $alarm={alarms.memory} />\n                                <IconDescription $alarm={alarms.memory}>\n                                    {bytesToString(stats.memoryUsageInBytes)}\n                                </IconDescription>\n                            </div>\n                            <p css={tw`text-xs text-neutral-600 text-center mt-1`}>共 {memoryLimit}</p>\n                        </div>\n                        <div css={tw`flex-1 ml-4 sm:block hidden`}>\n                            <div css={tw`flex justify-center`}>\n                                <Icon icon={faHdd} $alarm={alarms.disk} />\n                                <IconDescription $alarm={alarms.disk}>\n                                    {bytesToString(stats.diskUsageInBytes)}\n                                </IconDescription>\n                            </div>\n                            <p css={tw`text-xs text-neutral-600 text-center mt-1`}>共 {diskLimit}</p>\n                        </div>\n                    </React.Fragment>\n                )}\n            </div>\n            <div className={'status-bar'} />\n        </StatusIndicatorBox>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/activity/ActivityLogContainer.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { ActivityLogFilters, useActivityLogs } from '@/api/account/activity';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport PageContentBlock from '@/components/elements/PageContentBlock';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport { Link } from 'react-router-dom';\nimport PaginationFooter from '@/components/elements/table/PaginationFooter';\nimport { DesktopComputerIcon, XCircleIcon } from '@heroicons/react/solid';\nimport Spinner from '@/components/elements/Spinner';\nimport { styles as btnStyles } from '@/components/elements/button/index';\nimport classNames from 'classnames';\nimport ActivityLogEntry from '@/components/elements/activity/ActivityLogEntry';\nimport Tooltip from '@/components/elements/tooltip/Tooltip';\nimport useLocationHash from '@/plugins/useLocationHash';\n\nexport default () => {\n    const { hash } = useLocationHash();\n    const { clearAndAddHttpError } = useFlashKey('account');\n    const [filters, setFilters] = useState<ActivityLogFilters>({ page: 1, sorts: { timestamp: -1 } });\n    const { data, isValidating, error } = useActivityLogs(filters, {\n        revalidateOnMount: true,\n        revalidateOnFocus: false,\n    });\n\n    useEffect(() => {\n        setFilters((value) => ({ ...value, filters: { ip: hash.ip, event: hash.event } }));\n    }, [hash]);\n\n    useEffect(() => {\n        clearAndAddHttpError(error);\n    }, [error]);\n\n    return (\n        <PageContentBlock title={'帐户活动日志'}>\n            <FlashMessageRender byKey={'account'} />\n            {(filters.filters?.event || filters.filters?.ip) && (\n                <div className={'flex justify-end mb-2'}>\n                    <Link\n                        to={'#'}\n                        className={classNames(btnStyles.button, btnStyles.text, 'w-full sm:w-auto')}\n                        onClick={() => setFilters((value) => ({ ...value, filters: {} }))}\n                    >\n                        重设过滤器 <XCircleIcon className={'w-4 h-4 ml-2'} />\n                    </Link>\n                </div>\n            )}\n            {!data && isValidating ? (\n                <Spinner centered />\n            ) : (\n                <div className={'bg-gray-700'}>\n                    {data?.items.map((activity) => (\n                        <ActivityLogEntry key={activity.id} activity={activity}>\n                            {typeof activity.properties.useragent === 'string' && (\n                                <Tooltip content={activity.properties.useragent} placement={'top'}>\n                                    <span>\n                                        <DesktopComputerIcon />\n                                    </span>\n                                </Tooltip>\n                            )}\n                        </ActivityLogEntry>\n                    ))}\n                </div>\n            )}\n            {data && (\n                <PaginationFooter\n                    pagination={data.pagination}\n                    onPageSelect={(page) => setFilters((value) => ({ ...value, page }))}\n                />\n            )}\n        </PageContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/forms/ConfigureTwoFactorForm.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { useStoreState } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport tw from 'twin.macro';\nimport { Button } from '@/components/elements/button/index';\nimport SetupTOTPDialog from '@/components/dashboard/forms/SetupTOTPDialog';\nimport RecoveryTokensDialog from '@/components/dashboard/forms/RecoveryTokensDialog';\nimport DisableTOTPDialog from '@/components/dashboard/forms/DisableTOTPDialog';\nimport { useFlashKey } from '@/plugins/useFlash';\n\nexport default () => {\n    const [tokens, setTokens] = useState<string[]>([]);\n    const [visible, setVisible] = useState<'enable' | 'disable' | null>(null);\n    const isEnabled = useStoreState((state: ApplicationStore) => state.user.data!.useTotp);\n    const { clearAndAddHttpError } = useFlashKey('account:two-step');\n\n    useEffect(() => {\n        return () => {\n            clearAndAddHttpError();\n        };\n    }, [visible]);\n\n    const onTokens = (tokens: string[]) => {\n        setTokens(tokens);\n        setVisible(null);\n    };\n\n    return (\n        <div>\n            <SetupTOTPDialog open={visible === 'enable'} onClose={() => setVisible(null)} onTokens={onTokens} />\n            <RecoveryTokensDialog tokens={tokens} open={tokens.length > 0} onClose={() => setTokens([])} />\n            <DisableTOTPDialog open={visible === 'disable'} onClose={() => setVisible(null)} />\n            <p css={tw`text-sm`}>\n                {isEnabled\n                    ? '您的帐户当前启用了动态口令认证。'\n                    : '您目前没有在您的帐户上启用动态口令认证，单击下面的按钮即可开始配置。'}\n            </p>\n            <div css={tw`mt-6`}>\n                {isEnabled ? (\n                    <Button.Danger onClick={() => setVisible('disable')}>禁用动态口令认证</Button.Danger>\n                ) : (\n                    <Button onClick={() => setVisible('enable')}>启用动态口令认证</Button>\n                )}\n            </div>\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/forms/CreateApiKeyForm.tsx",
    "content": "import React, { useState } from 'react';\nimport { Field, Form, Formik, FormikHelpers } from 'formik';\nimport { object, string } from 'yup';\nimport FormikFieldWrapper from '@/components/elements/FormikFieldWrapper';\nimport createApiKey from '@/api/account/createApiKey';\nimport { Actions, useStoreActions } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport { httpErrorToHuman } from '@/api/http';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport { ApiKey } from '@/api/account/getApiKeys';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport Input, { Textarea } from '@/components/elements/Input';\nimport styled from 'styled-components/macro';\nimport ApiKeyModal from '@/components/dashboard/ApiKeyModal';\n\ninterface Values {\n    description: string;\n    allowedIps: string;\n}\n\nconst CustomTextarea = styled(Textarea)`\n    ${tw`h-32`}\n`;\n\nexport default ({ onKeyCreated }: { onKeyCreated: (key: ApiKey) => void }) => {\n    const [apiKey, setApiKey] = useState('');\n    const { addError, clearFlashes } = useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n\n    const submit = (values: Values, { setSubmitting, resetForm }: FormikHelpers<Values>) => {\n        clearFlashes('account');\n        createApiKey(values.description, values.allowedIps)\n            .then(({ secretToken, ...key }) => {\n                resetForm();\n                setSubmitting(false);\n                setApiKey(`${key.identifier}${secretToken}`);\n                onKeyCreated(key);\n            })\n            .catch((error) => {\n                console.error(error);\n\n                addError({ key: 'account', message: httpErrorToHuman(error) });\n                setSubmitting(false);\n            });\n    };\n\n    return (\n        <>\n            <ApiKeyModal visible={apiKey.length > 0} onModalDismissed={() => setApiKey('')} apiKey={apiKey} />\n            <Formik\n                onSubmit={submit}\n                initialValues={{ description: '', allowedIps: '' }}\n                validationSchema={object().shape({\n                    allowedIps: string(),\n                    description: string().required().min(4),\n                })}\n            >\n                {({ isSubmitting }) => (\n                    <Form>\n                        <SpinnerOverlay visible={isSubmitting} />\n                        <FormikFieldWrapper\n                            label={'描述'}\n                            name={'description'}\n                            description={'此 API 密钥的描述。'}\n                            css={tw`mb-6`}\n                        >\n                            <Field name={'description'} as={Input} />\n                        </FormikFieldWrapper>\n                        <FormikFieldWrapper\n                            label={'IP 白名单'}\n                            name={'allowedIps'}\n                            description={'留空以允许任何 IP 地址使用此 API 密钥，否则在每一行中提供每个 IP 地址。'}\n                        >\n                            <Field name={'allowedIps'} as={CustomTextarea} />\n                        </FormikFieldWrapper>\n                        <div css={tw`flex justify-end mt-6`}>\n                            <Button>创建</Button>\n                        </div>\n                    </Form>\n                )}\n            </Formik>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/forms/DisableTOTPDialog.tsx",
    "content": "import React, { useContext, useEffect, useState } from 'react';\nimport asDialog from '@/hoc/asDialog';\nimport { Dialog, DialogWrapperContext } from '@/components/elements/dialog';\nimport { Button } from '@/components/elements/button/index';\nimport { Input } from '@/components/elements/inputs';\nimport Tooltip from '@/components/elements/tooltip/Tooltip';\nimport disableAccountTwoFactor from '@/api/account/disableAccountTwoFactor';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport { useStoreActions } from '@/state/hooks';\nimport FlashMessageRender from '@/components/FlashMessageRender';\n\nconst DisableTOTPDialog = () => {\n    const [submitting, setSubmitting] = useState(false);\n    const [password, setPassword] = useState('');\n    const { clearAndAddHttpError } = useFlashKey('account:two-step');\n    const { close, setProps } = useContext(DialogWrapperContext);\n    const updateUserData = useStoreActions((actions) => actions.user.updateUserData);\n\n    useEffect(() => {\n        setProps((state) => ({ ...state, preventExternalClose: submitting }));\n    }, [submitting]);\n\n    const submit = (e: React.FormEvent<HTMLFormElement>) => {\n        e.preventDefault();\n        e.stopPropagation();\n\n        if (submitting) return;\n\n        setSubmitting(true);\n        clearAndAddHttpError();\n        disableAccountTwoFactor(password)\n            .then(() => {\n                updateUserData({ useTotp: false });\n                close();\n            })\n            .catch(clearAndAddHttpError)\n            .then(() => setSubmitting(false));\n    };\n\n    return (\n        <form id={'disable-totp-form'} className={'mt-6'} onSubmit={submit}>\n            <FlashMessageRender byKey={'account:two-step'} className={'-mt-2 mb-6'} />\n            <label className={'block pb-1'} htmlFor={'totp-password'}>\n                密码\n            </label>\n            <Input.Text\n                id={'totp-password'}\n                type={'password'}\n                variant={Input.Text.Variants.Loose}\n                value={password}\n                onChange={(e: React.ChangeEvent<HTMLInputElement>) => setPassword(e.currentTarget.value)}\n            />\n            <Dialog.Footer>\n                <Button.Text onClick={close}>取消</Button.Text>\n                <Tooltip delay={100} disabled={password.length > 0} content={'您必须输入您的帐户密码才能继续。'}>\n                    <Button.Danger type={'submit'} form={'disable-totp-form'} disabled={submitting || !password.length}>\n                        禁用\n                    </Button.Danger>\n                </Tooltip>\n            </Dialog.Footer>\n        </form>\n    );\n};\n\nexport default asDialog({\n    title: '禁用动态口令认证',\n    description: '禁用动态口令认证将会使您的帐户安全性降低。',\n})(DisableTOTPDialog);\n"
  },
  {
    "path": "resources/scripts/components/dashboard/forms/RecoveryTokensDialog.tsx",
    "content": "import React from 'react';\nimport { Dialog, DialogProps } from '@/components/elements/dialog';\nimport { Button } from '@/components/elements/button/index';\nimport CopyOnClick from '@/components/elements/CopyOnClick';\nimport { Alert } from '@/components/elements/alert';\n\ninterface RecoveryTokenDialogProps extends DialogProps {\n    tokens: string[];\n}\n\nexport default ({ tokens, open, onClose }: RecoveryTokenDialogProps) => {\n    const grouped = [] as [string, string][];\n    tokens.forEach((token, index) => {\n        if (index % 2 === 0) {\n            grouped.push([token, tokens[index + 1] || '']);\n        }\n    });\n\n    return (\n        <Dialog\n            open={open}\n            onClose={onClose}\n            title={'启用动态口令认证'}\n            description={'将下面的代码存储在安全的地方。如果您无法使用手机，则可以使用这些备用代码登录。'}\n            hideCloseIcon\n            preventExternalClose\n        >\n            <Dialog.Icon position={'container'} type={'success'} />\n            <CopyOnClick text={tokens.join('\\n')} showInNotification={false}>\n                <pre className={'bg-gray-800 rounded p-2 mt-6'}>\n                    {grouped.map((value) => (\n                        <span key={value.join('_')} className={'block'}>\n                            {value[0]}\n                            <span className={'mx-2 selection:bg-gray-800'}>&nbsp;</span>\n                            {value[1]}\n                            <span className={'selection:bg-gray-800'}>&nbsp;</span>\n                        </span>\n                    ))}\n                </pre>\n            </CopyOnClick>\n            <Alert type={'danger'} className={'mt-3'}>\n                这些代码将不再会显示。\n            </Alert>\n            <Dialog.Footer>\n                <Button.Text onClick={onClose}>我知道了</Button.Text>\n            </Dialog.Footer>\n        </Dialog>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/forms/SetupTOTPDialog.tsx",
    "content": "import React, { useContext, useEffect, useState } from 'react';\nimport { Dialog, DialogWrapperContext } from '@/components/elements/dialog';\nimport getTwoFactorTokenData, { TwoFactorTokenData } from '@/api/account/getTwoFactorTokenData';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport tw from 'twin.macro';\nimport QRCode from 'qrcode.react';\nimport { Button } from '@/components/elements/button/index';\nimport Spinner from '@/components/elements/Spinner';\nimport { Input } from '@/components/elements/inputs';\nimport CopyOnClick from '@/components/elements/CopyOnClick';\nimport Tooltip from '@/components/elements/tooltip/Tooltip';\nimport enableAccountTwoFactor from '@/api/account/enableAccountTwoFactor';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport { Actions, useStoreActions } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport asDialog from '@/hoc/asDialog';\n\ninterface Props {\n    onTokens: (tokens: string[]) => void;\n}\n\nconst ConfigureTwoFactorForm = ({ onTokens }: Props) => {\n    const [submitting, setSubmitting] = useState(false);\n    const [value, setValue] = useState('');\n    const [password, setPassword] = useState('');\n    const [token, setToken] = useState<TwoFactorTokenData | null>(null);\n    const { clearAndAddHttpError } = useFlashKey('account:two-step');\n    const updateUserData = useStoreActions((actions: Actions<ApplicationStore>) => actions.user.updateUserData);\n\n    const { close, setProps } = useContext(DialogWrapperContext);\n\n    useEffect(() => {\n        getTwoFactorTokenData()\n            .then(setToken)\n            .catch((error) => clearAndAddHttpError(error));\n    }, []);\n\n    useEffect(() => {\n        setProps((state) => ({ ...state, preventExternalClose: submitting }));\n    }, [submitting]);\n\n    const submit = (e: React.FormEvent<HTMLFormElement>) => {\n        e.preventDefault();\n        e.stopPropagation();\n\n        if (submitting) return;\n\n        setSubmitting(true);\n        clearAndAddHttpError();\n        enableAccountTwoFactor(value, password)\n            .then((tokens) => {\n                updateUserData({ useTotp: true });\n                onTokens(tokens);\n            })\n            .catch((error) => {\n                clearAndAddHttpError(error);\n                setSubmitting(false);\n            });\n    };\n\n    return (\n        <form id={'enable-totp-form'} onSubmit={submit}>\n            <FlashMessageRender byKey={'account:two-step'} className={'mt-4'} />\n            <div className={'flex items-center justify-center w-56 h-56 p-2 bg-gray-50 shadow mx-auto mt-6'}>\n                {!token ? (\n                    <Spinner />\n                ) : (\n                    <QRCode renderAs={'svg'} value={token.image_url_data} css={tw`w-full h-full shadow-none`} />\n                )}\n            </div>\n            <CopyOnClick text={token?.secret}>\n                <p className={'font-mono text-sm text-gray-100 text-center mt-2'}>\n                    {token?.secret.match(/.{1,4}/g)!.join(' ') || '正在加载...'}\n                </p>\n            </CopyOnClick>\n            <p id={'totp-code-description'} className={'mt-6'}>\n                使用您选择的动态口令认证应用程序扫描上面的二维码。然后将生成的 6 位验证码输入到下面的文本框中。\n            </p>\n            <Input.Text\n                aria-labelledby={'totp-code-description'}\n                variant={Input.Text.Variants.Loose}\n                value={value}\n                onChange={(e: React.ChangeEvent<HTMLInputElement>) => setValue(e.currentTarget.value)}\n                className={'mt-3'}\n                placeholder={'000000'}\n                type={'text'}\n                inputMode={'numeric'}\n                autoComplete={'one-time-code'}\n                pattern={'\\\\d{6}'}\n            />\n            <label htmlFor={'totp-password'} className={'block mt-3'}>\n                账户密码\n            </label>\n            <Input.Text\n                variant={Input.Text.Variants.Loose}\n                className={'mt-1'}\n                type={'password'}\n                value={password}\n                onChange={(e: React.ChangeEvent<HTMLInputElement>) => setPassword(e.currentTarget.value)}\n            />\n            <Dialog.Footer>\n                <Button.Text onClick={close}>取消</Button.Text>\n                <Tooltip\n                    disabled={password.length > 0 && value.length === 6}\n                    content={!token ? '正在等待二维码加载...' : '您必须输入 6 位验证码和密码才能继续。'}\n                    delay={100}\n                >\n                    <Button\n                        disabled={!token || value.length !== 6 || !password.length}\n                        type={'submit'}\n                        form={'enable-totp-form'}\n                    >\n                        启用\n                    </Button>\n                </Tooltip>\n            </Dialog.Footer>\n        </form>\n    );\n};\n\nexport default asDialog({\n    title: '启用动态口令认证',\n    description: '帮助保护您的账户免遭未经授权的访问。每次登录时都会提示您输入验证码。',\n})(ConfigureTwoFactorForm);\n"
  },
  {
    "path": "resources/scripts/components/dashboard/forms/UpdateEmailAddressForm.tsx",
    "content": "import React from 'react';\nimport { Actions, State, useStoreActions, useStoreState } from 'easy-peasy';\nimport { Form, Formik, FormikHelpers } from 'formik';\nimport * as Yup from 'yup';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport Field from '@/components/elements/Field';\nimport { httpErrorToHuman } from '@/api/http';\nimport { ApplicationStore } from '@/state';\nimport tw from 'twin.macro';\nimport { Button } from '@/components/elements/button/index';\n\ninterface Values {\n    email: string;\n    password: string;\n}\n\nconst schema = Yup.object().shape({\n    email: Yup.string().email().required(),\n    password: Yup.string().required('您必须提供您当前的帐户密码。'),\n});\n\nexport default () => {\n    const user = useStoreState((state: State<ApplicationStore>) => state.user.data);\n    const updateEmail = useStoreActions((state: Actions<ApplicationStore>) => state.user.updateUserEmail);\n\n    const { clearFlashes, addFlash } = useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n\n    const submit = (values: Values, { resetForm, setSubmitting }: FormikHelpers<Values>) => {\n        clearFlashes('account:email');\n\n        updateEmail({ ...values })\n            .then(() =>\n                addFlash({\n                    type: 'success',\n                    key: 'account:email',\n                    message: '您的首选电子邮箱地址已更新。',\n                })\n            )\n            .catch((error) =>\n                addFlash({\n                    type: 'error',\n                    key: 'account:email',\n                    title: '错误',\n                    message: httpErrorToHuman(error),\n                })\n            )\n            .then(() => {\n                resetForm();\n                setSubmitting(false);\n            });\n    };\n\n    return (\n        <Formik onSubmit={submit} validationSchema={schema} initialValues={{ email: user!.email, password: '' }}>\n            {({ isSubmitting, isValid }) => (\n                <React.Fragment>\n                    <SpinnerOverlay size={'large'} visible={isSubmitting} />\n                    <Form css={tw`m-0`}>\n                        <Field id={'current_email'} type={'email'} name={'email'} label={'邮箱'} />\n                        <div css={tw`mt-6`}>\n                            <Field id={'confirm_password'} type={'password'} name={'password'} label={'确认密码'} />\n                        </div>\n                        <div css={tw`mt-6`}>\n                            <Button disabled={isSubmitting || !isValid}>更新邮箱地址</Button>\n                        </div>\n                    </Form>\n                </React.Fragment>\n            )}\n        </Formik>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/forms/UpdatePasswordForm.tsx",
    "content": "import React from 'react';\nimport { Actions, State, useStoreActions, useStoreState } from 'easy-peasy';\nimport { Form, Formik, FormikHelpers } from 'formik';\nimport Field from '@/components/elements/Field';\nimport * as Yup from 'yup';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport updateAccountPassword from '@/api/account/updateAccountPassword';\nimport { httpErrorToHuman } from '@/api/http';\nimport { ApplicationStore } from '@/state';\nimport tw from 'twin.macro';\nimport { Button } from '@/components/elements/button/index';\n\ninterface Values {\n    current: string;\n    password: string;\n    confirmPassword: string;\n}\n\nconst schema = Yup.object().shape({\n    current: Yup.string().min(1).required('您必须提供当前密码。'),\n    password: Yup.string().min(8).required(),\n    confirmPassword: Yup.string().test('password', '密码确认与您输入的密码不匹配。', function (value) {\n        return value === this.parent.password;\n    }),\n});\n\nexport default () => {\n    const user = useStoreState((state: State<ApplicationStore>) => state.user.data);\n    const { clearFlashes, addFlash } = useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n\n    if (!user) {\n        return null;\n    }\n\n    const submit = (values: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        clearFlashes('account:password');\n        updateAccountPassword({ ...values })\n            .then(() => {\n                // @ts-expect-error this is valid\n                window.location = '/auth/login';\n            })\n            .catch((error) =>\n                addFlash({\n                    key: 'account:password',\n                    type: 'error',\n                    title: '错误',\n                    message: httpErrorToHuman(error),\n                })\n            )\n            .then(() => setSubmitting(false));\n    };\n\n    return (\n        <React.Fragment>\n            <Formik\n                onSubmit={submit}\n                validationSchema={schema}\n                initialValues={{ current: '', password: '', confirmPassword: '' }}\n            >\n                {({ isSubmitting, isValid }) => (\n                    <React.Fragment>\n                        <SpinnerOverlay size={'large'} visible={isSubmitting} />\n                        <Form css={tw`m-0`}>\n                            <Field id={'current_password'} type={'password'} name={'current'} label={'当前密码'} />\n                            <div css={tw`mt-6`}>\n                                <Field\n                                    id={'new_password'}\n                                    type={'password'}\n                                    name={'password'}\n                                    label={'新密码'}\n                                    description={'您的新密码长度应至少为 8 个字符。'}\n                                />\n                            </div>\n                            <div css={tw`mt-6`}>\n                                <Field\n                                    id={'confirm_new_password'}\n                                    type={'password'}\n                                    name={'confirmPassword'}\n                                    label={'确认新密码'}\n                                />\n                            </div>\n                            <div css={tw`mt-6`}>\n                                <Button disabled={isSubmitting || !isValid}>更新密码</Button>\n                            </div>\n                        </Form>\n                    </React.Fragment>\n                )}\n            </Formik>\n        </React.Fragment>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/search/SearchContainer.tsx",
    "content": "import React, { useState } from 'react';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faSearch } from '@fortawesome/free-solid-svg-icons';\nimport useEventListener from '@/plugins/useEventListener';\nimport SearchModal from '@/components/dashboard/search/SearchModal';\nimport Tooltip from '@/components/elements/tooltip/Tooltip';\n\nexport default () => {\n    const [visible, setVisible] = useState(false);\n\n    useEventListener('keydown', (e: KeyboardEvent) => {\n        if (['input', 'textarea'].indexOf(((e.target as HTMLElement).tagName || 'input').toLowerCase()) < 0) {\n            if (!visible && e.metaKey && e.key.toLowerCase() === '/') {\n                setVisible(true);\n            }\n        }\n    });\n\n    return (\n        <>\n            {visible && <SearchModal appear visible={visible} onDismissed={() => setVisible(false)} />}\n            <Tooltip placement={'bottom'} content={'搜索'}>\n                <div className={'navigation-link'} onClick={() => setVisible(true)}>\n                    <FontAwesomeIcon icon={faSearch} />\n                </div>\n            </Tooltip>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/search/SearchModal.tsx",
    "content": "import React, { useEffect, useRef, useState } from 'react';\nimport Modal, { RequiredModalProps } from '@/components/elements/Modal';\nimport { Field, Form, Formik, FormikHelpers, useFormikContext } from 'formik';\nimport { Actions, useStoreActions, useStoreState } from 'easy-peasy';\nimport { object, string } from 'yup';\nimport debounce from 'debounce';\nimport FormikFieldWrapper from '@/components/elements/FormikFieldWrapper';\nimport InputSpinner from '@/components/elements/InputSpinner';\nimport getServers from '@/api/getServers';\nimport { Server } from '@/api/server/getServer';\nimport { ApplicationStore } from '@/state';\nimport { Link } from 'react-router-dom';\nimport styled from 'styled-components/macro';\nimport tw from 'twin.macro';\nimport Input from '@/components/elements/Input';\nimport { ip } from '@/lib/formatters';\n\ntype Props = RequiredModalProps;\n\ninterface Values {\n    term: string;\n}\n\nconst ServerResult = styled(Link)`\n    ${tw`flex items-center bg-neutral-900 p-4 rounded border-l-4 border-neutral-900 no-underline transition-all duration-150`};\n\n    &:hover {\n        ${tw`shadow border-cyan-500`};\n    }\n\n    &:not(:last-of-type) {\n        ${tw`mb-2`};\n    }\n`;\n\nconst SearchWatcher = () => {\n    const { values, submitForm } = useFormikContext<Values>();\n\n    useEffect(() => {\n        if (values.term.length >= 3) {\n            submitForm();\n        }\n    }, [values.term]);\n\n    return null;\n};\n\nexport default ({ ...props }: Props) => {\n    const ref = useRef<HTMLInputElement>(null);\n    const isAdmin = useStoreState((state) => state.user.data!.rootAdmin);\n    const [servers, setServers] = useState<Server[]>([]);\n    const { clearAndAddHttpError, clearFlashes } = useStoreActions(\n        (actions: Actions<ApplicationStore>) => actions.flashes\n    );\n\n    const search = debounce(({ term }: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        clearFlashes('search');\n\n        // if (ref.current) ref.current.focus();\n        getServers({ query: term, type: isAdmin ? 'admin-all' : undefined })\n            .then((servers) => setServers(servers.items.filter((_, index) => index < 5)))\n            .catch((error) => {\n                console.error(error);\n                clearAndAddHttpError({ key: 'search', error });\n            })\n            .then(() => setSubmitting(false))\n            .then(() => ref.current?.focus());\n    }, 500);\n\n    useEffect(() => {\n        if (props.visible) {\n            if (ref.current) ref.current.focus();\n        }\n    }, [props.visible]);\n\n    // Formik does not support an innerRef on custom components.\n    const InputWithRef = (props: any) => <Input autoFocus {...props} ref={ref} />;\n\n    return (\n        <Formik\n            onSubmit={search}\n            validationSchema={object().shape({\n                term: string().min(3, '请输入至少三个字符以开始搜索。'),\n            })}\n            initialValues={{ term: '' } as Values}\n        >\n            {({ isSubmitting }) => (\n                <Modal {...props}>\n                    <Form>\n                        <FormikFieldWrapper\n                            name={'term'}\n                            label={'搜索词'}\n                            description={'输入服务器名称、UUID 或分配以开始搜索。'}\n                        >\n                            <SearchWatcher />\n                            <InputSpinner visible={isSubmitting}>\n                                <Field as={InputWithRef} name={'term'} />\n                            </InputSpinner>\n                        </FormikFieldWrapper>\n                    </Form>\n                    {servers.length > 0 && (\n                        <div css={tw`mt-6`}>\n                            {servers.map((server) => (\n                                <ServerResult\n                                    key={server.uuid}\n                                    to={`/server/${server.id}`}\n                                    onClick={() => props.onDismissed()}\n                                >\n                                    <div css={tw`flex-1 mr-4`}>\n                                        <p css={tw`text-sm`}>{server.name}</p>\n                                        <p css={tw`mt-1 text-xs text-neutral-400`}>\n                                            {server.allocations\n                                                .filter((alloc) => alloc.isDefault)\n                                                .map((allocation) => (\n                                                    <span key={allocation.ip + allocation.port.toString()}>\n                                                        {allocation.alias || ip(allocation.ip)}:{allocation.port}\n                                                    </span>\n                                                ))}\n                                        </p>\n                                    </div>\n                                    <div css={tw`flex-none text-right`}>\n                                        <span css={tw`text-xs py-1 px-2 bg-cyan-800 text-cyan-100 rounded`}>\n                                            {server.node}\n                                        </span>\n                                    </div>\n                                </ServerResult>\n                            ))}\n                        </div>\n                    )}\n                </Modal>\n            )}\n        </Formik>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/ssh/AccountSSHContainer.tsx",
    "content": "import React, { useEffect } from 'react';\nimport ContentBox from '@/components/elements/ContentBox';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport PageContentBlock from '@/components/elements/PageContentBlock';\nimport tw from 'twin.macro';\nimport GreyRowBox from '@/components/elements/GreyRowBox';\nimport { useSSHKeys } from '@/api/account/ssh-keys';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faKey } from '@fortawesome/free-solid-svg-icons';\nimport { format } from 'date-fns';\nimport CreateSSHKeyForm from '@/components/dashboard/ssh/CreateSSHKeyForm';\nimport DeleteSSHKeyButton from '@/components/dashboard/ssh/DeleteSSHKeyButton';\n\nexport default () => {\n    const { clearAndAddHttpError } = useFlashKey('account');\n    const { data, isValidating, error } = useSSHKeys({\n        revalidateOnMount: true,\n        revalidateOnFocus: false,\n    });\n\n    useEffect(() => {\n        clearAndAddHttpError(error);\n    }, [error]);\n\n    return (\n        <PageContentBlock title={'SSH 密钥'}>\n            <FlashMessageRender byKey={'account'} />\n            <div css={tw`md:flex flex-nowrap my-10`}>\n                <ContentBox title={'添加 SSH 密钥'} css={tw`flex-none w-full md:w-1/2`}>\n                    <CreateSSHKeyForm />\n                </ContentBox>\n                <ContentBox title={'SSH 密钥'} css={tw`flex-1 overflow-hidden mt-8 md:mt-0 md:ml-8`}>\n                    <SpinnerOverlay visible={!data && isValidating} />\n                    {!data || !data.length ? (\n                        <p css={tw`text-center text-sm`}>{!data ? '加载中...' : '此账户下无可用 SSH 密钥.'}</p>\n                    ) : (\n                        data.map((key, index) => (\n                            <GreyRowBox\n                                key={key.fingerprint}\n                                css={[tw`bg-neutral-600 flex space-x-4 items-center`, index > 0 && tw`mt-2`]}\n                            >\n                                <FontAwesomeIcon icon={faKey} css={tw`text-neutral-300`} />\n                                <div css={tw`flex-1`}>\n                                    <p css={tw`text-sm break-words font-medium`}>{key.name}</p>\n                                    <p css={tw`text-xs mt-1 font-mono truncate`}>SHA256:{key.fingerprint}</p>\n                                    <p css={tw`text-xs mt-1 text-neutral-300 uppercase`}>\n                                        添加于:&nbsp;\n                                        {format(key.createdAt, 'yyyy年M月d日 HH:mm')}\n                                    </p>\n                                </div>\n                                <DeleteSSHKeyButton name={key.name} fingerprint={key.fingerprint} />\n                            </GreyRowBox>\n                        ))\n                    )}\n                </ContentBox>\n            </div>\n        </PageContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/ssh/CreateSSHKeyForm.tsx",
    "content": "import React from 'react';\nimport { Field, Form, Formik, FormikHelpers } from 'formik';\nimport { object, string } from 'yup';\nimport FormikFieldWrapper from '@/components/elements/FormikFieldWrapper';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport Input, { Textarea } from '@/components/elements/Input';\nimport styled from 'styled-components/macro';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport { createSSHKey, useSSHKeys } from '@/api/account/ssh-keys';\n\ninterface Values {\n    name: string;\n    publicKey: string;\n}\n\nconst CustomTextarea = styled(Textarea)`\n    ${tw`h-32`}\n`;\n\nexport default () => {\n    const { clearAndAddHttpError } = useFlashKey('account');\n    const { mutate } = useSSHKeys();\n\n    const submit = (values: Values, { setSubmitting, resetForm }: FormikHelpers<Values>) => {\n        clearAndAddHttpError();\n\n        createSSHKey(values.name, values.publicKey)\n            .then((key) => {\n                resetForm();\n                mutate((data) => (data || []).concat(key));\n            })\n            .catch((error) => clearAndAddHttpError(error))\n            .then(() => setSubmitting(false));\n    };\n\n    return (\n        <>\n            <Formik\n                onSubmit={submit}\n                initialValues={{ name: '', publicKey: '' }}\n                validationSchema={object().shape({\n                    name: string().required(),\n                    publicKey: string().required(),\n                })}\n            >\n                {({ isSubmitting }) => (\n                    <Form>\n                        <SpinnerOverlay visible={isSubmitting} />\n                        <FormikFieldWrapper label={'SSH 密钥名'} name={'name'} css={tw`mb-6`}>\n                            <Field name={'name'} as={Input} />\n                        </FormikFieldWrapper>\n                        <FormikFieldWrapper label={'公钥'} name={'publicKey'} description={'输入你的公钥.'}>\n                            <Field name={'publicKey'} as={CustomTextarea} />\n                        </FormikFieldWrapper>\n                        <div css={tw`flex justify-end mt-6`}>\n                            <Button>保存</Button>\n                        </div>\n                    </Form>\n                )}\n            </Formik>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/dashboard/ssh/DeleteSSHKeyButton.tsx",
    "content": "import tw from 'twin.macro';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faTrashAlt } from '@fortawesome/free-solid-svg-icons';\nimport React, { useState } from 'react';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport { deleteSSHKey, useSSHKeys } from '@/api/account/ssh-keys';\nimport { Dialog } from '@/components/elements/dialog';\nimport Code from '@/components/elements/Code';\n\nexport default ({ name, fingerprint }: { name: string; fingerprint: string }) => {\n    const { clearAndAddHttpError } = useFlashKey('account');\n    const [visible, setVisible] = useState(false);\n    const { mutate } = useSSHKeys();\n\n    const onClick = () => {\n        clearAndAddHttpError();\n\n        Promise.all([\n            mutate((data) => data?.filter((value) => value.fingerprint !== fingerprint), false),\n            deleteSSHKey(fingerprint),\n        ]).catch((error) => {\n            mutate(undefined, true).catch(console.error);\n            clearAndAddHttpError(error);\n        });\n    };\n\n    return (\n        <>\n            <Dialog.Confirm\n                open={visible}\n                title={'SSH 密钥删除确定'}\n                confirm={'确定删除'}\n                onConfirmed={onClick}\n                onClose={() => setVisible(false)}\n            >\n                删除 <Code>{name}</Code> SSH 密钥将使其在整个面板中的使用无效。\n            </Dialog.Confirm>\n            <button css={tw`ml-4 p-2 text-sm`} onClick={() => setVisible(true)}>\n                <FontAwesomeIcon\n                    icon={faTrashAlt}\n                    css={tw`text-neutral-400 hover:text-red-400 transition-colors duration-150`}\n                />\n            </button>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/AuthenticatedRoute.tsx",
    "content": "import React from 'react';\nimport { Redirect, Route, RouteProps } from 'react-router';\nimport { useStoreState } from '@/state/hooks';\n\nexport default ({ children, ...props }: Omit<RouteProps, 'render'>) => {\n    const isAuthenticated = useStoreState((state) => !!state.user.data?.uuid);\n\n    return (\n        <Route\n            {...props}\n            render={({ location }) =>\n                isAuthenticated ? children : <Redirect to={{ pathname: '/auth/login', state: { from: location } }} />\n            }\n        />\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/Button.tsx",
    "content": "import React from 'react';\nimport styled, { css } from 'styled-components/macro';\nimport tw from 'twin.macro';\nimport Spinner from '@/components/elements/Spinner';\n\ninterface Props {\n    isLoading?: boolean;\n    size?: 'xsmall' | 'small' | 'large' | 'xlarge';\n    color?: 'green' | 'red' | 'primary' | 'grey';\n    isSecondary?: boolean;\n}\n\nconst ButtonStyle = styled.button<Omit<Props, 'isLoading'>>`\n    ${tw`relative inline-block rounded p-2 uppercase tracking-wide text-sm transition-all duration-150 border`};\n\n    ${(props) =>\n        ((!props.isSecondary && !props.color) || props.color === 'primary') &&\n        css<Props>`\n            ${(props) => !props.isSecondary && tw`bg-primary-500 border-primary-600 border text-primary-50`};\n\n            &:hover:not(:disabled) {\n                ${tw`bg-primary-600 border-primary-700`};\n            }\n        `};\n\n    ${(props) =>\n        props.color === 'grey' &&\n        css`\n            ${tw`border-neutral-600 bg-neutral-500 text-neutral-50`};\n\n            &:hover:not(:disabled) {\n                ${tw`bg-neutral-600 border-neutral-700`};\n            }\n        `};\n\n    ${(props) =>\n        props.color === 'green' &&\n        css<Props>`\n            ${tw`border-green-600 bg-green-500 text-green-50`};\n\n            &:hover:not(:disabled) {\n                ${tw`bg-green-600 border-green-700`};\n            }\n\n            ${(props) =>\n                props.isSecondary &&\n                css`\n                    &:active:not(:disabled) {\n                        ${tw`bg-green-600 border-green-700`};\n                    }\n                `};\n        `};\n\n    ${(props) =>\n        props.color === 'red' &&\n        css<Props>`\n            ${tw`border-red-600 bg-red-500 text-red-50`};\n\n            &:hover:not(:disabled) {\n                ${tw`bg-red-600 border-red-700`};\n            }\n\n            ${(props) =>\n                props.isSecondary &&\n                css`\n                    &:active:not(:disabled) {\n                        ${tw`bg-red-600 border-red-700`};\n                    }\n                `};\n        `};\n\n    ${(props) => props.size === 'xsmall' && tw`px-2 py-1 text-xs`};\n    ${(props) => (!props.size || props.size === 'small') && tw`px-4 py-2`};\n    ${(props) => props.size === 'large' && tw`p-4 text-sm`};\n    ${(props) => props.size === 'xlarge' && tw`p-4 w-full`};\n\n    ${(props) =>\n        props.isSecondary &&\n        css<Props>`\n            ${tw`border-neutral-600 bg-transparent text-neutral-200`};\n\n            &:hover:not(:disabled) {\n                ${tw`border-neutral-500 text-neutral-100`};\n                ${(props) => props.color === 'red' && tw`bg-red-500 border-red-600 text-red-50`};\n                ${(props) => props.color === 'primary' && tw`bg-primary-500 border-primary-600 text-primary-50`};\n                ${(props) => props.color === 'green' && tw`bg-green-500 border-green-600 text-green-50`};\n            }\n        `};\n\n    &:disabled {\n        opacity: 0.55;\n        cursor: default;\n    }\n`;\n\ntype ComponentProps = Omit<JSX.IntrinsicElements['button'], 'ref' | keyof Props> & Props;\n\nconst Button: React.FC<ComponentProps> = ({ children, isLoading, ...props }) => (\n    <ButtonStyle {...props}>\n        {isLoading && (\n            <div css={tw`flex absolute justify-center items-center w-full h-full left-0 top-0`}>\n                <Spinner size={'small'} />\n            </div>\n        )}\n        <span css={isLoading ? tw`text-transparent` : undefined}>{children}</span>\n    </ButtonStyle>\n);\n\ntype LinkProps = Omit<JSX.IntrinsicElements['a'], 'ref' | keyof Props> & Props;\n\nconst LinkButton: React.FC<LinkProps> = (props) => <ButtonStyle as={'a'} {...props} />;\n\nexport { LinkButton, ButtonStyle };\nexport default Button;\n"
  },
  {
    "path": "resources/scripts/components/elements/Can.tsx",
    "content": "import React, { memo } from 'react';\nimport { usePermissions } from '@/plugins/usePermissions';\nimport isEqual from 'react-fast-compare';\n\ninterface Props {\n    action: string | string[];\n    matchAny?: boolean;\n    renderOnError?: React.ReactNode | null;\n    children: React.ReactNode;\n}\n\nconst Can = ({ action, matchAny = false, renderOnError, children }: Props) => {\n    const can = usePermissions(action);\n\n    return (\n        <>\n            {(matchAny && can.filter((p) => p).length > 0) || (!matchAny && can.every((p) => p))\n                ? children\n                : renderOnError}\n        </>\n    );\n};\n\nexport default memo(Can, isEqual);\n"
  },
  {
    "path": "resources/scripts/components/elements/Checkbox.tsx",
    "content": "import React from 'react';\nimport { Field, FieldProps } from 'formik';\nimport Input from '@/components/elements/Input';\n\ninterface Props {\n    name: string;\n    value: string;\n    className?: string;\n}\n\ntype OmitFields = 'ref' | 'name' | 'value' | 'type' | 'checked' | 'onClick' | 'onChange';\n\ntype InputProps = Omit<JSX.IntrinsicElements['input'], OmitFields>;\n\nconst Checkbox = ({ name, value, className, ...props }: Props & InputProps) => (\n    <Field name={name}>\n        {({ field, form }: FieldProps) => {\n            if (!Array.isArray(field.value)) {\n                console.error('Attempting to mount a checkbox using a field value that is not an array.');\n\n                return null;\n            }\n\n            return (\n                <Input\n                    {...field}\n                    {...props}\n                    className={className}\n                    type={'checkbox'}\n                    checked={(field.value || []).includes(value)}\n                    onClick={() => form.setFieldTouched(field.name, true)}\n                    onChange={(e) => {\n                        const set = new Set(field.value);\n                        set.has(value) ? set.delete(value) : set.add(value);\n\n                        field.onChange(e);\n                        form.setFieldValue(field.name, Array.from(set));\n                    }}\n                />\n            );\n        }}\n    </Field>\n);\n\nexport default Checkbox;\n"
  },
  {
    "path": "resources/scripts/components/elements/Code.tsx",
    "content": "import React from 'react';\nimport classNames from 'classnames';\n\ninterface CodeProps {\n    dark?: boolean | undefined;\n    className?: string;\n    children: React.ReactChild | React.ReactFragment | React.ReactPortal;\n}\n\nexport default ({ dark, className, children }: CodeProps) => (\n    <code\n        className={classNames('font-mono text-sm px-2 py-1 inline-block rounded', className, {\n            'bg-neutral-700': !dark,\n            'bg-neutral-900 text-gray-100': dark,\n        })}\n    >\n        {children}\n    </code>\n);\n"
  },
  {
    "path": "resources/scripts/components/elements/CodemirrorEditor.tsx",
    "content": "import React, { useCallback, useEffect, useState } from 'react';\nimport CodeMirror from 'codemirror';\nimport styled from 'styled-components/macro';\nimport tw from 'twin.macro';\nimport modes from '@/modes';\n\nrequire('codemirror/lib/codemirror.css');\nrequire('codemirror/theme/ayu-mirage.css');\nrequire('codemirror/addon/edit/closebrackets');\nrequire('codemirror/addon/edit/closetag');\nrequire('codemirror/addon/edit/matchbrackets');\nrequire('codemirror/addon/edit/matchtags');\nrequire('codemirror/addon/edit/trailingspace');\nrequire('codemirror/addon/fold/foldcode');\nrequire('codemirror/addon/fold/foldgutter.css');\nrequire('codemirror/addon/fold/foldgutter');\nrequire('codemirror/addon/fold/brace-fold');\nrequire('codemirror/addon/fold/comment-fold');\nrequire('codemirror/addon/fold/indent-fold');\nrequire('codemirror/addon/fold/markdown-fold');\nrequire('codemirror/addon/fold/xml-fold');\nrequire('codemirror/addon/hint/css-hint');\nrequire('codemirror/addon/hint/html-hint');\nrequire('codemirror/addon/hint/javascript-hint');\nrequire('codemirror/addon/hint/show-hint.css');\nrequire('codemirror/addon/hint/show-hint');\nrequire('codemirror/addon/hint/sql-hint');\nrequire('codemirror/addon/hint/xml-hint');\nrequire('codemirror/addon/mode/simple');\nrequire('codemirror/addon/dialog/dialog.css');\nrequire('codemirror/addon/dialog/dialog');\nrequire('codemirror/addon/scroll/annotatescrollbar');\nrequire('codemirror/addon/scroll/scrollpastend');\nrequire('codemirror/addon/scroll/simplescrollbars.css');\nrequire('codemirror/addon/scroll/simplescrollbars');\nrequire('codemirror/addon/search/jump-to-line');\nrequire('codemirror/addon/search/match-highlighter');\nrequire('codemirror/addon/search/matchesonscrollbar.css');\nrequire('codemirror/addon/search/matchesonscrollbar');\nrequire('codemirror/addon/search/search');\nrequire('codemirror/addon/search/searchcursor');\n\nrequire('codemirror/mode/brainfuck/brainfuck');\nrequire('codemirror/mode/clike/clike');\nrequire('codemirror/mode/css/css');\nrequire('codemirror/mode/dart/dart');\nrequire('codemirror/mode/diff/diff');\nrequire('codemirror/mode/dockerfile/dockerfile');\nrequire('codemirror/mode/erlang/erlang');\nrequire('codemirror/mode/gfm/gfm');\nrequire('codemirror/mode/go/go');\nrequire('codemirror/mode/handlebars/handlebars');\nrequire('codemirror/mode/htmlembedded/htmlembedded');\nrequire('codemirror/mode/htmlmixed/htmlmixed');\nrequire('codemirror/mode/http/http');\nrequire('codemirror/mode/javascript/javascript');\nrequire('codemirror/mode/jsx/jsx');\nrequire('codemirror/mode/julia/julia');\nrequire('codemirror/mode/lua/lua');\nrequire('codemirror/mode/markdown/markdown');\nrequire('codemirror/mode/nginx/nginx');\nrequire('codemirror/mode/perl/perl');\nrequire('codemirror/mode/php/php');\nrequire('codemirror/mode/properties/properties');\nrequire('codemirror/mode/protobuf/protobuf');\nrequire('codemirror/mode/pug/pug');\nrequire('codemirror/mode/python/python');\nrequire('codemirror/mode/rpm/rpm');\nrequire('codemirror/mode/ruby/ruby');\nrequire('codemirror/mode/rust/rust');\nrequire('codemirror/mode/sass/sass');\nrequire('codemirror/mode/shell/shell');\nrequire('codemirror/mode/smarty/smarty');\nrequire('codemirror/mode/sql/sql');\nrequire('codemirror/mode/swift/swift');\nrequire('codemirror/mode/toml/toml');\nrequire('codemirror/mode/twig/twig');\nrequire('codemirror/mode/vue/vue');\nrequire('codemirror/mode/xml/xml');\nrequire('codemirror/mode/yaml/yaml');\n\nconst EditorContainer = styled.div`\n    min-height: 16rem;\n    height: calc(100vh - 20rem);\n    ${tw`relative`};\n\n    > div {\n        ${tw`rounded h-full`};\n    }\n\n    .CodeMirror {\n        font-size: 12px;\n        line-height: 1.375rem;\n    }\n\n    .CodeMirror-linenumber {\n        padding: 1px 12px 0 12px !important;\n    }\n\n    .CodeMirror-foldmarker {\n        color: #cbccc6;\n        text-shadow: none;\n        margin-left: 0.25rem;\n        margin-right: 0.25rem;\n    }\n`;\n\nexport interface Props {\n    style?: React.CSSProperties;\n    initialContent?: string;\n    mode: string;\n    filename?: string;\n    onModeChanged: (mode: string) => void;\n    fetchContent: (callback: () => Promise<string>) => void;\n    onContentSaved: () => void;\n}\n\nconst findModeByFilename = (filename: string) => {\n    for (let i = 0; i < modes.length; i++) {\n        const info = modes[i];\n\n        if (info.file && info.file.test(filename)) {\n            return info;\n        }\n    }\n\n    const dot = filename.lastIndexOf('.');\n    const ext = dot > -1 && filename.substring(dot + 1, filename.length);\n\n    if (ext) {\n        for (let i = 0; i < modes.length; i++) {\n            const info = modes[i];\n            if (info.ext) {\n                for (let j = 0; j < info.ext.length; j++) {\n                    if (info.ext[j] === ext) {\n                        return info;\n                    }\n                }\n            }\n        }\n    }\n\n    return undefined;\n};\n\nexport default ({ style, initialContent, filename, mode, fetchContent, onContentSaved, onModeChanged }: Props) => {\n    const [editor, setEditor] = useState<CodeMirror.Editor>();\n\n    const ref = useCallback((node) => {\n        if (!node) return;\n\n        const e = CodeMirror.fromTextArea(node, {\n            mode: 'text/plain',\n            theme: 'ayu-mirage',\n            indentUnit: 4,\n            smartIndent: true,\n            tabSize: 4,\n            indentWithTabs: false,\n            lineWrapping: true,\n            lineNumbers: true,\n            foldGutter: true,\n            fixedGutter: true,\n            scrollbarStyle: 'overlay',\n            coverGutterNextToScrollbar: false,\n            readOnly: false,\n            showCursorWhenSelecting: false,\n            autofocus: false,\n            spellcheck: true,\n            autocorrect: false,\n            autocapitalize: false,\n            lint: false,\n            // @ts-expect-error this property is actually used, the d.ts file for CodeMirror is incorrect.\n            autoCloseBrackets: true,\n            matchBrackets: true,\n            gutters: ['CodeMirror-linenumbers', 'CodeMirror-foldgutter'],\n        });\n\n        setEditor(e);\n    }, []);\n\n    useEffect(() => {\n        if (filename === undefined) {\n            return;\n        }\n\n        onModeChanged(findModeByFilename(filename)?.mime || 'text/plain');\n    }, [filename]);\n\n    useEffect(() => {\n        editor && editor.setOption('mode', mode);\n    }, [editor, mode]);\n\n    useEffect(() => {\n        if (editor) {\n            editor.setValue(initialContent || '');\n            // Reset the history so that \"Ctrl+Z\" doesn't delete the intial content\n            // we just set above.\n            editor.setHistory({ done: [], undone: [] });\n        }\n    }, [editor, initialContent]);\n\n    useEffect(() => {\n        if (!editor) {\n            fetchContent(() => Promise.reject(new Error('no editor session has been configured')));\n            return;\n        }\n\n        editor.addKeyMap({\n            'Ctrl-S': () => onContentSaved(),\n            'Cmd-S': () => onContentSaved(),\n        });\n\n        fetchContent(() => Promise.resolve(editor.getValue()));\n    }, [editor, fetchContent, onContentSaved]);\n\n    return (\n        <EditorContainer style={style}>\n            <textarea ref={ref} />\n        </EditorContainer>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/ConfirmationModal.tsx",
    "content": "import React, { useContext } from 'react';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport asModal from '@/hoc/asModal';\nimport ModalContext from '@/context/ModalContext';\n\ntype Props = {\n    title: string;\n    buttonText: string;\n    onConfirmed: () => void;\n    showSpinnerOverlay?: boolean;\n};\n\nconst ConfirmationModal: React.FC<Props> = ({ title, children, buttonText, onConfirmed }) => {\n    const { dismiss } = useContext(ModalContext);\n\n    return (\n        <>\n            <h2 css={tw`text-2xl mb-6`}>{title}</h2>\n            <div css={tw`text-neutral-300`}>{children}</div>\n            <div css={tw`flex flex-wrap items-center justify-end mt-8`}>\n                <Button isSecondary onClick={() => dismiss()} css={tw`w-full sm:w-auto border-transparent`}>\n                    取消\n                </Button>\n                <Button color={'red'} css={tw`w-full sm:w-auto mt-4 sm:mt-0 sm:ml-4`} onClick={() => onConfirmed()}>\n                    {buttonText}\n                </Button>\n            </div>\n        </>\n    );\n};\n\nConfirmationModal.displayName = 'ConfirmationModal';\n\nexport default asModal<Props>((props) => ({\n    showSpinnerOverlay: props.showSpinnerOverlay,\n}))(ConfirmationModal);\n"
  },
  {
    "path": "resources/scripts/components/elements/ContentBox.tsx",
    "content": "import React from 'react';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport tw from 'twin.macro';\n\ntype Props = Readonly<\n    React.DetailedHTMLProps<React.HTMLAttributes<HTMLDivElement>, HTMLDivElement> & {\n        title?: string;\n        borderColor?: string;\n        showFlashes?: string | boolean;\n        showLoadingOverlay?: boolean;\n    }\n>;\n\nconst ContentBox = ({ title, borderColor, showFlashes, showLoadingOverlay, children, ...props }: Props) => (\n    <div {...props}>\n        {title && <h2 css={tw`text-neutral-300 mb-4 px-4 text-2xl`}>{title}</h2>}\n        {showFlashes && (\n            <FlashMessageRender byKey={typeof showFlashes === 'string' ? showFlashes : undefined} css={tw`mb-4`} />\n        )}\n        <div css={[tw`bg-neutral-700 p-4 rounded shadow-lg relative`, !!borderColor && tw`border-t-4`]}>\n            <SpinnerOverlay visible={showLoadingOverlay || false} />\n            {children}\n        </div>\n    </div>\n);\n\nexport default ContentBox;\n"
  },
  {
    "path": "resources/scripts/components/elements/ContentContainer.tsx",
    "content": "import styled from 'styled-components/macro';\nimport { breakpoint } from '@/theme';\nimport tw from 'twin.macro';\n\nconst ContentContainer = styled.div`\n    max-width: 1200px;\n    ${tw`mx-4`};\n\n    ${breakpoint('xl')`\n        ${tw`mx-auto`};\n    `};\n`;\nContentContainer.displayName = 'ContentContainer';\n\nexport default ContentContainer;\n"
  },
  {
    "path": "resources/scripts/components/elements/CopyOnClick.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport Fade from '@/components/elements/Fade';\nimport Portal from '@/components/elements/Portal';\nimport copy from 'copy-to-clipboard';\nimport classNames from 'classnames';\n\ninterface CopyOnClickProps {\n    text: string | number | null | undefined;\n    showInNotification?: boolean;\n    children: React.ReactNode;\n}\n\nconst CopyOnClick = ({ text, showInNotification = true, children }: CopyOnClickProps) => {\n    const [copied, setCopied] = useState(false);\n\n    useEffect(() => {\n        if (!copied) return;\n\n        const timeout = setTimeout(() => {\n            setCopied(false);\n        }, 2500);\n\n        return () => {\n            clearTimeout(timeout);\n        };\n    }, [copied]);\n\n    if (!React.isValidElement(children)) {\n        throw new Error('传递给 <CopyOnClick/> 的必须是有效的 React 元素。');\n    }\n\n    const child = !text\n        ? React.Children.only(children)\n        : React.cloneElement(React.Children.only(children), {\n              // @ts-expect-error todo: check on this\n              className: classNames(children.props.className || '', 'cursor-pointer'),\n              onClick: (e: React.MouseEvent<HTMLElement>) => {\n                  copy(String(text));\n                  setCopied(true);\n                  if (typeof children.props.onClick === 'function') {\n                      children.props.onClick(e);\n                  }\n              },\n          });\n\n    return (\n        <>\n            {copied && (\n                <Portal>\n                    <Fade in appear timeout={250} key={copied ? 'visible' : 'invisible'}>\n                        <div className={'fixed z-50 bottom-0 right-0 m-4'}>\n                            <div className={'rounded-md py-3 px-4 text-gray-200 bg-neutral-600/95 shadow'}>\n                                <p>\n                                    {showInNotification ? `已复制 \"${String(text)}\" 到剪切板.` : '已将文本复制到剪贴板'}\n                                </p>\n                            </div>\n                        </div>\n                    </Fade>\n                </Portal>\n            )}\n            {child}\n        </>\n    );\n};\n\nexport default CopyOnClick;\n"
  },
  {
    "path": "resources/scripts/components/elements/DropdownMenu.tsx",
    "content": "import React, { createRef } from 'react';\nimport styled from 'styled-components/macro';\nimport tw from 'twin.macro';\nimport Fade from '@/components/elements/Fade';\n\ninterface Props {\n    children: React.ReactNode;\n    renderToggle: (onClick: (e: React.MouseEvent<any, MouseEvent>) => void) => React.ReactChild;\n}\n\nexport const DropdownButtonRow = styled.button<{ danger?: boolean }>`\n    ${tw`p-2 flex items-center rounded w-full text-neutral-500`};\n    transition: 150ms all ease;\n\n    &:hover {\n        ${(props) => (props.danger ? tw`text-red-700 bg-red-100` : tw`text-neutral-700 bg-neutral-100`)};\n    }\n`;\n\ninterface State {\n    posX: number;\n    visible: boolean;\n}\n\nclass DropdownMenu extends React.PureComponent<Props, State> {\n    menu = createRef<HTMLDivElement>();\n\n    state: State = {\n        posX: 0,\n        visible: false,\n    };\n\n    componentWillUnmount() {\n        this.removeListeners();\n    }\n\n    componentDidUpdate(prevProps: Readonly<Props>, prevState: Readonly<State>) {\n        const menu = this.menu.current;\n\n        if (this.state.visible && !prevState.visible && menu) {\n            document.addEventListener('click', this.windowListener);\n            document.addEventListener('contextmenu', this.contextMenuListener);\n            menu.style.left = `${Math.round(this.state.posX - menu.clientWidth)}px`;\n        }\n\n        if (!this.state.visible && prevState.visible) {\n            this.removeListeners();\n        }\n    }\n\n    removeListeners = () => {\n        document.removeEventListener('click', this.windowListener);\n        document.removeEventListener('contextmenu', this.contextMenuListener);\n    };\n\n    onClickHandler = (e: React.MouseEvent<any, MouseEvent>) => {\n        e.preventDefault();\n        this.triggerMenu(e.clientX);\n    };\n\n    contextMenuListener = () => this.setState({ visible: false });\n\n    windowListener = (e: MouseEvent) => {\n        const menu = this.menu.current;\n\n        if (e.button === 2 || !this.state.visible || !menu) {\n            return;\n        }\n\n        if (e.target === menu || menu.contains(e.target as Node)) {\n            return;\n        }\n\n        if (e.target !== menu && !menu.contains(e.target as Node)) {\n            this.setState({ visible: false });\n        }\n    };\n\n    triggerMenu = (posX: number) =>\n        this.setState((s) => ({\n            posX: !s.visible ? posX : s.posX,\n            visible: !s.visible,\n        }));\n\n    render() {\n        return (\n            <div>\n                {this.props.renderToggle(this.onClickHandler)}\n                <Fade timeout={150} in={this.state.visible} unmountOnExit>\n                    <div\n                        ref={this.menu}\n                        onClick={(e) => {\n                            e.stopPropagation();\n                            this.setState({ visible: false });\n                        }}\n                        style={{ width: '12rem' }}\n                        css={tw`absolute bg-white p-2 rounded border border-neutral-700 shadow-lg text-neutral-500 z-50`}\n                    >\n                        {this.props.children}\n                    </div>\n                </Fade>\n            </div>\n        );\n    }\n}\n\nexport default DropdownMenu;\n"
  },
  {
    "path": "resources/scripts/components/elements/ErrorBoundary.tsx",
    "content": "import React from 'react';\nimport tw from 'twin.macro';\nimport Icon from '@/components/elements/Icon';\nimport { faExclamationTriangle } from '@fortawesome/free-solid-svg-icons';\n\ninterface State {\n    hasError: boolean;\n}\n\n// eslint-disable-next-line @typescript-eslint/ban-types\nclass ErrorBoundary extends React.Component<{}, State> {\n    state: State = {\n        hasError: false,\n    };\n\n    static getDerivedStateFromError() {\n        return { hasError: true };\n    }\n\n    componentDidCatch(error: Error) {\n        console.error(error);\n    }\n\n    render() {\n        return this.state.hasError ? (\n            <div css={tw`flex items-center justify-center w-full my-4`}>\n                <div css={tw`flex items-center bg-neutral-900 rounded p-3 text-red-500`}>\n                    <Icon icon={faExclamationTriangle} css={tw`h-4 w-auto mr-2`} />\n                    <p css={tw`text-sm text-neutral-100`}>应用程序在渲染此视图时遇到错误，请尝试刷新此页面.</p>\n                </div>\n            </div>\n        ) : (\n            this.props.children\n        );\n    }\n}\n\nexport default ErrorBoundary;\n"
  },
  {
    "path": "resources/scripts/components/elements/Fade.tsx",
    "content": "import React from 'react';\nimport tw from 'twin.macro';\nimport styled from 'styled-components/macro';\nimport CSSTransition, { CSSTransitionProps } from 'react-transition-group/CSSTransition';\n\ninterface Props extends Omit<CSSTransitionProps, 'timeout' | 'classNames'> {\n    timeout: number;\n}\n\nconst Container = styled.div<{ timeout: number }>`\n    .fade-enter,\n    .fade-exit,\n    .fade-appear {\n        will-change: opacity;\n    }\n\n    .fade-enter,\n    .fade-appear {\n        ${tw`opacity-0`};\n\n        &.fade-enter-active,\n        &.fade-appear-active {\n            ${tw`opacity-100 transition-opacity ease-in`};\n            transition-duration: ${(props) => props.timeout}ms;\n        }\n    }\n\n    .fade-exit {\n        ${tw`opacity-100`};\n\n        &.fade-exit-active {\n            ${tw`opacity-0 transition-opacity ease-in`};\n            transition-duration: ${(props) => props.timeout}ms;\n        }\n    }\n`;\n\nconst Fade: React.FC<Props> = ({ timeout, children, ...props }) => (\n    <Container timeout={timeout}>\n        <CSSTransition timeout={timeout} classNames={'fade'} {...props}>\n            {children}\n        </CSSTransition>\n    </Container>\n);\nFade.displayName = 'Fade';\n\nexport default Fade;\n"
  },
  {
    "path": "resources/scripts/components/elements/Field.tsx",
    "content": "import React, { forwardRef } from 'react';\nimport { Field as FormikField, FieldProps } from 'formik';\nimport Input from '@/components/elements/Input';\nimport Label from '@/components/elements/Label';\n\ninterface OwnProps {\n    name: string;\n    light?: boolean;\n    label?: string;\n    description?: string;\n    validate?: (value: any) => undefined | string | Promise<any>;\n}\n\ntype Props = OwnProps & Omit<React.InputHTMLAttributes<HTMLInputElement>, 'name'>;\n\nconst Field = forwardRef<HTMLInputElement, Props>(\n    ({ id, name, light = false, label, description, validate, ...props }, ref) => (\n        <FormikField innerRef={ref} name={name} validate={validate}>\n            {({ field, form: { errors, touched } }: FieldProps) => (\n                <div>\n                    {label && (\n                        <Label htmlFor={id} isLight={light}>\n                            {label}\n                        </Label>\n                    )}\n                    <Input\n                        id={id}\n                        {...field}\n                        {...props}\n                        isLight={light}\n                        hasError={!!(touched[field.name] && errors[field.name])}\n                    />\n                    {touched[field.name] && errors[field.name] ? (\n                        <p className={'input-help error'}>\n                            {(errors[field.name] as string).charAt(0).toUpperCase() +\n                                (errors[field.name] as string).slice(1)}\n                        </p>\n                    ) : description ? (\n                        <p className={'input-help'}>{description}</p>\n                    ) : null}\n                </div>\n            )}\n        </FormikField>\n    )\n);\nField.displayName = 'Field';\n\nexport default Field;\n"
  },
  {
    "path": "resources/scripts/components/elements/FormikFieldWrapper.tsx",
    "content": "import React from 'react';\nimport { Field, FieldProps } from 'formik';\nimport InputError from '@/components/elements/InputError';\nimport Label from '@/components/elements/Label';\n\ninterface Props {\n    id?: string;\n    name: string;\n    children: React.ReactNode;\n    className?: string;\n    label?: string;\n    description?: string;\n    validate?: (value: any) => undefined | string | Promise<any>;\n}\n\nconst FormikFieldWrapper = ({ id, name, label, className, description, validate, children }: Props) => (\n    <Field name={name} validate={validate}>\n        {({ field, form: { errors, touched } }: FieldProps) => (\n            <div className={`${className} ${touched[field.name] && errors[field.name] ? 'has-error' : undefined}`}>\n                {label && <Label htmlFor={id}>{label}</Label>}\n                {children}\n                <InputError errors={errors} touched={touched} name={field.name}>\n                    {description || null}\n                </InputError>\n            </div>\n        )}\n    </Field>\n);\n\nexport default FormikFieldWrapper;\n"
  },
  {
    "path": "resources/scripts/components/elements/FormikSwitch.tsx",
    "content": "import React from 'react';\nimport FormikFieldWrapper from '@/components/elements/FormikFieldWrapper';\nimport { Field, FieldProps } from 'formik';\nimport Switch, { SwitchProps } from '@/components/elements/Switch';\n\nconst FormikSwitch = ({ name, label, ...props }: SwitchProps) => {\n    return (\n        <FormikFieldWrapper name={name}>\n            <Field name={name}>\n                {({ field, form }: FieldProps) => (\n                    <Switch\n                        name={name}\n                        label={label}\n                        onChange={() => {\n                            form.setFieldTouched(name);\n                            form.setFieldValue(field.name, !field.value);\n                        }}\n                        defaultChecked={field.value}\n                        {...props}\n                    />\n                )}\n            </Field>\n        </FormikFieldWrapper>\n    );\n};\n\nexport default FormikSwitch;\n"
  },
  {
    "path": "resources/scripts/components/elements/GreyRowBox.tsx",
    "content": "import styled from 'styled-components/macro';\nimport tw from 'twin.macro';\n\nexport default styled.div<{ $hoverable?: boolean }>`\n    ${tw`flex rounded no-underline text-neutral-200 items-center bg-neutral-700 p-4 border border-transparent transition-colors duration-150 overflow-hidden`};\n\n    ${(props) => props.$hoverable !== false && tw`hover:border-neutral-500`};\n\n    & .icon {\n        ${tw`rounded-full w-16 flex items-center justify-center bg-neutral-500 p-3`};\n    }\n`;\n"
  },
  {
    "path": "resources/scripts/components/elements/Icon.tsx",
    "content": "import React, { CSSProperties } from 'react';\nimport { IconDefinition } from '@fortawesome/fontawesome-svg-core';\nimport tw from 'twin.macro';\n\ninterface Props {\n    icon: IconDefinition;\n    className?: string;\n    style?: CSSProperties;\n}\n\nconst Icon = ({ icon, className, style }: Props) => {\n    const [width, height, , , paths] = icon.icon;\n\n    return (\n        <svg\n            xmlns={'http://www.w3.org/2000/svg'}\n            viewBox={`0 0 ${width} ${height}`}\n            css={tw`fill-current inline-block`}\n            className={className}\n            style={style}\n        >\n            {(Array.isArray(paths) ? paths : [paths]).map((path, index) => (\n                <path key={`svg_path_${index}`} d={path} />\n            ))}\n        </svg>\n    );\n};\n\nexport default Icon;\n"
  },
  {
    "path": "resources/scripts/components/elements/Input.tsx",
    "content": "import styled, { css } from 'styled-components/macro';\nimport tw from 'twin.macro';\n\nexport interface Props {\n    isLight?: boolean;\n    hasError?: boolean;\n}\n\nconst light = css<Props>`\n    ${tw`bg-white border-neutral-200 text-neutral-800`};\n    &:focus {\n        ${tw`border-primary-400`}\n    }\n\n    &:disabled {\n        ${tw`bg-neutral-100 border-neutral-200`};\n    }\n`;\n\nconst checkboxStyle = css<Props>`\n    ${tw`bg-neutral-500 cursor-pointer appearance-none inline-block align-middle select-none flex-shrink-0 w-4 h-4 text-primary-400 border border-neutral-300 rounded-sm`};\n    color-adjust: exact;\n    background-origin: border-box;\n    transition: all 75ms linear, box-shadow 25ms linear;\n\n    &:checked {\n        ${tw`border-transparent bg-no-repeat bg-center`};\n        background-image: url(\"data:image/svg+xml,%3csvg viewBox='0 0 16 16' fill='white' xmlns='http://www.w3.org/2000/svg'%3e%3cpath d='M5.707 7.293a1 1 0 0 0-1.414 1.414l2 2a1 1 0 0 0 1.414 0l4-4a1 1 0 0 0-1.414-1.414L7 8.586 5.707 7.293z'/%3e%3c/svg%3e\");\n        background-color: currentColor;\n        background-size: 100% 100%;\n    }\n\n    &:focus {\n        ${tw`outline-none border-primary-300`};\n        box-shadow: 0 0 0 1px rgba(9, 103, 210, 0.25);\n    }\n`;\n\nconst inputStyle = css<Props>`\n    // Reset to normal styling.\n    resize: none;\n    ${tw`appearance-none outline-none w-full min-w-0`};\n    ${tw`p-3 border-2 rounded text-sm transition-all duration-150`};\n    ${tw`bg-neutral-600 border-neutral-500 hover:border-neutral-400 text-neutral-200 shadow-none focus:ring-0`};\n\n    & + .input-help {\n        ${tw`mt-1 text-xs`};\n        ${(props) => (props.hasError ? tw`text-red-200` : tw`text-neutral-200`)};\n    }\n\n    &:required,\n    &:invalid {\n        ${tw`shadow-none`};\n    }\n\n    &:not(:disabled):not(:read-only):focus {\n        ${tw`shadow-md border-primary-300 ring-2 ring-primary-400 ring-opacity-50`};\n        ${(props) => props.hasError && tw`border-red-300 ring-red-200`};\n    }\n\n    &:disabled {\n        ${tw`opacity-75`};\n    }\n\n    ${(props) => props.isLight && light};\n    ${(props) => props.hasError && tw`text-red-100 border-red-400 hover:border-red-300`};\n`;\n\nconst Input = styled.input<Props>`\n    &:not([type='checkbox']):not([type='radio']) {\n        ${inputStyle};\n    }\n\n    &[type='checkbox'],\n    &[type='radio'] {\n        ${checkboxStyle};\n\n        &[type='radio'] {\n            ${tw`rounded-full`};\n        }\n    }\n`;\nconst Textarea = styled.textarea<Props>`\n    ${inputStyle}\n`;\n\nexport { Textarea };\nexport default Input;\n"
  },
  {
    "path": "resources/scripts/components/elements/InputError.tsx",
    "content": "import React from 'react';\nimport { FormikErrors, FormikTouched } from 'formik';\nimport tw from 'twin.macro';\nimport { capitalize } from '@/lib/strings';\n\ninterface Props {\n    errors: FormikErrors<any>;\n    touched: FormikTouched<any>;\n    name: string;\n    children?: string | number | null | undefined;\n}\n\nconst InputError = ({ errors, touched, name, children }: Props) =>\n    touched[name] && errors[name] ? (\n        <p css={tw`text-xs text-red-400 pt-2`}>\n            {typeof errors[name] === 'string'\n                ? capitalize(errors[name] as string)\n                : capitalize((errors[name] as unknown as string[])[0])}\n        </p>\n    ) : (\n        <>{children ? <p css={tw`text-xs text-neutral-400 pt-2`}>{children}</p> : null}</>\n    );\n\nexport default InputError;\n"
  },
  {
    "path": "resources/scripts/components/elements/InputSpinner.tsx",
    "content": "import React from 'react';\nimport Spinner from '@/components/elements/Spinner';\nimport Fade from '@/components/elements/Fade';\nimport tw from 'twin.macro';\nimport styled, { css } from 'styled-components/macro';\nimport Select from '@/components/elements/Select';\n\nconst Container = styled.div<{ visible?: boolean }>`\n    ${tw`relative`};\n\n    ${(props) =>\n        props.visible &&\n        css`\n            & ${Select} {\n                background-image: none;\n            }\n        `};\n`;\n\nconst InputSpinner = ({ visible, children }: { visible: boolean; children: React.ReactNode }) => (\n    <Container visible={visible}>\n        <Fade appear unmountOnExit in={visible} timeout={150}>\n            <div css={tw`absolute right-0 h-full flex items-center justify-end pr-3`}>\n                <Spinner size={'small'} />\n            </div>\n        </Fade>\n        {children}\n    </Container>\n);\n\nexport default InputSpinner;\n"
  },
  {
    "path": "resources/scripts/components/elements/Label.tsx",
    "content": "import styled from 'styled-components/macro';\nimport tw from 'twin.macro';\n\nconst Label = styled.label<{ isLight?: boolean }>`\n    ${tw`block text-xs uppercase text-neutral-200 mb-1 sm:mb-2`};\n    ${(props) => props.isLight && tw`text-neutral-700`};\n`;\n\nexport default Label;\n"
  },
  {
    "path": "resources/scripts/components/elements/Modal.tsx",
    "content": "import React, { useEffect, useMemo, useRef, useState } from 'react';\nimport Spinner from '@/components/elements/Spinner';\nimport tw from 'twin.macro';\nimport styled, { css } from 'styled-components/macro';\nimport { breakpoint } from '@/theme';\nimport Fade from '@/components/elements/Fade';\nimport { createPortal } from 'react-dom';\n\nexport interface RequiredModalProps {\n    visible: boolean;\n    onDismissed: () => void;\n    appear?: boolean;\n    top?: boolean;\n}\n\nexport interface ModalProps extends RequiredModalProps {\n    dismissable?: boolean;\n    closeOnEscape?: boolean;\n    closeOnBackground?: boolean;\n    showSpinnerOverlay?: boolean;\n}\n\nexport const ModalMask = styled.div`\n    ${tw`fixed z-50 overflow-auto flex w-full inset-0`};\n    background: rgba(0, 0, 0, 0.7);\n`;\n\nconst ModalContainer = styled.div<{ alignTop?: boolean }>`\n    max-width: 95%;\n    max-height: calc(100vh - 8rem);\n    ${breakpoint('md')`max-width: 75%`};\n    ${breakpoint('lg')`max-width: 50%`};\n\n    ${tw`relative flex flex-col w-full m-auto`};\n    ${(props) =>\n        props.alignTop &&\n        css`\n            margin-top: 20%;\n            ${breakpoint('md')`margin-top: 10%`};\n        `};\n\n    margin-bottom: auto;\n\n    & > .close-icon {\n        ${tw`absolute right-0 p-2 text-white cursor-pointer opacity-50 transition-all duration-150 ease-linear hover:opacity-100`};\n        top: -2.5rem;\n\n        &:hover {\n            ${tw`transform rotate-90`}\n        }\n\n        & > svg {\n            ${tw`w-6 h-6`};\n        }\n    }\n`;\n\nconst Modal: React.FC<ModalProps> = ({\n    visible,\n    appear,\n    dismissable,\n    showSpinnerOverlay,\n    top = true,\n    closeOnBackground = true,\n    closeOnEscape = true,\n    onDismissed,\n    children,\n}) => {\n    const [render, setRender] = useState(visible);\n\n    const isDismissable = useMemo(() => {\n        return (dismissable || true) && !(showSpinnerOverlay || false);\n    }, [dismissable, showSpinnerOverlay]);\n\n    useEffect(() => {\n        if (!isDismissable || !closeOnEscape) return;\n\n        const handler = (e: KeyboardEvent) => {\n            if (e.key === 'Escape') setRender(false);\n        };\n\n        window.addEventListener('keydown', handler);\n        return () => {\n            window.removeEventListener('keydown', handler);\n        };\n    }, [isDismissable, closeOnEscape, render]);\n\n    useEffect(() => setRender(visible), [visible]);\n\n    return (\n        <Fade in={render} timeout={150} appear={appear || true} unmountOnExit onExited={() => onDismissed()}>\n            <ModalMask\n                onClick={(e) => e.stopPropagation()}\n                onContextMenu={(e) => e.stopPropagation()}\n                onMouseDown={(e) => {\n                    if (isDismissable && closeOnBackground) {\n                        e.stopPropagation();\n                        if (e.target === e.currentTarget) {\n                            setRender(false);\n                        }\n                    }\n                }}\n            >\n                <ModalContainer alignTop={top}>\n                    {isDismissable && (\n                        <div className={'close-icon'} onClick={() => setRender(false)}>\n                            <svg\n                                xmlns={'http://www.w3.org/2000/svg'}\n                                fill={'none'}\n                                viewBox={'0 0 24 24'}\n                                stroke={'currentColor'}\n                            >\n                                <path\n                                    strokeLinecap={'round'}\n                                    strokeLinejoin={'round'}\n                                    strokeWidth={'2'}\n                                    d={'M6 18L18 6M6 6l12 12'}\n                                />\n                            </svg>\n                        </div>\n                    )}\n                    {showSpinnerOverlay && (\n                        <Fade timeout={150} appear in>\n                            <div\n                                css={tw`absolute w-full h-full rounded flex items-center justify-center`}\n                                style={{ background: 'hsla(211, 10%, 53%, 0.35)', zIndex: 9999 }}\n                            >\n                                <Spinner />\n                            </div>\n                        </Fade>\n                    )}\n                    <div\n                        css={tw`bg-neutral-800 p-3 sm:p-4 md:p-6 rounded shadow-md overflow-y-scroll transition-all duration-150`}\n                    >\n                        {children}\n                    </div>\n                </ModalContainer>\n            </ModalMask>\n        </Fade>\n    );\n};\n\nconst PortaledModal: React.FC<ModalProps> = ({ children, ...props }) => {\n    const element = useRef(document.getElementById('modal-portal'));\n\n    return createPortal(<Modal {...props}>{children}</Modal>, element.current!);\n};\n\nexport default PortaledModal;\n"
  },
  {
    "path": "resources/scripts/components/elements/PageContentBlock.tsx",
    "content": "import React, { useEffect } from 'react';\nimport ContentContainer from '@/components/elements/ContentContainer';\nimport { CSSTransition } from 'react-transition-group';\nimport tw from 'twin.macro';\nimport FlashMessageRender from '@/components/FlashMessageRender';\n\nexport interface PageContentBlockProps {\n    title?: string;\n    className?: string;\n    showFlashKey?: string;\n}\n\nconst PageContentBlock: React.FC<PageContentBlockProps> = ({ title, showFlashKey, className, children }) => {\n    useEffect(() => {\n        if (title) {\n            document.title = title;\n        }\n    }, [title]);\n\n    return (\n        <CSSTransition timeout={150} classNames={'fade'} appear in>\n            <>\n                <ContentContainer css={tw`my-4 sm:my-10`} className={className}>\n                    {showFlashKey && <FlashMessageRender byKey={showFlashKey} css={tw`mb-4`} />}\n                    {children}\n                </ContentContainer>\n                <ContentContainer css={tw`mb-4`}>\n                    <p css={tw`text-center text-neutral-500 text-xs`}>\n                        <a\n                            rel={'noopener nofollow noreferrer'}\n                            href={'https://pterodactyl.io'}\n                            target={'_blank'}\n                            css={tw`no-underline text-neutral-500 hover:text-neutral-300`}\n                        >\n                            Pterodactyl&reg;\n                        </a>\n                        &nbsp;&copy; 2015 - {new Date().getFullYear()}\n                        &nbsp;| Sinicizated by&nbsp;\n                        <a\n                            rel={'noopener nofollow noreferrer'}\n                            href={'https://pterodactyl.top'}\n                            target={'_blank'}\n                            css={tw`no-underline text-neutral-500 hover:text-neutral-300`}\n                        >\n                            翼龙中国&reg;\n                        </a>\n                    </p>\n                </ContentContainer>\n            </>\n        </CSSTransition>\n    );\n};\n\nexport default PageContentBlock;\n"
  },
  {
    "path": "resources/scripts/components/elements/Pagination.tsx",
    "content": "import React from 'react';\nimport { PaginatedResult } from '@/api/http';\nimport tw from 'twin.macro';\nimport styled from 'styled-components/macro';\nimport Button from '@/components/elements/Button';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faAngleDoubleLeft, faAngleDoubleRight } from '@fortawesome/free-solid-svg-icons';\n\ninterface RenderFuncProps<T> {\n    items: T[];\n    isLastPage: boolean;\n    isFirstPage: boolean;\n}\n\ninterface Props<T> {\n    data: PaginatedResult<T>;\n    showGoToLast?: boolean;\n    showGoToFirst?: boolean;\n    onPageSelect: (page: number) => void;\n    children: (props: RenderFuncProps<T>) => React.ReactNode;\n}\n\nconst Block = styled(Button)`\n    ${tw`p-0 w-10 h-10`}\n\n    &:not(:last-of-type) {\n        ${tw`mr-2`};\n    }\n`;\n\nfunction Pagination<T>({ data: { items, pagination }, onPageSelect, children }: Props<T>) {\n    const isFirstPage = pagination.currentPage === 1;\n    const isLastPage = pagination.currentPage >= pagination.totalPages;\n\n    const pages = [];\n\n    // Start two spaces before the current page. If that puts us before the starting page default\n    // to the first page as the starting point.\n    const start = Math.max(pagination.currentPage - 2, 1);\n    const end = Math.min(pagination.totalPages, pagination.currentPage + 5);\n\n    for (let i = start; i <= end; i++) {\n        pages.push(i);\n    }\n\n    return (\n        <>\n            {children({ items, isFirstPage, isLastPage })}\n            {pages.length > 1 && (\n                <div css={tw`mt-4 flex justify-center`}>\n                    {pages[0] > 1 && !isFirstPage && (\n                        <Block isSecondary color={'primary'} onClick={() => onPageSelect(1)}>\n                            <FontAwesomeIcon icon={faAngleDoubleLeft} />\n                        </Block>\n                    )}\n                    {pages.map((i) => (\n                        <Block\n                            isSecondary={pagination.currentPage !== i}\n                            color={'primary'}\n                            key={`block_page_${i}`}\n                            onClick={() => onPageSelect(i)}\n                        >\n                            {i}\n                        </Block>\n                    ))}\n                    {pages[4] < pagination.totalPages && !isLastPage && (\n                        <Block isSecondary color={'primary'} onClick={() => onPageSelect(pagination.totalPages)}>\n                            <FontAwesomeIcon icon={faAngleDoubleRight} />\n                        </Block>\n                    )}\n                </div>\n            )}\n        </>\n    );\n}\n\nexport default Pagination;\n"
  },
  {
    "path": "resources/scripts/components/elements/PermissionRoute.tsx",
    "content": "import React from 'react';\nimport { Route } from 'react-router-dom';\nimport { RouteProps } from 'react-router';\nimport Can from '@/components/elements/Can';\nimport { ServerError } from '@/components/elements/ScreenBlock';\n\ninterface Props extends Omit<RouteProps, 'path'> {\n    path: string;\n    permission: string | string[] | null;\n}\n\nexport default ({ permission, children, ...props }: Props) => (\n    <Route {...props}>\n        {!permission ? (\n            children\n        ) : (\n            <Can\n                matchAny\n                action={permission}\n                renderOnError={<ServerError title={'拒绝访问'} message={'您无权访问此页面。'} />}\n            >\n                {children}\n            </Can>\n        )}\n    </Route>\n);\n"
  },
  {
    "path": "resources/scripts/components/elements/Portal.tsx",
    "content": "import React, { useRef } from 'react';\nimport { createPortal } from 'react-dom';\n\nexport default ({ children }: { children: React.ReactNode }) => {\n    const element = useRef(document.getElementById('modal-portal'));\n\n    return createPortal(children, element!.current!);\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/ProgressBar.tsx",
    "content": "import React, { useEffect, useRef, useState } from 'react';\nimport styled from 'styled-components/macro';\nimport { useStoreActions, useStoreState } from 'easy-peasy';\nimport { randomInt } from '@/helpers';\nimport { CSSTransition } from 'react-transition-group';\nimport tw from 'twin.macro';\n\nconst BarFill = styled.div`\n    ${tw`h-full bg-cyan-400`};\n    transition: 250ms ease-in-out;\n    box-shadow: 0 -2px 10px 2px hsl(178, 78%, 57%);\n`;\n\ntype Timer = ReturnType<typeof setTimeout>;\n\nexport default () => {\n    const interval = useRef<Timer>(null) as React.MutableRefObject<Timer>;\n    const timeout = useRef<Timer>(null) as React.MutableRefObject<Timer>;\n    const [visible, setVisible] = useState(false);\n    const progress = useStoreState((state) => state.progress.progress);\n    const continuous = useStoreState((state) => state.progress.continuous);\n    const setProgress = useStoreActions((actions) => actions.progress.setProgress);\n\n    useEffect(() => {\n        return () => {\n            timeout.current && clearTimeout(timeout.current);\n            interval.current && clearInterval(interval.current);\n        };\n    }, []);\n\n    useEffect(() => {\n        setVisible((progress || 0) > 0);\n\n        if (progress === 100) {\n            timeout.current = setTimeout(() => setProgress(undefined), 500);\n        }\n    }, [progress]);\n\n    useEffect(() => {\n        if (!continuous) {\n            interval.current && clearInterval(interval.current);\n            return;\n        }\n\n        if (!progress || progress === 0) {\n            setProgress(randomInt(20, 30));\n        }\n    }, [continuous]);\n\n    useEffect(() => {\n        if (continuous) {\n            interval.current && clearInterval(interval.current);\n            if ((progress || 0) >= 90) {\n                setProgress(90);\n            } else {\n                interval.current = setTimeout(() => setProgress((progress || 0) + randomInt(1, 5)), 500);\n            }\n        }\n    }, [progress, continuous]);\n\n    return (\n        <div css={tw`w-full fixed`} style={{ height: '2px' }}>\n            <CSSTransition timeout={150} appear in={visible} unmountOnExit classNames={'fade'}>\n                <BarFill style={{ width: progress === undefined ? '100%' : `${progress}%` }} />\n            </CSSTransition>\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/ScreenBlock.tsx",
    "content": "import React from 'react';\nimport PageContentBlock from '@/components/elements/PageContentBlock';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faArrowLeft, faSyncAlt } from '@fortawesome/free-solid-svg-icons';\nimport styled, { keyframes } from 'styled-components/macro';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport NotFoundSvg from '@/assets/images/not_found.svg';\nimport ServerErrorSvg from '@/assets/images/server_error.svg';\n\ninterface BaseProps {\n    title: string;\n    image: string;\n    message: string;\n    onRetry?: () => void;\n    onBack?: () => void;\n}\n\ninterface PropsWithRetry extends BaseProps {\n    onRetry?: () => void;\n    onBack?: never;\n}\n\ninterface PropsWithBack extends BaseProps {\n    onBack?: () => void;\n    onRetry?: never;\n}\n\nexport type ScreenBlockProps = PropsWithBack | PropsWithRetry;\n\nconst spin = keyframes`\n    to { transform: rotate(360deg) }\n`;\n\nconst ActionButton = styled(Button)`\n    ${tw`rounded-full w-8 h-8 flex items-center justify-center p-0`};\n\n    &.hover\\\\:spin:hover {\n        animation: ${spin} 2s linear infinite;\n    }\n`;\n\nconst ScreenBlock = ({ title, image, message, onBack, onRetry }: ScreenBlockProps) => (\n    <PageContentBlock>\n        <div css={tw`flex justify-center`}>\n            <div\n                css={tw`w-full sm:w-3/4 md:w-1/2 p-12 md:p-20 bg-neutral-100 rounded-lg shadow-lg text-center relative`}\n            >\n                {(typeof onBack === 'function' || typeof onRetry === 'function') && (\n                    <div css={tw`absolute left-0 top-0 ml-4 mt-4`}>\n                        <ActionButton\n                            onClick={() => (onRetry ? onRetry() : onBack ? onBack() : null)}\n                            className={onRetry ? 'hover:spin' : undefined}\n                        >\n                            <FontAwesomeIcon icon={onRetry ? faSyncAlt : faArrowLeft} />\n                        </ActionButton>\n                    </div>\n                )}\n                <img src={image} css={tw`w-2/3 h-auto select-none mx-auto`} />\n                <h2 css={tw`mt-10 text-neutral-900 font-bold text-4xl`}>{title}</h2>\n                <p css={tw`text-sm text-neutral-700 mt-2`}>{message}</p>\n            </div>\n        </div>\n    </PageContentBlock>\n);\n\ntype ServerErrorProps = (Omit<PropsWithBack, 'image' | 'title'> | Omit<PropsWithRetry, 'image' | 'title'>) & {\n    title?: string;\n};\n\nconst ServerError = ({ title, ...props }: ServerErrorProps) => (\n    <ScreenBlock title={title || '出了些问题'} image={ServerErrorSvg} {...props} />\n);\n\nconst NotFound = ({ title, message, onBack }: Partial<Pick<ScreenBlockProps, 'title' | 'message' | 'onBack'>>) => (\n    <ScreenBlock title={title || '404'} image={NotFoundSvg} message={message || '找不到请求的资源。'} onBack={onBack} />\n);\n\nexport { ServerError, NotFound };\nexport default ScreenBlock;\n"
  },
  {
    "path": "resources/scripts/components/elements/Select.tsx",
    "content": "import styled, { css } from 'styled-components/macro';\nimport tw from 'twin.macro';\n\ninterface Props {\n    hideDropdownArrow?: boolean;\n}\n\nconst Select = styled.select<Props>`\n    ${tw`shadow-none block p-3 pr-8 rounded border w-full text-sm transition-colors duration-150 ease-linear`};\n\n    &,\n    &:hover:not(:disabled),\n    &:focus {\n        ${tw`outline-none`};\n    }\n\n    -webkit-appearance: none;\n    -moz-appearance: none;\n    background-size: 1rem;\n    background-repeat: no-repeat;\n    background-position-x: calc(100% - 0.75rem);\n    background-position-y: center;\n\n    &::-ms-expand {\n        display: none;\n    }\n\n    ${(props) =>\n        !props.hideDropdownArrow &&\n        css`\n            ${tw`bg-neutral-600 border-neutral-500 text-neutral-200`};\n            background-image: url(\"data:image/svg+xml;charset=UTF-8,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20'%3e%3cpath fill='%23C3D1DF' d='M9.293 12.95l.707.707L15.657 8l-1.414-1.414L10 10.828 5.757 6.586 4.343 8z'/%3e%3c/svg%3e \");\n\n            &:hover:not(:disabled),\n            &:focus {\n                ${tw`border-neutral-400`};\n            }\n        `};\n`;\n\nexport default Select;\n"
  },
  {
    "path": "resources/scripts/components/elements/ServerContentBlock.tsx",
    "content": "import PageContentBlock, { PageContentBlockProps } from '@/components/elements/PageContentBlock';\nimport React from 'react';\nimport { ServerContext } from '@/state/server';\n\ninterface Props extends PageContentBlockProps {\n    title: string;\n}\n\nconst ServerContentBlock: React.FC<Props> = ({ title, children, ...props }) => {\n    const name = ServerContext.useStoreState((state) => state.server.data!.name);\n\n    return (\n        <PageContentBlock title={`${name} | ${title}`} {...props}>\n            {children}\n        </PageContentBlock>\n    );\n};\n\nexport default ServerContentBlock;\n"
  },
  {
    "path": "resources/scripts/components/elements/Spinner.tsx",
    "content": "import React, { Suspense } from 'react';\nimport styled, { css, keyframes } from 'styled-components/macro';\nimport tw from 'twin.macro';\nimport ErrorBoundary from '@/components/elements/ErrorBoundary';\n\nexport type SpinnerSize = 'small' | 'base' | 'large';\n\ninterface Props {\n    size?: SpinnerSize;\n    centered?: boolean;\n    isBlue?: boolean;\n}\n\ninterface Spinner extends React.FC<Props> {\n    Size: Record<'SMALL' | 'BASE' | 'LARGE', SpinnerSize>;\n    Suspense: React.FC<Props>;\n}\n\nconst spin = keyframes`\n    to { transform: rotate(360deg); }\n`;\n\n// noinspection CssOverwrittenProperties\nconst SpinnerComponent = styled.div<Props>`\n    ${tw`w-8 h-8`};\n    border-width: 3px;\n    border-radius: 50%;\n    animation: ${spin} 1s cubic-bezier(0.55, 0.25, 0.25, 0.7) infinite;\n\n    ${(props) =>\n        props.size === 'small'\n            ? tw`w-4 h-4 border-2`\n            : props.size === 'large'\n            ? css`\n                  ${tw`w-16 h-16`};\n                  border-width: 6px;\n              `\n            : null};\n\n    border-color: ${(props) => (!props.isBlue ? 'rgba(255, 255, 255, 0.2)' : 'hsla(212, 92%, 43%, 0.2)')};\n    border-top-color: ${(props) => (!props.isBlue ? 'rgb(255, 255, 255)' : 'hsl(212, 92%, 43%)')};\n`;\n\nconst Spinner: Spinner = ({ centered, ...props }) =>\n    centered ? (\n        <div css={[tw`flex justify-center items-center`, props.size === 'large' ? tw`m-20` : tw`m-6`]}>\n            <SpinnerComponent {...props} />\n        </div>\n    ) : (\n        <SpinnerComponent {...props} />\n    );\nSpinner.displayName = 'Spinner';\n\nSpinner.Size = {\n    SMALL: 'small',\n    BASE: 'base',\n    LARGE: 'large',\n};\n\nSpinner.Suspense = ({ children, centered = true, size = Spinner.Size.LARGE, ...props }) => (\n    <Suspense fallback={<Spinner centered={centered} size={size} {...props} />}>\n        <ErrorBoundary>{children}</ErrorBoundary>\n    </Suspense>\n);\nSpinner.Suspense.displayName = 'Spinner.Suspense';\n\nexport default Spinner;\n"
  },
  {
    "path": "resources/scripts/components/elements/SpinnerOverlay.tsx",
    "content": "import React from 'react';\nimport Spinner, { SpinnerSize } from '@/components/elements/Spinner';\nimport Fade from '@/components/elements/Fade';\nimport tw from 'twin.macro';\n\ninterface Props {\n    visible: boolean;\n    fixed?: boolean;\n    size?: SpinnerSize;\n    backgroundOpacity?: number;\n}\n\nconst SpinnerOverlay: React.FC<Props> = ({ size, fixed, visible, backgroundOpacity, children }) => (\n    <Fade timeout={150} in={visible} unmountOnExit>\n        <div\n            css={[\n                tw`top-0 left-0 flex items-center justify-center w-full h-full rounded flex-col z-40`,\n                !fixed ? tw`absolute` : tw`fixed`,\n            ]}\n            style={{ background: `rgba(0, 0, 0, ${backgroundOpacity || 0.45})` }}\n        >\n            <Spinner size={size} />\n            {children && (typeof children === 'string' ? <p css={tw`mt-4 text-neutral-400`}>{children}</p> : children)}\n        </div>\n    </Fade>\n);\n\nexport default SpinnerOverlay;\n"
  },
  {
    "path": "resources/scripts/components/elements/SubNavigation.tsx",
    "content": "import styled from 'styled-components/macro';\nimport tw, { theme } from 'twin.macro';\n\nconst SubNavigation = styled.div`\n    ${tw`w-full bg-neutral-700 shadow overflow-x-auto`};\n\n    & > div {\n        ${tw`flex items-center text-sm mx-auto px-2`};\n        max-width: 1200px;\n\n        & > a,\n        & > div {\n            ${tw`inline-block py-3 px-4 text-neutral-300 no-underline whitespace-nowrap transition-all duration-150`};\n\n            &:not(:first-of-type) {\n                ${tw`ml-2`};\n            }\n\n            &:hover {\n                ${tw`text-neutral-100`};\n            }\n\n            &:active,\n            &.active {\n                ${tw`text-neutral-100`};\n                box-shadow: inset 0 -2px ${theme`colors.cyan.600`.toString()};\n            }\n        }\n    }\n`;\n\nexport default SubNavigation;\n"
  },
  {
    "path": "resources/scripts/components/elements/Switch.tsx",
    "content": "import React, { useMemo } from 'react';\nimport styled from 'styled-components/macro';\nimport { v4 } from 'uuid';\nimport tw from 'twin.macro';\nimport Label from '@/components/elements/Label';\nimport Input from '@/components/elements/Input';\n\nconst ToggleContainer = styled.div`\n    ${tw`relative select-none w-12 leading-normal`};\n\n    & > input[type='checkbox'] {\n        ${tw`hidden`};\n\n        &:checked + label {\n            ${tw`bg-primary-500 border-primary-700 shadow-none`};\n        }\n\n        &:checked + label:before {\n            right: 0.125rem;\n        }\n    }\n\n    & > label {\n        ${tw`mb-0 block overflow-hidden cursor-pointer bg-neutral-400 border border-neutral-700 rounded-full h-6 shadow-inner`};\n        transition: all 75ms linear;\n\n        &::before {\n            ${tw`absolute block bg-white border h-5 w-5 rounded-full`};\n            top: 0.125rem;\n            right: calc(50% + 0.125rem);\n            //width: 1.25rem;\n            //height: 1.25rem;\n            content: '';\n            transition: all 75ms ease-in;\n        }\n    }\n`;\n\nexport interface SwitchProps {\n    name: string;\n    label?: string;\n    description?: string;\n    checked?: boolean;\n    defaultChecked?: boolean;\n    readOnly?: boolean;\n    onChange?: (e: React.ChangeEvent<HTMLInputElement>) => void;\n    children?: React.ReactNode;\n}\n\nconst Switch = ({ name, label, description, checked, defaultChecked, readOnly, onChange, children }: SwitchProps) => {\n    const uuid = useMemo(() => v4(), []);\n\n    return (\n        <div css={tw`flex items-center`}>\n            <ToggleContainer css={tw`flex-none`}>\n                {children || (\n                    <Input\n                        id={uuid}\n                        name={name}\n                        type={'checkbox'}\n                        onChange={(e) => onChange && onChange(e)}\n                        {...(checked !== undefined ? { checked } : { defaultChecked })}\n                        disabled={readOnly}\n                    />\n                )}\n                <Label htmlFor={uuid} />\n            </ToggleContainer>\n            {(label || description) && (\n                <div css={tw`ml-4 w-full`}>\n                    {label && (\n                        <Label css={[tw`cursor-pointer`, !!description && tw`mb-0`]} htmlFor={uuid}>\n                            {label}\n                        </Label>\n                    )}\n                    {description && <p css={tw`text-neutral-400 text-sm mt-2`}>{description}</p>}\n                </div>\n            )}\n        </div>\n    );\n};\n\nexport default Switch;\n"
  },
  {
    "path": "resources/scripts/components/elements/TitledGreyBox.tsx",
    "content": "import React, { memo } from 'react';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { IconProp } from '@fortawesome/fontawesome-svg-core';\nimport tw from 'twin.macro';\nimport isEqual from 'react-fast-compare';\n\ninterface Props {\n    icon?: IconProp;\n    title: string | React.ReactNode;\n    className?: string;\n    children: React.ReactNode;\n}\n\nconst TitledGreyBox = ({ icon, title, children, className }: Props) => (\n    <div css={tw`rounded shadow-md bg-neutral-700`} className={className}>\n        <div css={tw`bg-neutral-900 rounded-t p-3 border-b border-black`}>\n            {typeof title === 'string' ? (\n                <p css={tw`text-sm uppercase`}>\n                    {icon && <FontAwesomeIcon icon={icon} css={tw`mr-2 text-neutral-300`} />}\n                    {title}\n                </p>\n            ) : (\n                title\n            )}\n        </div>\n        <div css={tw`p-3`}>{children}</div>\n    </div>\n);\n\nexport default memo(TitledGreyBox, isEqual);\n"
  },
  {
    "path": "resources/scripts/components/elements/Translate.tsx",
    "content": "import React from 'react';\nimport { Trans, TransSelectorProps, useTranslation } from 'react-i18next';\n\ntype Props = Omit<TransSelectorProps<any, any>, 't'>;\n\nexport default ({ ns, children, ...props }: Props) => {\n    const { t } = useTranslation(ns);\n\n    return (\n        <Trans t={t} {...props}>\n            {children}\n        </Trans>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/activity/ActivityLogEntry.tsx",
    "content": "import React from 'react';\nimport { Link } from 'react-router-dom';\nimport Tooltip from '@/components/elements/tooltip/Tooltip';\nimport Translate from '@/components/elements/Translate';\nimport { format, formatDistanceToNowStrict } from 'date-fns';\nimport { zhCN } from 'date-fns/locale';\nimport { ActivityLog } from '@definitions/user';\nimport ActivityLogMetaButton from '@/components/elements/activity/ActivityLogMetaButton';\nimport { FolderOpenIcon, TerminalIcon } from '@heroicons/react/solid';\nimport classNames from 'classnames';\nimport style from './style.module.css';\nimport Avatar from '@/components/Avatar';\nimport useLocationHash from '@/plugins/useLocationHash';\nimport { getObjectKeys, isObject } from '@/lib/objects';\n\ninterface Props {\n    activity: ActivityLog;\n    children?: React.ReactNode;\n}\n\nfunction wrapProperties(value: unknown): any {\n    if (value === null || typeof value === 'string' || typeof value === 'number') {\n        return `<strong>${String(value)}</strong>`;\n    }\n\n    if (isObject(value)) {\n        return getObjectKeys(value).reduce((obj, key) => {\n            if (key === 'count' || (typeof key === 'string' && key.endsWith('_count'))) {\n                return { ...obj, [key]: value[key] };\n            }\n            return { ...obj, [key]: wrapProperties(value[key]) };\n        }, {} as Record<string, unknown>);\n    }\n\n    if (Array.isArray(value)) {\n        return value.map(wrapProperties);\n    }\n\n    return value;\n}\n\nexport default ({ activity, children }: Props) => {\n    const { pathTo } = useLocationHash();\n    const actor = activity.relationships.actor;\n    const properties = wrapProperties(activity.properties);\n\n    return (\n        <div className={'grid grid-cols-10 py-4 border-b-2 border-gray-800 last:rounded-b last:border-0 group'}>\n            <div className={'hidden sm:flex sm:col-span-1 items-center justify-center select-none'}>\n                <div className={'flex items-center w-10 h-10 rounded-full bg-gray-600 overflow-hidden'}>\n                    <Avatar name={actor?.uuid || 'system'} />\n                </div>\n            </div>\n            <div className={'col-span-10 sm:col-span-9 flex'}>\n                <div className={'flex-1 px-4 sm:px-0'}>\n                    <div className={'flex items-center text-gray-50'}>\n                        <Tooltip placement={'top'} content={actor?.email || '系统用户'}>\n                            <span>{actor?.username || '系统'}</span>\n                        </Tooltip>\n                        <span className={'text-gray-400'}>&nbsp;&mdash;&nbsp;</span>\n                        <Link\n                            to={`#${pathTo({ event: activity.event })}`}\n                            className={'transition-colors duration-75 active:text-cyan-400 hover:text-cyan-400'}\n                        >\n                            {activity.event}\n                        </Link>\n                        <div className={classNames(style.icons, 'group-hover:text-gray-300')}>\n                            {activity.isApi && (\n                                <Tooltip placement={'top'} content={'使用 API 密钥'}>\n                                    <TerminalIcon />\n                                </Tooltip>\n                            )}\n                            {activity.event.startsWith('server:sftp.') && (\n                                <Tooltip placement={'top'} content={'使用 SFTP'}>\n                                    <FolderOpenIcon />\n                                </Tooltip>\n                            )}\n                            {children}\n                        </div>\n                    </div>\n                    <p className={style.description}>\n                        <Translate ns={'activity'} values={properties} i18nKey={activity.event.replace(':', '.')} />\n                    </p>\n                    <div className={'mt-1 flex items-center text-sm'}>\n                        {activity.ip && (\n                            <span>\n                                {activity.ip}\n                                <span className={'text-gray-400'}>&nbsp;|&nbsp;</span>\n                            </span>\n                        )}\n                        <Tooltip placement={'right'} content={format(activity.timestamp, 'yyyy年M月d日 HH:mm:ss')}>\n                            <span>\n                                {formatDistanceToNowStrict(activity.timestamp, { addSuffix: true, locale: zhCN })}\n                            </span>\n                        </Tooltip>\n                    </div>\n                </div>\n                {activity.hasAdditionalMetadata && <ActivityLogMetaButton meta={activity.properties} />}\n            </div>\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/activity/ActivityLogMetaButton.tsx",
    "content": "import React, { useState } from 'react';\nimport { ClipboardListIcon } from '@heroicons/react/outline';\nimport { Dialog } from '@/components/elements/dialog';\nimport { Button } from '@/components/elements/button/index';\n\nexport default ({ meta }: { meta: Record<string, unknown> }) => {\n    const [open, setOpen] = useState(false);\n\n    return (\n        <div className={'self-center md:px-4'}>\n            <Dialog open={open} onClose={() => setOpen(false)} hideCloseIcon title={'元数据'}>\n                <pre\n                    className={\n                        'bg-gray-900 rounded p-2 font-mono text-sm leading-relaxed overflow-x-scroll whitespace-pre-wrap'\n                    }\n                >\n                    {JSON.stringify(meta, null, 2)}\n                </pre>\n                <Dialog.Footer>\n                    <Button.Text onClick={() => setOpen(false)}>关闭</Button.Text>\n                </Dialog.Footer>\n            </Dialog>\n            <button\n                aria-describedby={'查看附加事件元数据'}\n                className={\n                    'p-2 transition-colors duration-100 text-gray-400 group-hover:text-gray-300 group-hover:hover:text-gray-50'\n                }\n                onClick={() => setOpen(true)}\n            >\n                <ClipboardListIcon className={'w-5 h-5'} />\n            </button>\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/activity/style.module.css",
    "content": ".icons {\n    @apply flex space-x-1 mx-2 transition-colors duration-100 text-gray-400;\n\n    & svg {\n        @apply px-1 py-px cursor-pointer hover:text-gray-50 h-5 w-auto;\n    }\n}\n\n.description {\n    @apply mt-1 text-sm break-words line-clamp-2 pr-4;\n\n    & strong {\n        @apply text-gray-50 font-semibold break-all;\n    }\n}\n"
  },
  {
    "path": "resources/scripts/components/elements/alert/Alert.tsx",
    "content": "import { ExclamationIcon, ShieldExclamationIcon } from '@heroicons/react/outline';\nimport React from 'react';\nimport classNames from 'classnames';\n\ninterface AlertProps {\n    type: 'warning' | 'danger';\n    className?: string;\n    children: React.ReactNode;\n}\n\nexport default ({ type, className, children }: AlertProps) => {\n    return (\n        <div\n            className={classNames(\n                'flex items-center border-l-8 text-gray-50 rounded-md shadow px-4 py-3',\n                {\n                    ['border-red-500 bg-red-500/25']: type === 'danger',\n                    ['border-yellow-500 bg-yellow-500/25']: type === 'warning',\n                },\n                className\n            )}\n        >\n            {type === 'danger' ? (\n                <ShieldExclamationIcon className={'w-6 h-6 text-red-400 mr-2'} />\n            ) : (\n                <ExclamationIcon className={'w-6 h-6 text-yellow-500 mr-2'} />\n            )}\n            {children}\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/alert/index.ts",
    "content": "export { default as Alert } from './Alert';\n"
  },
  {
    "path": "resources/scripts/components/elements/button/Button.tsx",
    "content": "import React, { forwardRef } from 'react';\nimport classNames from 'classnames';\nimport { ButtonProps, Options } from '@/components/elements/button/types';\nimport styles from './style.module.css';\n\nconst Button = forwardRef<HTMLButtonElement, ButtonProps>(\n    ({ children, shape, size, variant, className, ...rest }, ref) => {\n        return (\n            <button\n                ref={ref}\n                className={classNames(\n                    styles.button,\n                    styles.primary,\n                    {\n                        [styles.secondary]: variant === Options.Variant.Secondary,\n                        [styles.square]: shape === Options.Shape.IconSquare,\n                        [styles.small]: size === Options.Size.Small,\n                        [styles.large]: size === Options.Size.Large,\n                    },\n                    className\n                )}\n                {...rest}\n            >\n                {children}\n            </button>\n        );\n    }\n);\n\nconst TextButton = forwardRef<HTMLButtonElement, ButtonProps>(({ className, ...props }, ref) => (\n    // @ts-expect-error not sure how to get this correct\n    <Button ref={ref} className={classNames(styles.text, className)} {...props} />\n));\n\nconst DangerButton = forwardRef<HTMLButtonElement, ButtonProps>(({ className, ...props }, ref) => (\n    // @ts-expect-error not sure how to get this correct\n    <Button ref={ref} className={classNames(styles.danger, className)} {...props} />\n));\n\nconst _Button = Object.assign(Button, {\n    Sizes: Options.Size,\n    Shapes: Options.Shape,\n    Variants: Options.Variant,\n    Text: TextButton,\n    Danger: DangerButton,\n});\n\nexport default _Button;\n"
  },
  {
    "path": "resources/scripts/components/elements/button/index.ts",
    "content": "export { default as Button } from './Button';\nexport { default as styles } from './style.module.css';\n"
  },
  {
    "path": "resources/scripts/components/elements/button/style.module.css",
    "content": ".button {\n    @apply px-4 py-2 inline-flex items-center justify-center;\n    @apply rounded text-base font-semibold transition-all duration-100;\n    @apply focus:ring-[3px] focus:ring-offset-2 focus:ring-offset-gray-700 focus:ring-opacity-50;\n\n    /* Sizing Controls */\n    &.small {\n        @apply px-4 py-0 h-8 font-normal text-sm focus:ring-2;\n    }\n\n    &.large {\n        @apply px-5 py-3;\n    }\n\n    &.secondary {\n        @apply text-gray-50 bg-transparent;\n\n        &:disabled {\n            background: transparent !important;\n        }\n    }\n\n    &:disabled {\n        @apply cursor-not-allowed;\n    }\n\n    &.square {\n        @apply p-0 w-12 h-12;\n\n        &.small {\n            @apply w-8 h-8;\n        }\n    }\n}\n\n.primary {\n    @apply bg-blue-600 text-blue-50;\n    @apply hover:bg-blue-500 active:bg-blue-500 focus:ring-blue-400 focus:ring-opacity-75;\n\n    &.secondary {\n        @apply hover:bg-blue-600 active:bg-blue-600;\n    }\n\n    &:disabled {\n        @apply bg-blue-500/75 text-blue-200/75;\n    }\n}\n\n.text {\n    @apply bg-gray-500 text-gray-50;\n    @apply hover:bg-gray-400 active:bg-gray-400 focus:ring-gray-300 focus:ring-opacity-50;\n\n    &.secondary {\n        @apply hover:bg-gray-500 active:bg-gray-500;\n    }\n\n    &:disabled {\n        @apply bg-gray-500/75 text-gray-200/75;\n    }\n}\n\n.danger {\n    @apply bg-red-600 text-gray-50;\n    @apply hover:bg-red-500 active:bg-red-500 focus:ring-red-400 focus:ring-opacity-75;\n\n    &.secondary {\n        @apply hover:bg-red-600 active:bg-red-600;\n    }\n\n    &:disabled {\n        @apply bg-red-600/75 text-red-50/75;\n    }\n}\n"
  },
  {
    "path": "resources/scripts/components/elements/button/types.ts",
    "content": "enum Shape {\n    Default,\n    IconSquare,\n}\n\nenum Size {\n    Default,\n    Small,\n    Large,\n}\n\nenum Variant {\n    Primary,\n    Secondary,\n}\n\nexport const Options = { Shape, Size, Variant };\n\nexport type ButtonProps = JSX.IntrinsicElements['button'] & {\n    shape?: Shape;\n    size?: Size;\n    variant?: Variant;\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/dialog/ConfirmationDialog.tsx",
    "content": "import React from 'react';\nimport { Dialog, RenderDialogProps } from './';\nimport { Button } from '@/components/elements/button/index';\n\ntype ConfirmationProps = Omit<RenderDialogProps, 'description' | 'children'> & {\n    children: React.ReactNode;\n    confirm?: string | undefined;\n    onConfirmed: (e: React.MouseEvent<HTMLButtonElement, MouseEvent>) => void;\n};\n\nexport default ({ confirm = '对，是的', children, onConfirmed, ...props }: ConfirmationProps) => {\n    return (\n        <Dialog {...props} description={typeof children === 'string' ? children : undefined}>\n            {typeof children !== 'string' && children}\n            <Dialog.Footer>\n                <Button.Text onClick={props.onClose}>取消</Button.Text>\n                <Button.Danger onClick={onConfirmed}>{confirm}</Button.Danger>\n            </Dialog.Footer>\n        </Dialog>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/dialog/Dialog.tsx",
    "content": "import React, { useRef, useState } from 'react';\nimport { Dialog as HDialog } from '@headlessui/react';\nimport { Button } from '@/components/elements/button/index';\nimport { XIcon } from '@heroicons/react/solid';\nimport { AnimatePresence, motion } from 'framer-motion';\nimport { DialogContext, IconPosition, RenderDialogProps, styles } from './';\n\nconst variants = {\n    open: {\n        scale: 1,\n        opacity: 1,\n        transition: {\n            type: 'spring',\n            damping: 15,\n            stiffness: 300,\n            duration: 0.15,\n        },\n    },\n    closed: {\n        scale: 0.75,\n        opacity: 0,\n        transition: {\n            type: 'easeIn',\n            duration: 0.15,\n        },\n    },\n    bounce: {\n        scale: 0.95,\n        opacity: 1,\n        transition: { type: 'linear', duration: 0.075 },\n    },\n};\n\nexport default ({\n    open,\n    title,\n    description,\n    onClose,\n    hideCloseIcon,\n    preventExternalClose,\n    children,\n}: RenderDialogProps) => {\n    const container = useRef<HTMLDivElement>(null);\n    const [icon, setIcon] = useState<React.ReactNode>();\n    const [footer, setFooter] = useState<React.ReactNode>();\n    const [iconPosition, setIconPosition] = useState<IconPosition>('title');\n    const [down, setDown] = useState(false);\n\n    const onContainerClick = (down: boolean, e: React.MouseEvent<HTMLDivElement>): void => {\n        if (e.target instanceof HTMLElement && container.current?.isSameNode(e.target)) {\n            setDown(down);\n        }\n    };\n\n    const onDialogClose = (): void => {\n        if (!preventExternalClose) {\n            return onClose();\n        }\n    };\n\n    return (\n        <AnimatePresence>\n            {open && (\n                <DialogContext.Provider value={{ setIcon, setFooter, setIconPosition }}>\n                    <HDialog\n                        static\n                        as={motion.div}\n                        initial={{ opacity: 0 }}\n                        animate={{ opacity: 1 }}\n                        exit={{ opacity: 0 }}\n                        transition={{ duration: 0.15 }}\n                        open={open}\n                        onClose={onDialogClose}\n                    >\n                        <div className={'fixed inset-0 bg-gray-900/50 z-40'} />\n                        <div className={'fixed inset-0 overflow-y-auto z-50'}>\n                            <div\n                                ref={container}\n                                className={styles.container}\n                                onMouseDown={onContainerClick.bind(this, true)}\n                                onMouseUp={onContainerClick.bind(this, false)}\n                            >\n                                <HDialog.Panel\n                                    as={motion.div}\n                                    initial={'closed'}\n                                    animate={down ? 'bounce' : 'open'}\n                                    exit={'closed'}\n                                    variants={variants}\n                                    className={styles.panel}\n                                >\n                                    <div className={'flex p-6 pb-0 overflow-y-auto'}>\n                                        {iconPosition === 'container' && icon}\n                                        <div className={'flex-1 max-h-[70vh] min-w-0'}>\n                                            <div className={'flex items-center'}>\n                                                {iconPosition !== 'container' && icon}\n                                                <div>\n                                                    {title && (\n                                                        <HDialog.Title className={styles.title}>{title}</HDialog.Title>\n                                                    )}\n                                                    {description && (\n                                                        <HDialog.Description>{description}</HDialog.Description>\n                                                    )}\n                                                </div>\n                                            </div>\n                                            {children}\n                                            <div className={'invisible h-6'} />\n                                        </div>\n                                    </div>\n                                    {footer}\n                                    {/* Keep this below the other buttons so that it isn't the default focus if they're present. */}\n                                    {!hideCloseIcon && (\n                                        <div className={'absolute right-0 top-0 m-4'}>\n                                            <Button.Text\n                                                size={Button.Sizes.Small}\n                                                shape={Button.Shapes.IconSquare}\n                                                onClick={onClose}\n                                                className={'group'}\n                                            >\n                                                <XIcon className={styles.close_icon} />\n                                            </Button.Text>\n                                        </div>\n                                    )}\n                                </HDialog.Panel>\n                            </div>\n                        </div>\n                    </HDialog>\n                </DialogContext.Provider>\n            )}\n        </AnimatePresence>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/dialog/DialogFooter.tsx",
    "content": "import React, { useContext } from 'react';\nimport { DialogContext } from './';\nimport { useDeepCompareEffect } from '@/plugins/useDeepCompareEffect';\n\nexport default ({ children }: { children: React.ReactNode }) => {\n    const { setFooter } = useContext(DialogContext);\n\n    useDeepCompareEffect(() => {\n        setFooter(\n            <div className={'px-6 py-3 bg-gray-700 flex items-center justify-end space-x-3 rounded-b'}>{children}</div>\n        );\n    }, [children]);\n\n    return null;\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/dialog/DialogIcon.tsx",
    "content": "import React, { useContext, useEffect } from 'react';\nimport { CheckIcon, ExclamationIcon, InformationCircleIcon, ShieldExclamationIcon } from '@heroicons/react/outline';\nimport classNames from 'classnames';\nimport { DialogContext, DialogIconProps, styles } from './';\n\nconst icons = {\n    danger: ShieldExclamationIcon,\n    warning: ExclamationIcon,\n    success: CheckIcon,\n    info: InformationCircleIcon,\n};\n\nexport default ({ type, position, className }: DialogIconProps) => {\n    const { setIcon, setIconPosition } = useContext(DialogContext);\n\n    useEffect(() => {\n        const Icon = icons[type];\n\n        setIcon(\n            <div className={classNames(styles.dialog_icon, styles[type], className)}>\n                <Icon className={'w-6 h-6'} />\n            </div>\n        );\n    }, [type, className]);\n\n    useEffect(() => {\n        setIconPosition(position);\n    }, [position]);\n\n    return null;\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/dialog/context.ts",
    "content": "import React from 'react';\nimport { DialogContextType, DialogWrapperContextType } from './types';\n\nexport const DialogContext = React.createContext<DialogContextType>({\n    setIcon: () => null,\n    setFooter: () => null,\n    setIconPosition: () => null,\n});\n\nexport const DialogWrapperContext = React.createContext<DialogWrapperContextType>({\n    props: {},\n    setProps: () => null,\n    close: () => null,\n});\n"
  },
  {
    "path": "resources/scripts/components/elements/dialog/index.ts",
    "content": "import DialogComponent from './Dialog';\nimport DialogFooter from './DialogFooter';\nimport DialogIcon from './DialogIcon';\nimport ConfirmationDialog from './ConfirmationDialog';\n\nconst Dialog = Object.assign(DialogComponent, {\n    Confirm: ConfirmationDialog,\n    Footer: DialogFooter,\n    Icon: DialogIcon,\n});\n\nexport { Dialog };\nexport * from './types.d';\nexport * from './context';\nexport { default as styles } from './style.module.css';\n"
  },
  {
    "path": "resources/scripts/components/elements/dialog/style.module.css",
    "content": ".container {\n    @apply flex min-h-full items-center justify-center p-4 text-center;\n}\n\n.panel {\n    @apply relative bg-gray-600 rounded max-w-xl w-full mx-auto shadow-lg text-left;\n    @apply ring-4 ring-gray-800 ring-opacity-80;\n}\n\n.title {\n    @apply font-header text-xl font-medium mb-2 text-gray-50 pr-4;\n}\n\n.close_icon {\n    @apply w-5 h-5 group-hover:rotate-90 transition-transform duration-100;\n}\n\n.dialog_icon {\n    @apply flex items-center justify-center w-10 h-10 rounded-full mr-4;\n\n    &.danger {\n        @apply bg-red-500 text-red-50;\n    }\n\n    &.warning {\n        @apply bg-yellow-600 text-yellow-50;\n    }\n\n    &.success {\n        @apply bg-green-600 text-green-50;\n    }\n\n    &.info {\n        @apply bg-primary-500 text-primary-50;\n    }\n}\n"
  },
  {
    "path": "resources/scripts/components/elements/dialog/types.d.ts",
    "content": "import React from 'react';\nimport { IconPosition } from '@/components/elements/dialog/DialogIcon';\n\ntype Callback<T> = ((value: T) => void) | React.Dispatch<React.SetStateAction<T>>;\n\nexport interface DialogProps {\n    open: boolean;\n    onClose: () => void;\n}\n\nexport type IconPosition = 'title' | 'container' | undefined;\n\nexport interface DialogIconProps {\n    type: 'danger' | 'info' | 'success' | 'warning';\n    position?: IconPosition;\n    className?: string;\n}\n\nexport interface RenderDialogProps extends DialogProps {\n    hideCloseIcon?: boolean;\n    preventExternalClose?: boolean;\n    title?: string;\n    description?: string | undefined;\n    children?: React.ReactNode;\n}\n\nexport type WrapperProps = Omit<RenderDialogProps, 'children' | 'open' | 'onClose'>;\nexport interface DialogWrapperContextType {\n    props: Readonly<WrapperProps>;\n    setProps: React.Dispatch<React.SetStateAction<WrapperProps>>;\n    close: () => void;\n}\n\nexport interface DialogContextType {\n    setIcon: Callback<React.ReactNode>;\n    setFooter: Callback<React.ReactNode>;\n    setIconPosition: Callback<IconPosition>;\n}\n"
  },
  {
    "path": "resources/scripts/components/elements/dropdown/Dropdown.tsx",
    "content": "import React, { ElementType, forwardRef, useMemo } from 'react';\nimport { Menu, Transition } from '@headlessui/react';\nimport styles from './style.module.css';\nimport classNames from 'classnames';\nimport DropdownItem from '@/components/elements/dropdown/DropdownItem';\nimport DropdownButton from '@/components/elements/dropdown/DropdownButton';\n\ninterface Props {\n    as?: ElementType;\n    children: React.ReactNode;\n}\n\nconst DropdownGap = ({ invisible }: { invisible?: boolean }) => (\n    <div className={classNames('border m-2', { 'border-neutral-700': !invisible, 'border-transparent': invisible })} />\n);\n\ntype TypedChild = (React.ReactChild | React.ReactFragment | React.ReactPortal) & {\n    type?: JSX.Element;\n};\n\nconst Dropdown = forwardRef<typeof Menu, Props>(({ as, children }, ref) => {\n    const [Button, items] = useMemo(() => {\n        const list = React.Children.toArray(children) as unknown as TypedChild[];\n\n        return [\n            list.filter((child) => child.type === DropdownButton),\n            list.filter((child) => child.type !== DropdownButton),\n        ];\n    }, [children]);\n\n    if (!Button) {\n        throw new Error('Cannot mount <Dropdown /> component without a child <Dropdown.Button />.');\n    }\n\n    return (\n        <Menu as={as || 'div'} className={styles.menu} ref={ref}>\n            {Button}\n            <Transition\n                enter={'transition duration-100 ease-out'}\n                enterFrom={'transition scale-95 opacity-0'}\n                enterTo={'transform scale-100 opacity-100'}\n                leave={'transition duration-75 ease-out'}\n                leaveFrom={'transform scale-100 opacity-100'}\n                leaveTo={'transform scale-95 opacity-0'}\n            >\n                <Menu.Items className={classNames(styles.items_container, 'w-56')}>\n                    <div className={'px-1 py-1'}>{items}</div>\n                </Menu.Items>\n            </Transition>\n        </Menu>\n    );\n});\n\nconst _Dropdown = Object.assign(Dropdown, {\n    Button: DropdownButton,\n    Item: DropdownItem,\n    Gap: DropdownGap,\n});\n\nexport { _Dropdown as default };\n"
  },
  {
    "path": "resources/scripts/components/elements/dropdown/DropdownButton.tsx",
    "content": "import classNames from 'classnames';\nimport styles from '@/components/elements/dropdown/style.module.css';\nimport { ChevronDownIcon } from '@heroicons/react/solid';\nimport { Menu } from '@headlessui/react';\nimport React from 'react';\n\ninterface Props {\n    className?: string;\n    animate?: boolean;\n    children: React.ReactNode;\n}\n\nexport default ({ className, animate = true, children }: Props) => (\n    <Menu.Button className={classNames(styles.button, className || 'px-4')}>\n        {typeof children === 'string' ? (\n            <>\n                <span className={'mr-2'}>{children}</span>\n                <ChevronDownIcon aria-hidden={'true'} data-animated={animate.toString()} />\n            </>\n        ) : (\n            children\n        )}\n    </Menu.Button>\n);\n"
  },
  {
    "path": "resources/scripts/components/elements/dropdown/DropdownItem.tsx",
    "content": "import React, { forwardRef } from 'react';\nimport { Menu } from '@headlessui/react';\nimport styles from './style.module.css';\nimport classNames from 'classnames';\n\ninterface Props {\n    children: React.ReactNode | ((opts: { active: boolean; disabled: boolean }) => JSX.Element);\n    danger?: boolean;\n    disabled?: boolean;\n    className?: string;\n    icon?: JSX.Element;\n    onClick?: (e: React.MouseEvent) => void;\n}\n\nconst DropdownItem = forwardRef<HTMLAnchorElement, Props>(\n    ({ disabled, danger, className, onClick, children, icon: IconComponent }, ref) => {\n        return (\n            <Menu.Item disabled={disabled}>\n                {({ disabled, active }) => (\n                    <a\n                        ref={ref}\n                        href={'#'}\n                        className={classNames(\n                            styles.menu_item,\n                            {\n                                [styles.danger]: danger,\n                                [styles.disabled]: disabled,\n                            },\n                            className\n                        )}\n                        onClick={onClick}\n                    >\n                        {IconComponent}\n                        {typeof children === 'function' ? children({ disabled, active }) : children}\n                    </a>\n                )}\n            </Menu.Item>\n        );\n    }\n);\n\nexport default DropdownItem;\n"
  },
  {
    "path": "resources/scripts/components/elements/dropdown/index.ts",
    "content": "export { default as Dropdown } from './Dropdown';\nexport * as styles from './style.module.css';\n"
  },
  {
    "path": "resources/scripts/components/elements/dropdown/style.module.css",
    "content": ".menu {\n  @apply relative inline-block text-left;\n\n  & .button {\n    @apply inline-flex justify-center items-center w-full py-2 text-neutral-100 rounded-md;\n    @apply transition-all duration-100;\n\n    &:hover, &[aria-expanded=\"true\"] {\n      @apply bg-neutral-600 text-white;\n    }\n\n    &:focus, &:focus-within, &:active {\n      @apply ring-2 ring-opacity-50 ring-neutral-300 text-white;\n    }\n\n    & svg {\n      @apply w-5 h-5 transition-transform duration-75;\n    }\n\n    &[aria-expanded=\"true\"] svg[data-animated=\"true\"] {\n      @apply rotate-180;\n    }\n  }\n\n  & .items_container {\n    @apply absolute right-0 mt-2 origin-top-right bg-neutral-900 rounded z-10;\n  }\n}\n\n.menu_item {\n  @apply flex items-center rounded w-full px-2 py-2;\n\n  & svg {\n    @apply w-4 h-4 mr-4 text-neutral-300;\n  }\n\n  &:hover, &:focus {\n    @apply bg-blue-500 text-blue-50;\n\n    & svg {\n      @apply text-blue-50;\n    }\n  }\n\n  &.danger {\n    &:hover, &:focus {\n      @apply bg-red-500 text-red-50;\n\n      & svg {\n        @apply text-red-50;\n      }\n    }\n  }\n\n  &.disabled {\n    @apply cursor-not-allowed hover:bg-neutral-800 opacity-30 focus:bg-transparent focus:hover:bg-neutral-800;\n  }\n}\n"
  },
  {
    "path": "resources/scripts/components/elements/inputs/Checkbox.tsx",
    "content": "import React, { forwardRef } from 'react';\nimport classNames from 'classnames';\nimport styles from './styles.module.css';\n\ntype Props = Omit<React.ComponentProps<'input'>, 'type'>;\n\nexport default forwardRef<HTMLInputElement, Props>(({ className, ...props }, ref) => (\n    <input\n        ref={ref}\n        type={'checkbox'}\n        className={classNames('form-input', styles.checkbox_input, className)}\n        {...props}\n    />\n));\n"
  },
  {
    "path": "resources/scripts/components/elements/inputs/InputField.tsx",
    "content": "import React, { forwardRef } from 'react';\nimport classNames from 'classnames';\nimport styles from './styles.module.css';\n\nenum Variant {\n    Normal,\n    Snug,\n    Loose,\n}\n\nconst Component = forwardRef<HTMLInputElement, React.ComponentProps<'input'> & { variant?: Variant }>(\n    ({ className, variant, ...props }, ref) => (\n        <input\n            ref={ref}\n            className={classNames(\n                'form-input',\n                styles.text_input,\n                { [styles.loose]: variant === Variant.Loose },\n                className\n            )}\n            {...props}\n        />\n    )\n);\n\nconst InputField = Object.assign(Component, { Variants: Variant });\n\nexport default InputField;\n"
  },
  {
    "path": "resources/scripts/components/elements/inputs/index.ts",
    "content": "import Checkbox from '@/components/elements/inputs/Checkbox';\nimport InputField from '@/components/elements/inputs/InputField';\n\nconst Input = Object.assign(\n    {},\n    {\n        Text: InputField,\n        Checkbox: Checkbox,\n    }\n);\n\nexport { Input };\nexport { default as styles } from './styles.module.css';\n"
  },
  {
    "path": "resources/scripts/components/elements/inputs/styles.module.css",
    "content": ".checkbox_input {\n    @apply w-4 h-4 rounded-sm border-neutral-500 bg-neutral-600 text-primary-500;\n\n    &:focus, &:active {\n        @apply ring-2 ring-primary-500 ring-offset-2 ring-offset-neutral-700;\n    }\n\n    &.indeterminate:checked {\n        @apply text-primary-500/50 border border-primary-500;\n        background-image: url(\"data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20' fill='white'%3E%3Cpath fill-rule='evenodd' d='M5 10a1 1 0 011-1h8a1 1 0 110 2H6a1 1 0 01-1-1z' clip-rule='evenodd' /%3E%3C/svg%3E\");\n    }\n}\n\n.text_input {\n    @apply transition-shadow duration-75;\n    @apply w-full bg-neutral-800 rounded px-4 py-2 outline-none border-0;\n\n    &:focus, &:active {\n        @apply ring-4 ring-blue-300 ring-opacity-75;\n    }\n\n    &.loose {\n        @apply px-6 py-3;\n    }\n}\n"
  },
  {
    "path": "resources/scripts/components/elements/table/PaginationFooter.tsx",
    "content": "import React from 'react';\nimport { PaginationDataSet } from '@/api/http';\nimport classNames from 'classnames';\nimport { Button } from '@/components/elements/button/index';\nimport { ChevronDoubleLeftIcon, ChevronDoubleRightIcon } from '@heroicons/react/solid';\n\ninterface Props {\n    className?: string;\n    pagination: PaginationDataSet;\n    onPageSelect: (page: number) => void;\n}\n\nconst PaginationFooter = ({ pagination, className, onPageSelect }: Props) => {\n    const start = (pagination.currentPage - 1) * pagination.perPage;\n    const end = (pagination.currentPage - 1) * pagination.perPage + pagination.count;\n\n    const { currentPage: current, totalPages: total } = pagination;\n\n    const pages = { previous: [] as number[], next: [] as number[] };\n    for (let i = 1; i <= 2; i++) {\n        if (current - i >= 1) {\n            pages.previous.push(current - i);\n        }\n        if (current + i <= total) {\n            pages.next.push(current + i);\n        }\n    }\n\n    if (pagination.total === 0) {\n        return null;\n    }\n\n    const buttonProps = (page: number) => ({\n        size: Button.Sizes.Small,\n        shape: Button.Shapes.IconSquare,\n        variant: Button.Variants.Secondary,\n        onClick: () => onPageSelect(page),\n    });\n\n    return (\n        <div className={classNames('flex items-center justify-between my-2', className)}>\n            <p className={'text-sm text-neutral-500'}>\n                显示&nbsp;\n                <span className={'font-semibold text-neutral-400'}>\n                    {Math.max(start, Math.min(pagination.total, 1))}\n                </span>\n                &nbsp;到&nbsp;\n                <span className={'font-semibold text-neutral-400'}>{end}</span> 个结果，共计&nbsp;\n                <span className={'font-semibold text-neutral-400'}>{pagination.total}</span> 个结果。\n            </p>\n            {pagination.totalPages > 1 && (\n                <div className={'flex space-x-1'}>\n                    <Button.Text {...buttonProps(1)} disabled={pages.previous.length !== 2}>\n                        <ChevronDoubleLeftIcon className={'w-3 h-3'} />\n                    </Button.Text>\n                    {pages.previous.reverse().map((value) => (\n                        <Button.Text key={`previous-${value}`} {...buttonProps(value)}>\n                            {value}\n                        </Button.Text>\n                    ))}\n                    <Button size={Button.Sizes.Small} shape={Button.Shapes.IconSquare}>\n                        {current}\n                    </Button>\n                    {pages.next.map((value) => (\n                        <Button.Text key={`next-${value}`} {...buttonProps(value)}>\n                            {value}\n                        </Button.Text>\n                    ))}\n                    <Button.Text {...buttonProps(total)} disabled={pages.next.length !== 2}>\n                        <ChevronDoubleRightIcon className={'w-3 h-3'} />\n                    </Button.Text>\n                </div>\n            )}\n        </div>\n    );\n};\n\nexport default PaginationFooter;\n"
  },
  {
    "path": "resources/scripts/components/elements/tooltip/Tooltip.tsx",
    "content": "import React, { cloneElement, useRef, useState } from 'react';\nimport {\n    arrow,\n    autoUpdate,\n    flip,\n    offset,\n    Placement,\n    shift,\n    Side,\n    useClick,\n    useDismiss,\n    useFloating,\n    useFocus,\n    useHover,\n    useInteractions,\n    useRole,\n} from '@floating-ui/react-dom-interactions';\nimport { AnimatePresence, motion } from 'framer-motion';\nimport classNames from 'classnames';\n\ntype Interaction = 'hover' | 'click' | 'focus';\n\ninterface Props {\n    rest?: number;\n    delay?: number | Partial<{ open: number; close: number }>;\n    content: string | React.ReactChild;\n    disabled?: boolean;\n    arrow?: boolean;\n    interactions?: Interaction[];\n    placement?: Placement;\n    className?: string;\n    children: React.ReactElement;\n}\n\nconst arrowSides: Record<Side, string> = {\n    top: 'bottom-[-6px] left-0',\n    bottom: 'top-[-6px] left-0',\n    right: 'top-0 left-[-6px]',\n    left: 'top-0 right-[-6px]',\n};\n\nexport default ({ children, ...props }: Props) => {\n    const arrowEl = useRef<HTMLDivElement>(null);\n    const [open, setOpen] = useState(false);\n\n    const { x, y, reference, floating, middlewareData, strategy, context } = useFloating({\n        open,\n        strategy: 'fixed',\n        placement: props.placement || 'top',\n        middleware: [\n            offset(props.arrow ? 10 : 6),\n            flip(),\n            shift({ padding: 6 }),\n            arrow({ element: arrowEl, padding: 6 }),\n        ],\n        onOpenChange: setOpen,\n        whileElementsMounted: autoUpdate,\n    });\n\n    const interactions = props.interactions || ['hover', 'focus'];\n    const { getReferenceProps, getFloatingProps } = useInteractions([\n        useHover(context, {\n            restMs: props.rest ?? 30,\n            delay: props.delay ?? 0,\n            enabled: interactions.includes('hover'),\n        }),\n        useFocus(context, { enabled: interactions.includes('focus') }),\n        useClick(context, { enabled: interactions.includes('click') }),\n        useRole(context, { role: 'tooltip' }),\n        useDismiss(context),\n    ]);\n\n    const side = arrowSides[(props.placement || 'top').split('-')[0] as Side];\n    const { x: ax, y: ay } = middlewareData.arrow || {};\n\n    if (props.disabled) {\n        return children;\n    }\n\n    return (\n        <>\n            {cloneElement(children, getReferenceProps({ ref: reference, ...children.props }))}\n            <AnimatePresence>\n                {open && (\n                    <motion.div\n                        initial={{ opacity: 0, scale: 0.85 }}\n                        animate={{ opacity: 1, scale: 1 }}\n                        exit={{ opacity: 0 }}\n                        transition={{ type: 'spring', damping: 20, stiffness: 300, duration: 0.075 }}\n                        {...getFloatingProps({\n                            ref: floating,\n                            className:\n                                'bg-gray-900 text-sm text-gray-200 px-3 py-2 rounded pointer-events-none max-w-[24rem]',\n                            style: {\n                                position: strategy,\n                                top: `${y || 0}px`,\n                                left: `${x || 0}px`,\n                            },\n                        })}\n                    >\n                        {props.content}\n                        {props.arrow && (\n                            <div\n                                ref={arrowEl}\n                                style={{\n                                    transform: `translate(${Math.round(ax || 0)}px, ${Math.round(\n                                        ay || 0\n                                    )}px) rotate(45deg)`,\n                                }}\n                                className={classNames('absolute bg-gray-900 w-3 h-3', side)}\n                            />\n                        )}\n                    </motion.div>\n                )}\n            </AnimatePresence>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/transitions/FadeTransition.tsx",
    "content": "import React from 'react';\nimport { Transition } from '@headlessui/react';\n\ntype Duration = `duration-${number}`;\n\ninterface Props {\n    as?: React.ElementType;\n    duration?: Duration | [Duration, Duration];\n    show: boolean;\n    children: React.ReactNode;\n}\n\nexport default ({ children, duration, ...props }: Props) => {\n    const [enterDuration, exitDuration] = Array.isArray(duration)\n        ? duration\n        : !duration\n        ? ['duration-200', 'duration-100']\n        : [duration, duration];\n\n    return (\n        <Transition\n            {...props}\n            enter={`ease-out ${enterDuration}`}\n            enterFrom={'opacity-0'}\n            enterTo={'opacity-100'}\n            leave={`ease-in ${exitDuration}`}\n            leaveFrom={'opacity-100'}\n            leaveTo={'opacity-0'}\n        >\n            {children}\n        </Transition>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/elements/transitions/index.ts",
    "content": "import { Transition as TransitionComponent } from '@headlessui/react';\nimport FadeTransition from '@/components/elements/transitions/FadeTransition';\n\nconst Transition = Object.assign(TransitionComponent, {\n    Fade: FadeTransition,\n});\n\nexport { Transition };\n"
  },
  {
    "path": "resources/scripts/components/history.ts",
    "content": "import { createBrowserHistory } from 'history';\n\nexport const history = createBrowserHistory({ basename: '/' });\n"
  },
  {
    "path": "resources/scripts/components/server/ConflictStateRenderer.tsx",
    "content": "import React from 'react';\nimport { ServerContext } from '@/state/server';\nimport ScreenBlock from '@/components/elements/ScreenBlock';\nimport ServerInstallSvg from '@/assets/images/server_installing.svg';\nimport ServerErrorSvg from '@/assets/images/server_error.svg';\nimport ServerRestoreSvg from '@/assets/images/server_restore.svg';\n\nexport default () => {\n    const status = ServerContext.useStoreState((state) => state.server.data?.status || null);\n    const isTransferring = ServerContext.useStoreState((state) => state.server.data?.isTransferring || false);\n    const isNodeUnderMaintenance = ServerContext.useStoreState(\n        (state) => state.server.data?.isNodeUnderMaintenance || false\n    );\n\n    return status === 'installing' || status === 'install_failed' || status === 'reinstall_failed' ? (\n        <ScreenBlock\n            title={'正在运行安装程序'}\n            image={ServerInstallSvg}\n            message={'此服务器应该很快就准备好了，请几分钟后再试。'}\n        />\n    ) : status === 'suspended' ? (\n        <ScreenBlock\n            title={'服务器已冻结'}\n            image={ServerErrorSvg}\n            message={'此服务器已被冻结，您目前无法访问此服务器。'}\n        />\n    ) : isNodeUnderMaintenance ? (\n        <ScreenBlock title={'节点维护中'} image={ServerErrorSvg} message={'此服务器的节点目前正在维护中。'} />\n    ) : (\n        <ScreenBlock\n            title={isTransferring ? '转移中' : '回档中'}\n            image={ServerRestoreSvg}\n            message={\n                isTransferring\n                    ? '您的服务器正在转移到新节点，请稍后再回来查看。'\n                    : '您的服务器当前正在从备份中恢复，请过几分钟再来查看。'\n            }\n        />\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/InstallListener.tsx",
    "content": "import useWebsocketEvent from '@/plugins/useWebsocketEvent';\nimport { ServerContext } from '@/state/server';\nimport { SocketEvent } from '@/components/server/events';\nimport { mutate } from 'swr';\nimport { getDirectorySwrKey } from '@/plugins/useFileManagerSwr';\n\nconst InstallListener = () => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const getServer = ServerContext.useStoreActions((actions) => actions.server.getServer);\n    const setServerFromState = ServerContext.useStoreActions((actions) => actions.server.setServerFromState);\n\n    useWebsocketEvent(SocketEvent.BACKUP_RESTORE_COMPLETED, () => {\n        mutate(getDirectorySwrKey(uuid, '/'), undefined);\n        setServerFromState((s) => ({ ...s, status: null }));\n    });\n\n    // Listen for the installation completion event and then fire off a request to fetch the updated\n    // server information. This allows the server to automatically become available to the user if they\n    // just sit on the page.\n    useWebsocketEvent(SocketEvent.INSTALL_COMPLETED, () => {\n        getServer(uuid).catch((error) => console.error(error));\n    });\n\n    // When we see the install started event immediately update the state to indicate such so that the\n    // screens automatically update.\n    useWebsocketEvent(SocketEvent.INSTALL_STARTED, () => {\n        setServerFromState((s) => ({ ...s, status: 'installing' }));\n    });\n\n    return null;\n};\n\nexport default InstallListener;\n"
  },
  {
    "path": "resources/scripts/components/server/ServerActivityLogContainer.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { useActivityLogs } from '@/api/server/activity';\nimport ServerContentBlock from '@/components/elements/ServerContentBlock';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport Spinner from '@/components/elements/Spinner';\nimport ActivityLogEntry from '@/components/elements/activity/ActivityLogEntry';\nimport PaginationFooter from '@/components/elements/table/PaginationFooter';\nimport { ActivityLogFilters } from '@/api/account/activity';\nimport { Link } from 'react-router-dom';\nimport classNames from 'classnames';\nimport { styles as btnStyles } from '@/components/elements/button/index';\nimport { XCircleIcon } from '@heroicons/react/solid';\nimport useLocationHash from '@/plugins/useLocationHash';\n\nexport default () => {\n    const { hash } = useLocationHash();\n    const { clearAndAddHttpError } = useFlashKey('server:activity');\n    const [filters, setFilters] = useState<ActivityLogFilters>({ page: 1, sorts: { timestamp: -1 } });\n\n    const { data, isValidating, error } = useActivityLogs(filters, {\n        revalidateOnMount: true,\n        revalidateOnFocus: false,\n    });\n\n    useEffect(() => {\n        setFilters((value) => ({ ...value, filters: { ip: hash.ip, event: hash.event } }));\n    }, [hash]);\n\n    useEffect(() => {\n        clearAndAddHttpError(error);\n    }, [error]);\n\n    return (\n        <ServerContentBlock title={'活动日志'}>\n            <FlashMessageRender byKey={'server:activity'} />\n            {(filters.filters?.event || filters.filters?.ip) && (\n                <div className={'flex justify-end mb-2'}>\n                    <Link\n                        to={'#'}\n                        className={classNames(btnStyles.button, btnStyles.text, 'w-full sm:w-auto')}\n                        onClick={() => setFilters((value) => ({ ...value, filters: {} }))}\n                    >\n                        清除筛选 <XCircleIcon className={'w-4 h-4 ml-2'} />\n                    </Link>\n                </div>\n            )}\n            {!data && isValidating ? (\n                <Spinner centered />\n            ) : !data?.items.length ? (\n                <p className={'text-sm text-center text-gray-400'}>此服务器没有可用的活动日志。</p>\n            ) : (\n                <div className={'bg-gray-700'}>\n                    {data?.items.map((activity) => (\n                        <ActivityLogEntry key={activity.id} activity={activity}>\n                            <span />\n                        </ActivityLogEntry>\n                    ))}\n                </div>\n            )}\n            {data && (\n                <PaginationFooter\n                    pagination={data.pagination}\n                    onPageSelect={(page) => setFilters((value) => ({ ...value, page }))}\n                />\n            )}\n        </ServerContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/TransferListener.tsx",
    "content": "import useWebsocketEvent from '@/plugins/useWebsocketEvent';\nimport { ServerContext } from '@/state/server';\nimport { SocketEvent } from '@/components/server/events';\n\nconst TransferListener = () => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const getServer = ServerContext.useStoreActions((actions) => actions.server.getServer);\n    const setServerFromState = ServerContext.useStoreActions((actions) => actions.server.setServerFromState);\n\n    // Listen for the transfer status event, so we can update the state of the server.\n    useWebsocketEvent(SocketEvent.TRANSFER_STATUS, (status: string) => {\n        if (status === 'pending' || status === 'processing') {\n            setServerFromState((s) => ({ ...s, isTransferring: true }));\n            return;\n        }\n\n        if (status === 'failed') {\n            setServerFromState((s) => ({ ...s, isTransferring: false }));\n            return;\n        }\n\n        if (status !== 'completed') {\n            return;\n        }\n\n        // Refresh the server's information as it's node and allocations were just updated.\n        getServer(uuid).catch((error) => console.error(error));\n    });\n\n    return null;\n};\n\nexport default TransferListener;\n"
  },
  {
    "path": "resources/scripts/components/server/UptimeDuration.tsx",
    "content": "import React from 'react';\n\nexport default ({ uptime }: { uptime: number }) => {\n    const days = Math.floor(uptime / (24 * 60 * 60));\n    const hours = Math.floor((Math.floor(uptime) / 60 / 60) % 24);\n    const remainder = Math.floor(uptime - hours * 60 * 60);\n    const minutes = Math.floor((remainder / 60) % 60);\n    const seconds = remainder % 60;\n\n    if (days > 0) {\n        return (\n            <>\n                {days}天 {hours}时 {minutes}分\n            </>\n        );\n    }\n\n    return (\n        <>\n            {hours}时 {minutes}分 {seconds}秒\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/WebsocketHandler.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { Websocket } from '@/plugins/Websocket';\nimport { ServerContext } from '@/state/server';\nimport getWebsocketToken from '@/api/server/getWebsocketToken';\nimport ContentContainer from '@/components/elements/ContentContainer';\nimport { CSSTransition } from 'react-transition-group';\nimport Spinner from '@/components/elements/Spinner';\nimport tw from 'twin.macro';\n\nconst reconnectErrors = ['jwt: exp claim is invalid', 'jwt: created too far in past (denylist)'];\n\nexport default () => {\n    let updatingToken = false;\n    const [error, setError] = useState<'connecting' | string>('');\n    const { connected, instance } = ServerContext.useStoreState((state) => state.socket);\n    const uuid = ServerContext.useStoreState((state) => state.server.data?.uuid);\n    const setServerStatus = ServerContext.useStoreActions((actions) => actions.status.setServerStatus);\n    const { setInstance, setConnectionState } = ServerContext.useStoreActions((actions) => actions.socket);\n\n    const updateToken = (uuid: string, socket: Websocket) => {\n        if (updatingToken) return;\n\n        updatingToken = true;\n        getWebsocketToken(uuid)\n            .then((data) => socket.setToken(data.token, true))\n            .catch((error) => console.error(error))\n            .then(() => {\n                updatingToken = false;\n            });\n    };\n\n    const connect = (uuid: string) => {\n        const socket = new Websocket();\n\n        socket.on('auth success', () => setConnectionState(true));\n        socket.on('SOCKET_CLOSE', () => setConnectionState(false));\n        socket.on('SOCKET_CONNECT_ERROR', () => {\n            setError('多次尝试后无法连接到 Websocket 实例，请尝试刷新页面。');\n        });\n        socket.on('SOCKET_ERROR', () => {\n            setError('connecting');\n            setConnectionState(false);\n        });\n        socket.on('status', (status) => setServerStatus(status));\n\n        socket.on('daemon error', (message) => {\n            console.warn('从守护程序套接字(socket)得到错误信息:', message);\n        });\n\n        socket.on('token expiring', () => updateToken(uuid, socket));\n        socket.on('token expired', () => updateToken(uuid, socket));\n        socket.on('jwt error', (error: string) => {\n            setConnectionState(false);\n            console.warn('JWT 与 WINGS 验证出现问题:', error);\n\n            if (reconnectErrors.find((v) => error.toLowerCase().indexOf(v) >= 0)) {\n                updateToken(uuid, socket);\n            } else {\n                setError('验证为 WEBSOCKET 提供的凭证时出错。请刷新页面。');\n            }\n        });\n\n        socket.on('transfer status', (status: string) => {\n            if (status === 'starting' || status === 'success') {\n                return;\n            }\n\n            // This code forces a reconnection to the websocket which will connect us to the target node instead of the source node\n            // in order to be able to receive transfer logs from the target node.\n            socket.close();\n            setError('connecting');\n            setConnectionState(false);\n            setInstance(null);\n            connect(uuid);\n        });\n\n        getWebsocketToken(uuid)\n            .then((data) => {\n                // Connect and then set the authentication token.\n                socket.setToken(data.token).connect(data.socket);\n\n                // Once that is done, set the instance.\n                setInstance(socket);\n            })\n            .catch((error) => console.error(error));\n    };\n\n    useEffect(() => {\n        connected && setError('');\n    }, [connected]);\n\n    useEffect(() => {\n        return () => {\n            instance && instance.close();\n        };\n    }, [instance]);\n\n    useEffect(() => {\n        // If there is already an instance or there is no server, just exit out of this process\n        // since we don't need to make a new connection.\n        if (instance || !uuid) {\n            return;\n        }\n\n        connect(uuid);\n    }, [uuid]);\n\n    return error ? (\n        <CSSTransition timeout={150} in appear classNames={'fade'}>\n            <div css={tw`bg-red-500 py-2`}>\n                <ContentContainer css={tw`flex items-center justify-center`}>\n                    {error === 'connecting' ? (\n                        <>\n                            <Spinner size={'small'} />\n                            <p css={tw`ml-2 text-sm text-red-100`}>我们在连接到你的服务器时出现错误，请等待...</p>\n                        </>\n                    ) : (\n                        <p css={tw`ml-2 text-sm text-white`}>{error}</p>\n                    )}\n                </ContentContainer>\n            </div>\n        </CSSTransition>\n    ) : null;\n};\n"
  },
  {
    "path": "resources/scripts/components/server/backups/BackupContainer.tsx",
    "content": "import React, { useContext, useEffect, useState } from 'react';\nimport Spinner from '@/components/elements/Spinner';\nimport useFlash from '@/plugins/useFlash';\nimport Can from '@/components/elements/Can';\nimport CreateBackupButton from '@/components/server/backups/CreateBackupButton';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport BackupRow from '@/components/server/backups/BackupRow';\nimport tw from 'twin.macro';\nimport getServerBackups, { Context as ServerBackupContext } from '@/api/swr/getServerBackups';\nimport { ServerContext } from '@/state/server';\nimport ServerContentBlock from '@/components/elements/ServerContentBlock';\nimport Pagination from '@/components/elements/Pagination';\n\nconst BackupContainer = () => {\n    const { page, setPage } = useContext(ServerBackupContext);\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const { data: backups, error, isValidating } = getServerBackups();\n\n    const backupLimit = ServerContext.useStoreState((state) => state.server.data!.featureLimits.backups);\n\n    useEffect(() => {\n        if (!error) {\n            clearFlashes('backups');\n\n            return;\n        }\n\n        clearAndAddHttpError({ error, key: 'backups' });\n    }, [error]);\n\n    if (!backups || (error && isValidating)) {\n        return <Spinner size={'large'} centered />;\n    }\n\n    return (\n        <ServerContentBlock title={'服务器备份'}>\n            <FlashMessageRender byKey={'backups'} css={tw`mb-4`} />\n            <Pagination data={backups} onPageSelect={setPage}>\n                {({ items }) =>\n                    !items.length ? (\n                        // Don't show any error messages if the server has no backups and the user cannot\n                        // create additional ones for the server.\n                        !backupLimit ? null : (\n                            <p css={tw`text-center text-sm text-neutral-300`}>\n                                {page > 1\n                                    ? '看起来这页没有您的备份，请尝试返回上一个页面。'\n                                    : '目前似乎没有为此服务器存储的备份。'}\n                            </p>\n                        )\n                    ) : (\n                        items.map((backup, index) => (\n                            <BackupRow key={backup.uuid} backup={backup} css={index > 0 ? tw`mt-2` : undefined} />\n                        ))\n                    )\n                }\n            </Pagination>\n            {backupLimit === 0 && (\n                <p css={tw`text-center text-sm text-neutral-300`}>\n                    无法为此服务器创建备份，因为此服务器备份限制设置为0.\n                </p>\n            )}\n            <Can action={'backup.create'}>\n                <div css={tw`mt-6 sm:flex items-center justify-end`}>\n                    {backupLimit > 0 && backups.backupCount > 0 && (\n                        <p css={tw`text-sm text-neutral-300 mb-4 sm:mr-6 sm:mb-0`}>\n                            {backups.backupCount} / {backupLimit} 个备份已为此服务器创建。\n                        </p>\n                    )}\n                    {backupLimit > 0 && backupLimit > backups.backupCount && (\n                        <CreateBackupButton css={tw`w-full sm:w-auto`} />\n                    )}\n                </div>\n            </Can>\n        </ServerContentBlock>\n    );\n};\n\nexport default () => {\n    const [page, setPage] = useState<number>(1);\n    return (\n        <ServerBackupContext.Provider value={{ page, setPage }}>\n            <BackupContainer />\n        </ServerBackupContext.Provider>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/backups/BackupContextMenu.tsx",
    "content": "import React, { useState } from 'react';\nimport {\n    faBoxOpen,\n    faCloudDownloadAlt,\n    faEllipsisH,\n    faLock,\n    faTrashAlt,\n    faUnlock,\n} from '@fortawesome/free-solid-svg-icons';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport DropdownMenu, { DropdownButtonRow } from '@/components/elements/DropdownMenu';\nimport getBackupDownloadUrl from '@/api/server/backups/getBackupDownloadUrl';\nimport useFlash from '@/plugins/useFlash';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport deleteBackup from '@/api/server/backups/deleteBackup';\nimport Can from '@/components/elements/Can';\nimport tw from 'twin.macro';\nimport getServerBackups from '@/api/swr/getServerBackups';\nimport { ServerBackup } from '@/api/server/types';\nimport { ServerContext } from '@/state/server';\nimport Input from '@/components/elements/Input';\nimport { restoreServerBackup } from '@/api/server/backups';\nimport http, { httpErrorToHuman } from '@/api/http';\nimport { Dialog } from '@/components/elements/dialog';\n\ninterface Props {\n    backup: ServerBackup;\n}\n\nexport default ({ backup }: Props) => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const setServerFromState = ServerContext.useStoreActions((actions) => actions.server.setServerFromState);\n    const [modal, setModal] = useState('');\n    const [loading, setLoading] = useState(false);\n    const [truncate, setTruncate] = useState(false);\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const { mutate } = getServerBackups();\n\n    const doDownload = () => {\n        setLoading(true);\n        clearFlashes('backups');\n        getBackupDownloadUrl(uuid, backup.uuid)\n            .then((url) => {\n                // @ts-expect-error this is valid\n                window.location = url;\n            })\n            .catch((error) => {\n                console.error(error);\n                clearAndAddHttpError({ key: 'backups', error });\n            })\n            .then(() => setLoading(false));\n    };\n\n    const doDeletion = () => {\n        setLoading(true);\n        clearFlashes('backups');\n        deleteBackup(uuid, backup.uuid)\n            .then(() =>\n                mutate(\n                    (data) => ({\n                        ...data,\n                        items: data.items.filter((b) => b.uuid !== backup.uuid),\n                        backupCount: data.backupCount - 1,\n                    }),\n                    false\n                )\n            )\n            .catch((error) => {\n                console.error(error);\n                clearAndAddHttpError({ key: 'backups', error });\n                setLoading(false);\n                setModal('');\n            });\n    };\n\n    const doRestorationAction = () => {\n        setLoading(true);\n        clearFlashes('backups');\n        restoreServerBackup(uuid, backup.uuid, truncate)\n            .then(() =>\n                setServerFromState((s) => ({\n                    ...s,\n                    status: 'restoring_backup',\n                }))\n            )\n            .catch((error) => {\n                console.error(error);\n                clearAndAddHttpError({ key: 'backups', error });\n            })\n            .then(() => setLoading(false))\n            .then(() => setModal(''));\n    };\n\n    const onLockToggle = () => {\n        if (backup.isLocked && modal !== 'unlock') {\n            return setModal('unlock');\n        }\n\n        http.post(`/api/client/servers/${uuid}/backups/${backup.uuid}/lock`)\n            .then(() =>\n                mutate(\n                    (data) => ({\n                        ...data,\n                        items: data.items.map((b) =>\n                            b.uuid !== backup.uuid\n                                ? b\n                                : {\n                                      ...b,\n                                      isLocked: !b.isLocked,\n                                  }\n                        ),\n                    }),\n                    false\n                )\n            )\n            .catch((error) => alert(httpErrorToHuman(error)))\n            .then(() => setModal(''));\n    };\n\n    return (\n        <>\n            <Dialog.Confirm\n                open={modal === 'unlock'}\n                onClose={() => setModal('')}\n                title={`解锁 \"${backup.name}\"`}\n                onConfirmed={onLockToggle}\n            >\n                您确定要解锁此备份吗？ 它将不再受到意外删除保护。\n            </Dialog.Confirm>\n            <Dialog.Confirm\n                open={modal === 'restore'}\n                onClose={() => setModal('')}\n                confirm={'回档'}\n                title={`恢复 \"${backup.name}\"`}\n                onConfirmed={() => doRestorationAction()}\n            >\n                <p>\n                    该服务器将停止以恢复备份。备份开始后，您将无法控制服务器电源状态、访问文件管理器或创建其他备份直到它完成。\n                </p>\n                <p css={tw`mt-4 -mb-2 bg-gray-700 p-3 rounded`}>\n                    <label htmlFor={'restore_truncate'} css={tw`text-base flex items-center cursor-pointer`}>\n                        <Input\n                            type={'checkbox'}\n                            css={tw`text-red-500! w-5! h-5! mr-2`}\n                            id={'restore_truncate'}\n                            value={'true'}\n                            checked={truncate}\n                            onChange={() => setTruncate((s) => !s)}\n                        />\n                        在恢复此备份之前删除所有文件和文件夹。\n                    </label>\n                </p>\n            </Dialog.Confirm>\n            <Dialog.Confirm\n                title={`删除 \"${backup.name}\"`}\n                confirm={'继续'}\n                open={modal === 'delete'}\n                onClose={() => setModal('')}\n                onConfirmed={doDeletion}\n            >\n                您确定要删除此备份吗？ 这是一个永久性操作。\n            </Dialog.Confirm>\n            <SpinnerOverlay visible={loading} fixed />\n            {backup.isSuccessful ? (\n                <DropdownMenu\n                    renderToggle={(onClick) => (\n                        <button\n                            onClick={onClick}\n                            css={tw`text-gray-200 transition-colors duration-150 hover:text-gray-100 p-2`}\n                        >\n                            <FontAwesomeIcon icon={faEllipsisH} />\n                        </button>\n                    )}\n                >\n                    <div css={tw`text-sm`}>\n                        <Can action={'backup.download'}>\n                            <DropdownButtonRow onClick={doDownload}>\n                                <FontAwesomeIcon fixedWidth icon={faCloudDownloadAlt} css={tw`text-xs`} />\n                                <span css={tw`ml-2`}>下载</span>\n                            </DropdownButtonRow>\n                        </Can>\n                        <Can action={'backup.restore'}>\n                            <DropdownButtonRow onClick={() => setModal('restore')}>\n                                <FontAwesomeIcon fixedWidth icon={faBoxOpen} css={tw`text-xs`} />\n                                <span css={tw`ml-2`}>恢复</span>\n                            </DropdownButtonRow>\n                        </Can>\n                        <Can action={'backup.delete'}>\n                            <>\n                                <DropdownButtonRow onClick={onLockToggle}>\n                                    <FontAwesomeIcon\n                                        fixedWidth\n                                        icon={backup.isLocked ? faUnlock : faLock}\n                                        css={tw`text-xs mr-2`}\n                                    />\n                                    {backup.isLocked ? '解锁' : '锁定'}\n                                </DropdownButtonRow>\n                                {!backup.isLocked && (\n                                    <DropdownButtonRow danger onClick={() => setModal('delete')}>\n                                        <FontAwesomeIcon fixedWidth icon={faTrashAlt} css={tw`text-xs`} />\n                                        <span css={tw`ml-2`}>删除</span>\n                                    </DropdownButtonRow>\n                                )}\n                            </>\n                        </Can>\n                    </div>\n                </DropdownMenu>\n            ) : (\n                <button\n                    onClick={() => setModal('delete')}\n                    css={tw`text-gray-200 transition-colors duration-150 hover:text-gray-100 p-2`}\n                >\n                    <FontAwesomeIcon icon={faTrashAlt} />\n                </button>\n            )}\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/backups/BackupRow.tsx",
    "content": "import React from 'react';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faArchive, faEllipsisH, faLock } from '@fortawesome/free-solid-svg-icons';\nimport { format, formatDistanceToNow } from 'date-fns';\nimport { zhCN } from 'date-fns/locale';\nimport Spinner from '@/components/elements/Spinner';\nimport { bytesToString } from '@/lib/formatters';\nimport Can from '@/components/elements/Can';\nimport useWebsocketEvent from '@/plugins/useWebsocketEvent';\nimport BackupContextMenu from '@/components/server/backups/BackupContextMenu';\nimport tw from 'twin.macro';\nimport GreyRowBox from '@/components/elements/GreyRowBox';\nimport getServerBackups from '@/api/swr/getServerBackups';\nimport { ServerBackup } from '@/api/server/types';\nimport { SocketEvent } from '@/components/server/events';\n\ninterface Props {\n    backup: ServerBackup;\n    className?: string;\n}\n\nexport default ({ backup, className }: Props) => {\n    const { mutate } = getServerBackups();\n\n    useWebsocketEvent(`${SocketEvent.BACKUP_COMPLETED}:${backup.uuid}` as SocketEvent, (data) => {\n        try {\n            const parsed = JSON.parse(data);\n\n            mutate(\n                (data) => ({\n                    ...data,\n                    items: data.items.map((b) =>\n                        b.uuid !== backup.uuid\n                            ? b\n                            : {\n                                  ...b,\n                                  isSuccessful: parsed.is_successful || true,\n                                  checksum: (parsed.checksum_type || '') + ':' + (parsed.checksum || ''),\n                                  bytes: parsed.file_size || 0,\n                                  completedAt: new Date(),\n                              }\n                    ),\n                }),\n                false\n            );\n        } catch (e) {\n            console.warn(e);\n        }\n    });\n\n    return (\n        <GreyRowBox css={tw`flex-wrap md:flex-nowrap items-center`} className={className}>\n            <div css={tw`flex items-center truncate w-full md:flex-1`}>\n                <div css={tw`mr-4`}>\n                    {backup.completedAt !== null ? (\n                        backup.isLocked ? (\n                            <FontAwesomeIcon icon={faLock} css={tw`text-yellow-500`} />\n                        ) : (\n                            <FontAwesomeIcon icon={faArchive} css={tw`text-neutral-300`} />\n                        )\n                    ) : (\n                        <Spinner size={'small'} />\n                    )}\n                </div>\n                <div css={tw`flex flex-col truncate`}>\n                    <div css={tw`flex items-center text-sm mb-1`}>\n                        {backup.completedAt !== null && !backup.isSuccessful && (\n                            <span\n                                css={tw`bg-red-500 py-px px-2 rounded-full text-white text-xs uppercase border border-red-600 mr-2`}\n                            >\n                                失败\n                            </span>\n                        )}\n                        <p css={tw`break-words truncate`}>{backup.name}</p>\n                        {backup.completedAt !== null && backup.isSuccessful && (\n                            <span css={tw`ml-3 text-neutral-300 text-xs font-extralight hidden sm:inline`}>\n                                {bytesToString(backup.bytes)}\n                            </span>\n                        )}\n                    </div>\n                    <p css={tw`mt-1 md:mt-0 text-xs text-neutral-400 font-mono truncate`}>{backup.checksum}</p>\n                </div>\n            </div>\n            <div css={tw`flex-1 md:flex-none md:w-48 mt-4 md:mt-0 md:ml-8 md:text-center`}>\n                <p title={format(backup.createdAt, 'yyyy年M月d日 HH:mm:ss')} css={tw`text-sm`}>\n                    {formatDistanceToNow(backup.createdAt, { includeSeconds: true, addSuffix: true, locale: zhCN })}\n                </p>\n                <p css={tw`text-2xs text-neutral-500 uppercase mt-1`}>创建于</p>\n            </div>\n            <Can action={['backup.download', 'backup.restore', 'backup.delete']} matchAny>\n                <div css={tw`mt-4 md:mt-0 ml-6`} style={{ marginRight: '-0.5rem' }}>\n                    {!backup.completedAt ? (\n                        <div css={tw`p-2 invisible`}>\n                            <FontAwesomeIcon icon={faEllipsisH} />\n                        </div>\n                    ) : (\n                        <BackupContextMenu backup={backup} />\n                    )}\n                </div>\n            </Can>\n        </GreyRowBox>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/backups/CreateBackupButton.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport Modal, { RequiredModalProps } from '@/components/elements/Modal';\nimport { Field as FormikField, Form, Formik, FormikHelpers, useFormikContext } from 'formik';\nimport { boolean, object, string } from 'yup';\nimport Field from '@/components/elements/Field';\nimport FormikFieldWrapper from '@/components/elements/FormikFieldWrapper';\nimport useFlash from '@/plugins/useFlash';\nimport createServerBackup from '@/api/server/backups/createServerBackup';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport Button from '@/components/elements/Button';\nimport tw from 'twin.macro';\nimport { Textarea } from '@/components/elements/Input';\nimport getServerBackups from '@/api/swr/getServerBackups';\nimport { ServerContext } from '@/state/server';\nimport FormikSwitch from '@/components/elements/FormikSwitch';\nimport Can from '@/components/elements/Can';\n\ninterface Values {\n    name: string;\n    ignored: string;\n    isLocked: boolean;\n}\n\nconst ModalContent = ({ ...props }: RequiredModalProps) => {\n    const { isSubmitting } = useFormikContext<Values>();\n\n    return (\n        <Modal {...props} showSpinnerOverlay={isSubmitting}>\n            <Form>\n                <FlashMessageRender byKey={'backups:create'} css={tw`mb-4`} />\n                <h2 css={tw`text-2xl mb-6`}>创建服务器备份</h2>\n                <Field name={'name'} label={'备份名称'} description={'如果提供，则应用于此备份的名称。'} />\n                <div css={tw`mt-6`}>\n                    <FormikFieldWrapper\n                        name={'ignored'}\n                        label={'忽略的文件和目录'}\n                        description={`\n                            输入生成此备份时要忽略的文件或文件夹。留空使用\n                            服务器目录根目录中 .pteroignore 文件的内容（如果存在）。\n                            除了通过以下方式否定规则外，还支持文件和文件夹的通配符匹配\n                            用感叹号作为路径前缀。\n                        `}\n                    >\n                        <FormikField as={Textarea} name={'ignored'} rows={6} />\n                    </FormikFieldWrapper>\n                </div>\n                <Can action={'backup.delete'}>\n                    <div css={tw`mt-6 bg-neutral-700 border border-neutral-800 shadow-inner p-4 rounded`}>\n                        <FormikSwitch name={'isLocked'} label={'锁定'} description={'防止此备份被删除，直到解锁。'} />\n                    </div>\n                </Can>\n                <div css={tw`flex justify-end mt-6`}>\n                    <Button type={'submit'} disabled={isSubmitting}>\n                        开始备份\n                    </Button>\n                </div>\n            </Form>\n        </Modal>\n    );\n};\n\nexport default () => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const [visible, setVisible] = useState(false);\n    const { mutate } = getServerBackups();\n\n    useEffect(() => {\n        clearFlashes('backups:create');\n    }, [visible]);\n\n    const submit = (values: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        clearFlashes('backups:create');\n        createServerBackup(uuid, values)\n            .then((backup) => {\n                mutate(\n                    (data) => ({ ...data, items: data.items.concat(backup), backupCount: data.backupCount + 1 }),\n                    false\n                );\n                setVisible(false);\n            })\n            .catch((error) => {\n                clearAndAddHttpError({ key: 'backups:create', error });\n                setSubmitting(false);\n            });\n    };\n\n    return (\n        <>\n            {visible && (\n                <Formik\n                    onSubmit={submit}\n                    initialValues={{ name: '', ignored: '', isLocked: false }}\n                    validationSchema={object().shape({\n                        name: string().max(191),\n                        ignored: string(),\n                        isLocked: boolean(),\n                    })}\n                >\n                    <ModalContent appear visible={visible} onDismissed={() => setVisible(false)} />\n                </Formik>\n            )}\n            <Button css={tw`w-full sm:w-auto`} onClick={() => setVisible(true)}>\n                创建备份\n            </Button>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/console/ChartBlock.tsx",
    "content": "import React from 'react';\nimport classNames from 'classnames';\nimport styles from '@/components/server/console/style.module.css';\n\ninterface ChartBlockProps {\n    title: string;\n    legend?: React.ReactNode;\n    children: React.ReactNode;\n}\n\nexport default ({ title, legend, children }: ChartBlockProps) => (\n    <div className={classNames(styles.chart_container, 'group')}>\n        <div className={'flex items-center justify-between px-4 py-2'}>\n            <h3 className={'font-header font-medium transition-colors duration-100 group-hover:text-gray-50'}>\n                {title}\n            </h3>\n            {legend && <p className={'text-sm flex items-center'}>{legend}</p>}\n        </div>\n        <div className={'z-10 ml-2'}>{children}</div>\n    </div>\n);\n"
  },
  {
    "path": "resources/scripts/components/server/console/Console.tsx",
    "content": "import React, { useEffect, useMemo, useRef, useState } from 'react';\nimport { ITerminalOptions, Terminal } from 'xterm';\nimport { FitAddon } from 'xterm-addon-fit';\nimport { SearchAddon } from 'xterm-addon-search';\nimport { SearchBarAddon } from 'xterm-addon-search-bar';\nimport { WebLinksAddon } from 'xterm-addon-web-links';\nimport { Unicode11Addon } from 'xterm-addon-unicode11';\nimport { ScrollDownHelperAddon } from '@/plugins/XtermScrollDownHelperAddon';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport { ServerContext } from '@/state/server';\nimport { usePermissions } from '@/plugins/usePermissions';\nimport { theme as th } from 'twin.macro';\nimport useEventListener from '@/plugins/useEventListener';\nimport { debounce } from 'debounce';\nimport { usePersistedState } from '@/plugins/usePersistedState';\nimport { SocketEvent, SocketRequest } from '@/components/server/events';\nimport classNames from 'classnames';\nimport { ChevronDoubleRightIcon } from '@heroicons/react/solid';\n\nimport 'xterm/css/xterm.css';\nimport styles from './style.module.css';\n\nconst theme = {\n    background: th`colors.black`.toString(),\n    cursor: 'transparent',\n    black: th`colors.black`.toString(),\n    red: '#E54B4B',\n    green: '#9ECE58',\n    yellow: '#FAED70',\n    blue: '#396FE2',\n    magenta: '#BB80B3',\n    cyan: '#2DDAFD',\n    white: '#d0d0d0',\n    brightBlack: 'rgba(255, 255, 255, 0.2)',\n    brightRed: '#FF5370',\n    brightGreen: '#C3E88D',\n    brightYellow: '#FFCB6B',\n    brightBlue: '#82AAFF',\n    brightMagenta: '#C792EA',\n    brightCyan: '#89DDFF',\n    brightWhite: '#ffffff',\n    selection: '#FAF089',\n};\n\nconst terminalProps: ITerminalOptions = {\n    disableStdin: true,\n    cursorStyle: 'underline',\n    allowTransparency: true,\n    fontSize: 12,\n    fontFamily: th('fontFamily.mono'),\n    rows: 30,\n    theme: theme,\n};\n\nexport default () => {\n    const TERMINAL_PRELUDE = '\\u001b[1m\\u001b[33mcontainer@pterodactyl~ \\u001b[0m';\n    const ref = useRef<HTMLDivElement>(null);\n    const terminal = useMemo(() => new Terminal({ ...terminalProps }), []);\n    const fitAddon = new FitAddon();\n    const searchAddon = new SearchAddon();\n    const searchBar = new SearchBarAddon({ searchAddon });\n    const webLinksAddon = new WebLinksAddon();\n    const unicode11Addon = new Unicode11Addon();\n    const scrollDownHelperAddon = new ScrollDownHelperAddon();\n    const { connected, instance } = ServerContext.useStoreState((state) => state.socket);\n    const [canSendCommands] = usePermissions(['control.console']);\n    const serverId = ServerContext.useStoreState((state) => state.server.data!.id);\n    const isTransferring = ServerContext.useStoreState((state) => state.server.data!.isTransferring);\n    const [history, setHistory] = usePersistedState<string[]>(`${serverId}:command_history`, []);\n    const [historyIndex, setHistoryIndex] = useState(-1);\n    // SearchBarAddon has hardcoded z-index: 999 :(\n    const zIndex = `\n    .xterm-search-bar__addon {\n        z-index: 10;\n    }`;\n\n    const handleConsoleOutput = (line: string, prelude = false) =>\n        terminal.writeln((prelude ? TERMINAL_PRELUDE : '') + line.replace(/(?:\\r\\n|\\r|\\n)$/im, '') + '\\u001b[0m');\n\n    const handleTransferStatus = (status: string) => {\n        switch (status) {\n            // Sent by either the source or target node if a failure occurs.\n            case 'failure':\n                terminal.writeln(TERMINAL_PRELUDE + '迁移失败.\\u001b[0m');\n                return;\n        }\n    };\n\n    const handleDaemonErrorOutput = (line: string) =>\n        terminal.writeln(\n            TERMINAL_PRELUDE + '\\u001b[1m\\u001b[41m' + line.replace(/(?:\\r\\n|\\r|\\n)$/im, '') + '\\u001b[0m'\n        );\n\n    const handlePowerChangeEvent = (state: string) =>\n        terminal.writeln(TERMINAL_PRELUDE + '服务器运行状态更新为: ' + state + '...\\u001b[0m');\n\n    const handleCommandKeyDown = (e: React.KeyboardEvent<HTMLInputElement>) => {\n        if (e.key === 'ArrowUp') {\n            const newIndex = Math.min(historyIndex + 1, history!.length - 1);\n\n            setHistoryIndex(newIndex);\n            e.currentTarget.value = history![newIndex] || '';\n\n            // By default up arrow will also bring the cursor to the start of the line,\n            // so we'll preventDefault to keep it at the end.\n            e.preventDefault();\n        }\n\n        if (e.key === 'ArrowDown') {\n            const newIndex = Math.max(historyIndex - 1, -1);\n\n            setHistoryIndex(newIndex);\n            e.currentTarget.value = history![newIndex] || '';\n        }\n\n        const command = e.currentTarget.value;\n        if (e.key === 'Enter' && command.length > 0) {\n            setHistory((prevHistory) => [command, ...prevHistory!].slice(0, 32));\n            setHistoryIndex(-1);\n\n            instance && instance.send('send command', command);\n            e.currentTarget.value = '';\n        }\n    };\n\n    useEffect(() => {\n        if (connected && ref.current && !terminal.element) {\n            terminal.loadAddon(fitAddon);\n            terminal.loadAddon(searchAddon);\n            terminal.loadAddon(searchBar);\n            terminal.loadAddon(webLinksAddon);\n            terminal.loadAddon(unicode11Addon);\n            terminal.loadAddon(scrollDownHelperAddon);\n\n            terminal.open(ref.current);\n\n            // Activate Unicode 11 for proper emoji and special character width handling\n            terminal.unicode.activeVersion = '11';\n\n            fitAddon.fit();\n            searchBar.addNewStyle(zIndex);\n\n            // Add support for capturing keys\n            terminal.attachCustomKeyEventHandler((e: KeyboardEvent) => {\n                if ((e.ctrlKey || e.metaKey) && e.key === 'c') {\n                    document.execCommand('copy');\n                    return false;\n                } else if ((e.ctrlKey || e.metaKey) && e.key === 'f') {\n                    e.preventDefault();\n                    searchBar.show();\n                    return false;\n                } else if (e.key === 'Escape') {\n                    searchBar.hidden();\n                }\n                return true;\n            });\n        }\n    }, [terminal, connected]);\n\n    useEventListener(\n        'resize',\n        debounce(() => {\n            if (terminal.element) {\n                fitAddon.fit();\n            }\n        }, 100)\n    );\n\n    useEffect(() => {\n        const listeners: Record<string, (s: string) => void> = {\n            [SocketEvent.STATUS]: handlePowerChangeEvent,\n            [SocketEvent.CONSOLE_OUTPUT]: handleConsoleOutput,\n            [SocketEvent.INSTALL_OUTPUT]: handleConsoleOutput,\n            [SocketEvent.TRANSFER_LOGS]: handleConsoleOutput,\n            [SocketEvent.TRANSFER_STATUS]: handleTransferStatus,\n            [SocketEvent.DAEMON_MESSAGE]: (line) => handleConsoleOutput(line, true),\n            [SocketEvent.DAEMON_ERROR]: handleDaemonErrorOutput,\n        };\n\n        if (connected && instance) {\n            // Do not clear the console if the server is being transferred.\n            if (!isTransferring) {\n                terminal.clear();\n            }\n\n            Object.keys(listeners).forEach((key: string) => {\n                instance.addListener(key, listeners[key]);\n            });\n            instance.send(SocketRequest.SEND_LOGS);\n        }\n\n        return () => {\n            if (instance) {\n                Object.keys(listeners).forEach((key: string) => {\n                    instance.removeListener(key, listeners[key]);\n                });\n            }\n        };\n    }, [connected, instance]);\n\n    return (\n        <div className={classNames(styles.terminal, 'relative')}>\n            <SpinnerOverlay visible={!connected} size={'large'} />\n            <div\n                className={classNames(styles.container, styles.overflows_container, { 'rounded-b': !canSendCommands })}\n            >\n                <div className={'h-full'}>\n                    <div id={styles.terminal} ref={ref} />\n                </div>\n            </div>\n            {canSendCommands && (\n                <div className={classNames('relative', styles.overflows_container)}>\n                    <input\n                        className={classNames('peer', styles.command_input)}\n                        type={'text'}\n                        placeholder={'在此输入指令...'}\n                        aria-label={'控制台指令输入.'}\n                        disabled={!instance || !connected}\n                        onKeyDown={handleCommandKeyDown}\n                        autoCorrect={'off'}\n                        autoCapitalize={'none'}\n                    />\n                    <div\n                        className={classNames(\n                            'text-gray-100 peer-focus:text-gray-50 peer-focus:animate-pulse',\n                            styles.command_icon\n                        )}\n                    >\n                        <ChevronDoubleRightIcon className={'w-4 h-4'} />\n                    </div>\n                </div>\n            )}\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/console/PowerButtons.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { Button } from '@/components/elements/button/index';\nimport Can from '@/components/elements/Can';\nimport { ServerContext } from '@/state/server';\nimport { PowerAction } from '@/components/server/console/ServerConsoleContainer';\nimport { Dialog } from '@/components/elements/dialog';\n\ninterface PowerButtonProps {\n    className?: string;\n}\n\nexport default ({ className }: PowerButtonProps) => {\n    const [open, setOpen] = useState(false);\n    const status = ServerContext.useStoreState((state) => state.status.value);\n    const instance = ServerContext.useStoreState((state) => state.socket.instance);\n\n    const killable = status === 'stopping';\n    const onButtonClick = (\n        action: PowerAction | 'kill-confirmed',\n        e: React.MouseEvent<HTMLButtonElement, MouseEvent>\n    ): void => {\n        e.preventDefault();\n        if (action === 'kill') {\n            return setOpen(true);\n        }\n\n        if (instance) {\n            setOpen(false);\n            instance.send('set state', action === 'kill-confirmed' ? 'kill' : action);\n        }\n    };\n\n    useEffect(() => {\n        if (status === 'offline') {\n            setOpen(false);\n        }\n    }, [status]);\n\n    return (\n        <div className={className}>\n            <Dialog.Confirm\n                open={open}\n                hideCloseIcon\n                onClose={() => setOpen(false)}\n                title={'强制停止进程'}\n                confirm={'继续'}\n                onConfirmed={onButtonClick.bind(this, 'kill-confirmed')}\n            >\n                强行停止服务器会导致数据损坏。\n            </Dialog.Confirm>\n            <Can action={'control.start'}>\n                <Button\n                    className={'flex-1'}\n                    disabled={status !== 'offline'}\n                    onClick={onButtonClick.bind(this, 'start')}\n                >\n                    开机\n                </Button>\n            </Can>\n            <Can action={'control.restart'}>\n                <Button.Text className={'flex-1'} disabled={!status} onClick={onButtonClick.bind(this, 'restart')}>\n                    重启\n                </Button.Text>\n            </Can>\n            <Can action={'control.stop'}>\n                <Button.Danger\n                    className={'flex-1'}\n                    disabled={status === 'offline'}\n                    onClick={onButtonClick.bind(this, killable ? 'kill' : 'stop')}\n                >\n                    {killable ? '强制停止' : '停止'}\n                </Button.Danger>\n            </Can>\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/console/ServerConsoleContainer.tsx",
    "content": "import React, { memo } from 'react';\nimport { ServerContext } from '@/state/server';\nimport Can from '@/components/elements/Can';\nimport ServerContentBlock from '@/components/elements/ServerContentBlock';\nimport isEqual from 'react-fast-compare';\nimport Spinner from '@/components/elements/Spinner';\nimport Features from '@feature/Features';\nimport Console from '@/components/server/console/Console';\nimport StatGraphs from '@/components/server/console/StatGraphs';\nimport PowerButtons from '@/components/server/console/PowerButtons';\nimport ServerDetailsBlock from '@/components/server/console/ServerDetailsBlock';\nimport { Alert } from '@/components/elements/alert';\n\nexport type PowerAction = 'start' | 'stop' | 'restart' | 'kill';\n\nconst ServerConsoleContainer = () => {\n    const name = ServerContext.useStoreState((state) => state.server.data!.name);\n    const description = ServerContext.useStoreState((state) => state.server.data!.description);\n    const isInstalling = ServerContext.useStoreState((state) => state.server.isInstalling);\n    const isTransferring = ServerContext.useStoreState((state) => state.server.data!.isTransferring);\n    const eggFeatures = ServerContext.useStoreState((state) => state.server.data!.eggFeatures, isEqual);\n    const isNodeUnderMaintenance = ServerContext.useStoreState((state) => state.server.data!.isNodeUnderMaintenance);\n\n    return (\n        <ServerContentBlock title={'控制台'}>\n            {(isNodeUnderMaintenance || isInstalling || isTransferring) && (\n                <Alert type={'warning'} className={'mb-4'}>\n                    {isNodeUnderMaintenance\n                        ? '此服务器的节点目前正在维护中，所有操作均不可用。'\n                        : isInstalling\n                        ? '此服务器当前正在运行其安装过程，大多数操作都是不可用的。'\n                        : '此服务器当前正在转移到另一个节点，所有操作都不可用。'}\n                </Alert>\n            )}\n            <div className={'grid grid-cols-4 gap-4 mb-4'}>\n                <div className={'hidden sm:block sm:col-span-2 lg:col-span-3 pr-4'}>\n                    <h1 className={'font-header font-medium text-2xl text-gray-50 leading-relaxed line-clamp-1'}>\n                        {name}\n                    </h1>\n                    <p className={'text-sm line-clamp-2'}>{description}</p>\n                </div>\n                <div className={'col-span-4 sm:col-span-2 lg:col-span-1 self-end'}>\n                    <Can action={['control.start', 'control.stop', 'control.restart']} matchAny>\n                        <PowerButtons className={'flex sm:justify-end space-x-2'} />\n                    </Can>\n                </div>\n            </div>\n            <div className={'grid grid-cols-4 gap-2 sm:gap-4 mb-4'}>\n                <div className={'flex col-span-4 lg:col-span-3'}>\n                    <Spinner.Suspense>\n                        <Console />\n                    </Spinner.Suspense>\n                </div>\n                <ServerDetailsBlock className={'col-span-4 lg:col-span-1 order-last lg:order-none'} />\n            </div>\n            <div className={'grid grid-cols-1 md:grid-cols-3 gap-2 sm:gap-4'}>\n                <Spinner.Suspense>\n                    <StatGraphs />\n                </Spinner.Suspense>\n            </div>\n            <Features enabled={eggFeatures} />\n        </ServerContentBlock>\n    );\n};\n\nexport default memo(ServerConsoleContainer, isEqual);\n"
  },
  {
    "path": "resources/scripts/components/server/console/ServerDetailsBlock.tsx",
    "content": "import React, { useEffect, useMemo, useState } from 'react';\nimport {\n    faClock,\n    faCloudDownloadAlt,\n    faCloudUploadAlt,\n    faHdd,\n    faMemory,\n    faMicrochip,\n    faWifi,\n} from '@fortawesome/free-solid-svg-icons';\nimport { bytesToString, ip, mbToBytes } from '@/lib/formatters';\nimport { ServerContext } from '@/state/server';\nimport { SocketEvent, SocketRequest } from '@/components/server/events';\nimport UptimeDuration from '@/components/server/UptimeDuration';\nimport StatBlock from '@/components/server/console/StatBlock';\nimport useWebsocketEvent from '@/plugins/useWebsocketEvent';\nimport classNames from 'classnames';\nimport { ServerStatus } from '@/state/server';\n\nconst statusMap: Record<NonNullable<ServerStatus>, string> = {\n    offline: '离线',\n    starting: '启动中',\n    stopping: '停止中',\n    running: '运行中',\n};\n\ntype Stats = Record<'memory' | 'cpu' | 'disk' | 'uptime' | 'rx' | 'tx', number>;\n\nconst getBackgroundColor = (value: number, max: number | null): string | undefined => {\n    const delta = !max ? 0 : value / max;\n\n    if (delta > 0.8) {\n        if (delta > 0.9) {\n            return 'bg-red-500';\n        }\n        return 'bg-yellow-500';\n    }\n\n    return undefined;\n};\n\nconst Limit = ({ limit, children }: { limit: string | null; children: React.ReactNode }) => (\n    <>\n        {children}\n        <span className={'ml-1 text-gray-300 text-[70%] select-none'}>/ {limit || <>&infin;</>}</span>\n    </>\n);\n\nconst ServerDetailsBlock = ({ className }: { className?: string }) => {\n    const [stats, setStats] = useState<Stats>({ memory: 0, cpu: 0, disk: 0, uptime: 0, tx: 0, rx: 0 });\n\n    const status = ServerContext.useStoreState((state) => state.status.value);\n    const connected = ServerContext.useStoreState((state) => state.socket.connected);\n    const instance = ServerContext.useStoreState((state) => state.socket.instance);\n    const limits = ServerContext.useStoreState((state) => state.server.data!.limits);\n\n    const textLimits = useMemo(\n        () => ({\n            cpu: limits?.cpu ? `${limits.cpu}%` : null,\n            memory: limits?.memory ? bytesToString(mbToBytes(limits.memory)) : null,\n            disk: limits?.disk ? bytesToString(mbToBytes(limits.disk)) : null,\n        }),\n        [limits]\n    );\n\n    const allocation = ServerContext.useStoreState((state) => {\n        const match = state.server.data!.allocations.find((allocation) => allocation.isDefault);\n\n        return !match ? 'n/a' : `${match.alias || ip(match.ip)}:${match.port}`;\n    });\n\n    useEffect(() => {\n        if (!connected || !instance) {\n            return;\n        }\n\n        instance.send(SocketRequest.SEND_STATS);\n    }, [instance, connected]);\n\n    useWebsocketEvent(SocketEvent.STATS, (data) => {\n        let stats: any = {};\n        try {\n            stats = JSON.parse(data);\n        } catch (e) {\n            return;\n        }\n\n        setStats({\n            memory: stats.memory_bytes,\n            cpu: stats.cpu_absolute,\n            disk: stats.disk_bytes,\n            tx: stats.network.tx_bytes,\n            rx: stats.network.rx_bytes,\n            uptime: stats.uptime || 0,\n        });\n    });\n\n    return (\n        <div className={classNames('grid grid-cols-6 gap-2 md:gap-4', className)}>\n            <StatBlock icon={faWifi} title={'地址'} copyOnClick={allocation}>\n                {allocation}\n            </StatBlock>\n            <StatBlock\n                icon={faClock}\n                title={'正常运行时间'}\n                color={getBackgroundColor(status === 'running' ? 0 : status !== 'offline' ? 9 : 10, 10)}\n            >\n                {status === null ? (\n                    '离线'\n                ) : stats.uptime > 0 ? (\n                    <UptimeDuration uptime={stats.uptime / 1000} />\n                ) : (\n                    statusMap[status] ?? '未知状态'\n                )}\n            </StatBlock>\n            <StatBlock icon={faMicrochip} title={'CPU'} color={getBackgroundColor(stats.cpu, limits.cpu)}>\n                {status === 'offline' ? (\n                    <span className={'text-gray-400'}>离线</span>\n                ) : (\n                    <Limit limit={textLimits.cpu}>{stats.cpu.toFixed(2)}%</Limit>\n                )}\n            </StatBlock>\n            <StatBlock\n                icon={faMemory}\n                title={'内存'}\n                color={getBackgroundColor(stats.memory / 1024, limits.memory * 1024)}\n            >\n                {status === 'offline' ? (\n                    <span className={'text-gray-400'}>离线</span>\n                ) : (\n                    <Limit limit={textLimits.memory}>{bytesToString(stats.memory)}</Limit>\n                )}\n            </StatBlock>\n            <StatBlock\n                icon={faHdd}\n                title={'存储空间'}\n                color={getBackgroundColor(stats.disk / 1024, limits.disk * 1024)}\n            >\n                <Limit limit={textLimits.disk}>{bytesToString(stats.disk)}</Limit>\n            </StatBlock>\n            <StatBlock icon={faCloudDownloadAlt} title={'网络(入站)'}>\n                {status === 'offline' ? <span className={'text-gray-400'}>离线</span> : bytesToString(stats.rx)}\n            </StatBlock>\n            <StatBlock icon={faCloudUploadAlt} title={'网络(出站)'}>\n                {status === 'offline' ? <span className={'text-gray-400'}>离线</span> : bytesToString(stats.tx)}\n            </StatBlock>\n        </div>\n    );\n};\n\nexport default ServerDetailsBlock;\n"
  },
  {
    "path": "resources/scripts/components/server/console/StatBlock.tsx",
    "content": "import React from 'react';\nimport Icon from '@/components/elements/Icon';\nimport { IconDefinition } from '@fortawesome/free-solid-svg-icons';\nimport classNames from 'classnames';\nimport styles from './style.module.css';\nimport useFitText from 'use-fit-text';\nimport CopyOnClick from '@/components/elements/CopyOnClick';\n\ninterface StatBlockProps {\n    title: string;\n    copyOnClick?: string;\n    color?: string | undefined;\n    icon: IconDefinition;\n    children: React.ReactNode;\n    className?: string;\n}\n\nexport default ({ title, copyOnClick, icon, color, className, children }: StatBlockProps) => {\n    const { fontSize, ref } = useFitText({ minFontSize: 8, maxFontSize: 500 });\n\n    return (\n        <CopyOnClick text={copyOnClick}>\n            <div className={classNames(styles.stat_block, 'bg-gray-600', className)}>\n                <div className={classNames(styles.status_bar, color || 'bg-gray-700')} />\n                <div className={classNames(styles.icon, color || 'bg-gray-700')}>\n                    <Icon\n                        icon={icon}\n                        className={classNames({\n                            'text-gray-100': !color || color === 'bg-gray-700',\n                            'text-gray-50': color && color !== 'bg-gray-700',\n                        })}\n                    />\n                </div>\n                <div className={'flex flex-col justify-center overflow-hidden w-full'}>\n                    <p className={'font-header font-medium leading-tight text-xs md:text-sm text-gray-200'}>{title}</p>\n                    <div\n                        ref={ref}\n                        className={'h-[1.75rem] w-full font-semibold text-gray-50 truncate'}\n                        style={{ fontSize }}\n                    >\n                        {children}\n                    </div>\n                </div>\n            </div>\n        </CopyOnClick>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/console/StatGraphs.tsx",
    "content": "import React, { useEffect, useRef } from 'react';\nimport { ServerContext } from '@/state/server';\nimport { SocketEvent } from '@/components/server/events';\nimport useWebsocketEvent from '@/plugins/useWebsocketEvent';\nimport { Line } from 'react-chartjs-2';\nimport { useChart, useChartTickLabel } from '@/components/server/console/chart';\nimport { hexToRgba } from '@/lib/helpers';\nimport { bytesToString } from '@/lib/formatters';\nimport { CloudDownloadIcon, CloudUploadIcon } from '@heroicons/react/solid';\nimport { theme } from 'twin.macro';\nimport ChartBlock from '@/components/server/console/ChartBlock';\nimport Tooltip from '@/components/elements/tooltip/Tooltip';\n\nexport default () => {\n    const status = ServerContext.useStoreState((state) => state.status.value);\n    const limits = ServerContext.useStoreState((state) => state.server.data!.limits);\n    const previous = useRef<Record<'tx' | 'rx', number>>({ tx: -1, rx: -1 });\n\n    const cpu = useChartTickLabel('CPU', limits.cpu, '%', 2);\n    const memory = useChartTickLabel('内存', limits.memory, 'MiB');\n    const network = useChart('网络', {\n        sets: 2,\n        options: {\n            scales: {\n                y: {\n                    ticks: {\n                        callback(value) {\n                            return bytesToString(typeof value === 'string' ? parseInt(value, 10) : value);\n                        },\n                    },\n                },\n            },\n        },\n        callback(opts, index) {\n            return {\n                ...opts,\n                label: !index ? '入站' : '出站',\n                borderColor: !index ? theme('colors.cyan.400') : theme('colors.yellow.400'),\n                backgroundColor: hexToRgba(!index ? theme('colors.cyan.700') : theme('colors.yellow.700'), 0.5),\n            };\n        },\n    });\n\n    useEffect(() => {\n        if (status === 'offline') {\n            cpu.clear();\n            memory.clear();\n            network.clear();\n        }\n    }, [status]);\n\n    useWebsocketEvent(SocketEvent.STATS, (data: string) => {\n        let values: any = {};\n        try {\n            values = JSON.parse(data);\n        } catch (e) {\n            return;\n        }\n        cpu.push(values.cpu_absolute);\n        memory.push(Math.floor(values.memory_bytes / 1024 / 1024));\n        network.push([\n            previous.current.tx < 0 ? 0 : Math.max(0, values.network.tx_bytes - previous.current.tx),\n            previous.current.rx < 0 ? 0 : Math.max(0, values.network.rx_bytes - previous.current.rx),\n        ]);\n\n        previous.current = { tx: values.network.tx_bytes, rx: values.network.rx_bytes };\n    });\n\n    return (\n        <>\n            <ChartBlock title={'CPU 使用率'}>\n                <Line {...cpu.props} />\n            </ChartBlock>\n            <ChartBlock title={'内存使用率'}>\n                <Line {...memory.props} />\n            </ChartBlock>\n            <ChartBlock\n                title={'网络'}\n                legend={\n                    <>\n                        <Tooltip arrow content={'入站'}>\n                            <CloudDownloadIcon className={'mr-2 w-4 h-4 text-yellow-400'} />\n                        </Tooltip>\n                        <Tooltip arrow content={'出站'}>\n                            <CloudUploadIcon className={'w-4 h-4 text-cyan-400'} />\n                        </Tooltip>\n                    </>\n                }\n            >\n                <Line {...network.props} />\n            </ChartBlock>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/console/chart.ts",
    "content": "import {\n    Chart as ChartJS,\n    ChartData,\n    ChartDataset,\n    ChartOptions,\n    Filler,\n    LinearScale,\n    LineElement,\n    PointElement,\n} from 'chart.js';\nimport { DeepPartial } from 'ts-essentials';\nimport { useState } from 'react';\nimport { deepmerge, deepmergeCustom } from 'deepmerge-ts';\nimport { theme } from 'twin.macro';\nimport { hexToRgba } from '@/lib/helpers';\n\nChartJS.register(LineElement, PointElement, Filler, LinearScale);\n\nconst options: ChartOptions<'line'> = {\n    responsive: true,\n    animation: false,\n    plugins: {\n        legend: { display: false },\n        title: { display: false },\n        tooltip: { enabled: false },\n    },\n    layout: {\n        padding: 0,\n    },\n    scales: {\n        x: {\n            min: 0,\n            max: 19,\n            type: 'linear',\n            grid: {\n                display: false,\n                drawBorder: false,\n            },\n            ticks: {\n                display: false,\n            },\n        },\n        y: {\n            min: 0,\n            type: 'linear',\n            grid: {\n                display: true,\n                color: theme('colors.gray.700'),\n                drawBorder: false,\n            },\n            ticks: {\n                display: true,\n                count: 3,\n                color: theme('colors.gray.200'),\n                font: {\n                    family: theme('fontFamily.sans'),\n                    size: 11,\n                    weight: '400',\n                },\n            },\n        },\n    },\n    elements: {\n        point: {\n            radius: 0,\n        },\n        line: {\n            tension: 0.15,\n        },\n    },\n};\n\nfunction getOptions(opts?: DeepPartial<ChartOptions<'line'>> | undefined): ChartOptions<'line'> {\n    return deepmerge(options, opts || {});\n}\n\ntype ChartDatasetCallback = (value: ChartDataset<'line'>, index: number) => ChartDataset<'line'>;\n\nfunction getEmptyData(label: string, sets = 1, callback?: ChartDatasetCallback | undefined): ChartData<'line'> {\n    const next = callback || ((value) => value);\n\n    return {\n        labels: Array(20)\n            .fill(0)\n            .map((_, index) => index),\n        datasets: Array(sets)\n            .fill(0)\n            .map((_, index) =>\n                next(\n                    {\n                        fill: true,\n                        label,\n                        data: Array(20).fill(-5),\n                        borderColor: theme('colors.cyan.400'),\n                        backgroundColor: hexToRgba(theme('colors.cyan.700'), 0.5),\n                    },\n                    index\n                )\n            ),\n    };\n}\n\nconst merge = deepmergeCustom({ mergeArrays: false });\n\ninterface UseChartOptions {\n    sets: number;\n    options?: DeepPartial<ChartOptions<'line'>> | number | undefined;\n    callback?: ChartDatasetCallback | undefined;\n}\n\nfunction useChart(label: string, opts?: UseChartOptions) {\n    const options = getOptions(\n        typeof opts?.options === 'number' ? { scales: { y: { min: 0, suggestedMax: opts.options } } } : opts?.options\n    );\n    const [data, setData] = useState(getEmptyData(label, opts?.sets || 1, opts?.callback));\n\n    const push = (items: number | null | (number | null)[]) =>\n        setData((state) =>\n            merge(state, {\n                datasets: (Array.isArray(items) ? items : [items]).map((item, index) => ({\n                    ...state.datasets[index],\n                    data: state.datasets[index].data\n                        .slice(1)\n                        .concat(typeof item === 'number' ? Number(item.toFixed(2)) : item),\n                })),\n            })\n        );\n\n    const clear = () =>\n        setData((state) =>\n            merge(state, {\n                datasets: state.datasets.map((value) => ({\n                    ...value,\n                    data: Array(20).fill(-5),\n                })),\n            })\n        );\n\n    return { props: { data, options }, push, clear };\n}\n\nfunction useChartTickLabel(label: string, max: number, tickLabel: string, roundTo?: number) {\n    return useChart(label, {\n        sets: 1,\n        options: {\n            scales: {\n                y: {\n                    suggestedMax: max,\n                    ticks: {\n                        callback(value) {\n                            return `${roundTo ? Number(value).toFixed(roundTo) : value}${tickLabel}`;\n                        },\n                    },\n                },\n            },\n        },\n    });\n}\n\nexport { useChart, useChartTickLabel, getOptions, getEmptyData };\n"
  },
  {
    "path": "resources/scripts/components/server/console/style.module.css",
    "content": ".stat_block {\n    @apply flex items-center rounded shadow-lg relative;\n    @apply col-span-3 md:col-span-2 lg:col-span-6;\n    @apply px-3 py-2 md:p-3 lg:p-4;\n\n    & > .status_bar {\n        @apply w-1 h-full absolute left-0 top-0 rounded-l sm:hidden;\n    }\n\n    & > .icon {\n        @apply hidden flex-shrink-0 items-center justify-center rounded-lg shadow-md w-12 h-12;\n        @apply transition-colors duration-500;\n        @apply sm:flex sm:mr-4;\n\n        & > svg {\n            @apply w-6 h-6 m-auto;\n        }\n    }\n}\n\n.terminal {\n    @apply flex flex-col w-full;\n\n    & .overflows_container {\n        @apply -ml-4 sm:ml-0;\n        width: calc(100% + 2rem);\n\n        @screen sm {\n            @apply w-full;\n        }\n    }\n\n    & > .container {\n        @apply rounded-t p-1 sm:p-2 bg-black min-h-[16rem] flex-1 font-mono text-sm;\n\n        & #terminal {\n            @apply h-full;\n\n            &::-webkit-scrollbar-track {\n                @apply w-2;\n            }\n\n            &::-webkit-scrollbar-thumb {\n                @apply bg-gray-900;\n            }\n        }\n    }\n\n    & .command_icon {\n        @apply flex items-center top-0 left-0 absolute z-10 select-none h-full px-3 transition-colors duration-100;\n    }\n\n    & .command_input {\n        @apply relative bg-gray-900 px-2 text-gray-100 pl-10 pr-4 py-2 w-full font-mono text-sm sm:rounded-b;\n        @apply focus:ring-0 outline-none focus-visible:outline-none;\n        @apply border-0 border-b-2 border-transparent transition-colors duration-100;\n        @apply active:border-cyan-500 focus:border-cyan-500;\n    }\n}\n\n.chart_container {\n    @apply bg-gray-600 rounded shadow-lg pt-2 border-b-4 border-gray-700 relative;\n}\n"
  },
  {
    "path": "resources/scripts/components/server/databases/CreateDatabaseButton.tsx",
    "content": "import React, { useState } from 'react';\nimport Modal from '@/components/elements/Modal';\nimport { Form, Formik, FormikHelpers } from 'formik';\nimport Field from '@/components/elements/Field';\nimport { object, string } from 'yup';\nimport createServerDatabase from '@/api/server/databases/createServerDatabase';\nimport { ServerContext } from '@/state/server';\nimport { httpErrorToHuman } from '@/api/http';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport useFlash from '@/plugins/useFlash';\nimport Button from '@/components/elements/Button';\nimport tw from 'twin.macro';\n\ninterface Values {\n    databaseName: string;\n    connectionsFrom: string;\n}\n\nconst schema = object().shape({\n    databaseName: string()\n        .required('必须提供数据库名称。')\n        .min(3, '数据库名称必须至少为 3 个字符。')\n        .max(48, '数据库名称不得超过 48 个字符。')\n        .matches(/^[\\w\\-.]{3,48}$/, '数据库名称应仅包含字母数字字符 下划线_ 破折号和 / 或半拼句号。'),\n    connectionsFrom: string().matches(/^[\\w\\-/.%:]+$/, '必须提供有效的连接地址。'),\n});\n\nexport default () => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const { addError, clearFlashes } = useFlash();\n    const [visible, setVisible] = useState(false);\n\n    const appendDatabase = ServerContext.useStoreActions((actions) => actions.databases.appendDatabase);\n\n    const submit = (values: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        clearFlashes('database:create');\n        createServerDatabase(uuid, {\n            databaseName: values.databaseName,\n            connectionsFrom: values.connectionsFrom || '%',\n        })\n            .then((database) => {\n                appendDatabase(database);\n                setVisible(false);\n            })\n            .catch((error) => {\n                addError({ key: 'database:create', message: httpErrorToHuman(error) });\n                setSubmitting(false);\n            });\n    };\n\n    return (\n        <>\n            <Formik\n                onSubmit={submit}\n                initialValues={{ databaseName: '', connectionsFrom: '' }}\n                validationSchema={schema}\n            >\n                {({ isSubmitting, resetForm }) => (\n                    <Modal\n                        visible={visible}\n                        dismissable={!isSubmitting}\n                        showSpinnerOverlay={isSubmitting}\n                        onDismissed={() => {\n                            resetForm();\n                            setVisible(false);\n                        }}\n                    >\n                        <FlashMessageRender byKey={'database:create'} css={tw`mb-6`} />\n                        <h2 css={tw`text-2xl mb-6`}>创建新数据库</h2>\n                        <Form css={tw`m-0`}>\n                            <Field\n                                type={'string'}\n                                id={'database_name'}\n                                name={'databaseName'}\n                                label={'数据库名'}\n                                description={'数据库实例的描述性名称。'}\n                            />\n                            <div css={tw`mt-6`}>\n                                <Field\n                                    type={'string'}\n                                    id={'connections_from'}\n                                    name={'connectionsFrom'}\n                                    label={'连接白名单'}\n                                    description={\n                                        '允许哪些IP地址可以连接至此数据库，留空表示允许任何IP地址连接到此数据库。'\n                                    }\n                                />\n                            </div>\n                            <div css={tw`flex flex-wrap justify-end mt-6`}>\n                                <Button\n                                    type={'button'}\n                                    isSecondary\n                                    css={tw`w-full sm:w-auto sm:mr-2`}\n                                    onClick={() => setVisible(false)}\n                                >\n                                    取消\n                                </Button>\n                                <Button css={tw`w-full mt-4 sm:w-auto sm:mt-0`} type={'submit'}>\n                                    创建数据库\n                                </Button>\n                            </div>\n                        </Form>\n                    </Modal>\n                )}\n            </Formik>\n            <Button onClick={() => setVisible(true)}>新数据库</Button>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/databases/DatabaseRow.tsx",
    "content": "import React, { useState } from 'react';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faDatabase, faEye, faTrashAlt } from '@fortawesome/free-solid-svg-icons';\nimport Modal from '@/components/elements/Modal';\nimport { Form, Formik, FormikHelpers } from 'formik';\nimport Field from '@/components/elements/Field';\nimport { object, string } from 'yup';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport { ServerContext } from '@/state/server';\nimport deleteServerDatabase from '@/api/server/databases/deleteServerDatabase';\nimport { httpErrorToHuman } from '@/api/http';\nimport RotatePasswordButton from '@/components/server/databases/RotatePasswordButton';\nimport Can from '@/components/elements/Can';\nimport { ServerDatabase } from '@/api/server/databases/getServerDatabases';\nimport useFlash from '@/plugins/useFlash';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport Label from '@/components/elements/Label';\nimport Input from '@/components/elements/Input';\nimport GreyRowBox from '@/components/elements/GreyRowBox';\nimport CopyOnClick from '@/components/elements/CopyOnClick';\n\ninterface Props {\n    database: ServerDatabase;\n    className?: string;\n}\n\nexport default ({ database, className }: Props) => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const { addError, clearFlashes } = useFlash();\n    const [visible, setVisible] = useState(false);\n    const [connectionVisible, setConnectionVisible] = useState(false);\n\n    const appendDatabase = ServerContext.useStoreActions((actions) => actions.databases.appendDatabase);\n    const removeDatabase = ServerContext.useStoreActions((actions) => actions.databases.removeDatabase);\n\n    const jdbcConnectionString = `jdbc:mysql://${database.username}${\n        database.password ? `:${encodeURIComponent(database.password)}` : ''\n    }@${database.connectionString}/${database.name}`;\n\n    const schema = object().shape({\n        confirm: string()\n            .required('必须提供数据库名称.')\n            .oneOf([database.name.split('_', 2)[1], database.name], '必须提供数据库名称.'),\n    });\n\n    const submit = (values: { confirm: string }, { setSubmitting }: FormikHelpers<{ confirm: string }>) => {\n        clearFlashes();\n        deleteServerDatabase(uuid, database.id)\n            .then(() => {\n                setVisible(false);\n                setTimeout(() => removeDatabase(database.id), 150);\n            })\n            .catch((error) => {\n                console.error(error);\n                setSubmitting(false);\n                addError({ key: 'database:delete', message: httpErrorToHuman(error) });\n            });\n    };\n\n    return (\n        <>\n            <Formik onSubmit={submit} initialValues={{ confirm: '' }} validationSchema={schema} isInitialValid={false}>\n                {({ isSubmitting, isValid, resetForm }) => (\n                    <Modal\n                        visible={visible}\n                        dismissable={!isSubmitting}\n                        showSpinnerOverlay={isSubmitting}\n                        onDismissed={() => {\n                            setVisible(false);\n                            resetForm();\n                        }}\n                    >\n                        <FlashMessageRender byKey={'database:delete'} css={tw`mb-6`} />\n                        <h2 css={tw`text-2xl mb-6`}>数据库删除确认</h2>\n                        <p css={tw`text-sm`}>\n                            删除数据库是一项永久性操作，无法撤消。这将永久 删除 <strong>{database.name}</strong>{' '}\n                            数据库并删除所有相关数据。\n                        </p>\n                        <Form css={tw`m-0 mt-6`}>\n                            <Field\n                                type={'text'}\n                                id={'confirm_name'}\n                                name={'confirm'}\n                                label={'确认数据库名称'}\n                                description={'输入数据库名称以确认删除。'}\n                            />\n                            <div css={tw`mt-6 text-right`}>\n                                <Button type={'button'} isSecondary css={tw`mr-2`} onClick={() => setVisible(false)}>\n                                    取消\n                                </Button>\n                                <Button type={'submit'} color={'red'} disabled={!isValid}>\n                                    删除数据库\n                                </Button>\n                            </div>\n                        </Form>\n                    </Modal>\n                )}\n            </Formik>\n            <Modal visible={connectionVisible} onDismissed={() => setConnectionVisible(false)}>\n                <FlashMessageRender byKey={'database-connection-modal'} css={tw`mb-6`} />\n                <h3 css={tw`mb-6 text-2xl`}>数据库连接详情</h3>\n                <div>\n                    <Label>数据库主机地址</Label>\n                    <CopyOnClick text={database.connectionString}>\n                        <Input type={'text'} readOnly value={database.connectionString} />\n                    </CopyOnClick>\n                </div>\n                <div css={tw`mt-6`}>\n                    <Label>连接白名单</Label>\n                    <Input type={'text'} readOnly value={database.allowConnectionsFrom} />\n                </div>\n                <div css={tw`mt-6`}>\n                    <Label>用户名</Label>\n                    <CopyOnClick text={database.username}>\n                        <Input type={'text'} readOnly value={database.username} />\n                    </CopyOnClick>\n                </div>\n                <Can action={'database.view_password'}>\n                    <div css={tw`mt-6`}>\n                        <Label>密码</Label>\n                        <CopyOnClick text={database.password} showInNotification={false}>\n                            <Input type={'text'} readOnly value={database.password} />\n                        </CopyOnClick>\n                    </div>\n                </Can>\n                <div css={tw`mt-6`}>\n                    <Label>JDBC 连接代码</Label>\n                    <CopyOnClick text={jdbcConnectionString} showInNotification={false}>\n                        <Input type={'text'} readOnly value={jdbcConnectionString} />\n                    </CopyOnClick>\n                </div>\n                <div css={tw`mt-6 text-right`}>\n                    <Can action={'database.update'}>\n                        <RotatePasswordButton databaseId={database.id} onUpdate={appendDatabase} />\n                    </Can>\n                    <Button isSecondary onClick={() => setConnectionVisible(false)}>\n                        关闭\n                    </Button>\n                </div>\n            </Modal>\n            <GreyRowBox $hoverable={false} className={className} css={tw`mb-2`}>\n                <div css={tw`hidden md:block`}>\n                    <FontAwesomeIcon icon={faDatabase} fixedWidth />\n                </div>\n                <div css={tw`flex-1 ml-4`}>\n                    <CopyOnClick text={database.name}>\n                        <p css={tw`text-lg`}>{database.name}</p>\n                    </CopyOnClick>\n                </div>\n                <div css={tw`ml-8 text-center hidden md:block`}>\n                    <CopyOnClick text={database.connectionString}>\n                        <p css={tw`text-sm`}>{database.connectionString}</p>\n                    </CopyOnClick>\n                    <p css={tw`mt-1 text-2xs text-neutral-500 uppercase select-none`}>数据库主机地址</p>\n                </div>\n                <div css={tw`ml-8 text-center hidden md:block`}>\n                    <p css={tw`text-sm`}>{database.allowConnectionsFrom}</p>\n                    <p css={tw`mt-1 text-2xs text-neutral-500 uppercase select-none`}>连接IP白名单</p>\n                </div>\n                <div css={tw`ml-8 text-center hidden md:block`}>\n                    <CopyOnClick text={database.username}>\n                        <p css={tw`text-sm`}>{database.username}</p>\n                    </CopyOnClick>\n                    <p css={tw`mt-1 text-2xs text-neutral-500 uppercase select-none`}>用户名</p>\n                </div>\n                <div css={tw`ml-8`}>\n                    <Button isSecondary css={tw`mr-2`} onClick={() => setConnectionVisible(true)}>\n                        <FontAwesomeIcon icon={faEye} fixedWidth />\n                    </Button>\n                    <Can action={'database.delete'}>\n                        <Button color={'red'} isSecondary onClick={() => setVisible(true)}>\n                            <FontAwesomeIcon icon={faTrashAlt} fixedWidth />\n                        </Button>\n                    </Can>\n                </div>\n            </GreyRowBox>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/databases/DatabasesContainer.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport getServerDatabases from '@/api/server/databases/getServerDatabases';\nimport { ServerContext } from '@/state/server';\nimport { httpErrorToHuman } from '@/api/http';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport DatabaseRow from '@/components/server/databases/DatabaseRow';\nimport Spinner from '@/components/elements/Spinner';\nimport CreateDatabaseButton from '@/components/server/databases/CreateDatabaseButton';\nimport Can from '@/components/elements/Can';\nimport useFlash from '@/plugins/useFlash';\nimport tw from 'twin.macro';\nimport Fade from '@/components/elements/Fade';\nimport ServerContentBlock from '@/components/elements/ServerContentBlock';\nimport { useDeepMemoize } from '@/plugins/useDeepMemoize';\n\nexport default () => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const databaseLimit = ServerContext.useStoreState((state) => state.server.data!.featureLimits.databases);\n\n    const { addError, clearFlashes } = useFlash();\n    const [loading, setLoading] = useState(true);\n\n    const databases = useDeepMemoize(ServerContext.useStoreState((state) => state.databases.data));\n    const setDatabases = ServerContext.useStoreActions((state) => state.databases.setDatabases);\n\n    useEffect(() => {\n        setLoading(!databases.length);\n        clearFlashes('databases');\n\n        getServerDatabases(uuid)\n            .then((databases) => setDatabases(databases))\n            .catch((error) => {\n                console.error(error);\n                addError({ key: 'databases', message: httpErrorToHuman(error) });\n            })\n            .then(() => setLoading(false));\n    }, []);\n\n    return (\n        <ServerContentBlock title={'数据库'}>\n            <FlashMessageRender byKey={'databases'} css={tw`mb-4`} />\n            {!databases.length && loading ? (\n                <Spinner size={'large'} centered />\n            ) : (\n                <Fade timeout={150}>\n                    <>\n                        {databases.length > 0 ? (\n                            databases.map((database, index) => (\n                                <DatabaseRow\n                                    key={database.id}\n                                    database={database}\n                                    className={index > 0 ? 'mt-1' : undefined}\n                                />\n                            ))\n                        ) : (\n                            <p css={tw`text-center text-sm text-neutral-300`}>\n                                {databaseLimit > 0 ? '看起来此服务器没有数据库.' : '此服务器无法创建数据库'}\n                            </p>\n                        )}\n                        <Can action={'database.create'}>\n                            <div css={tw`mt-6 flex items-center justify-end`}>\n                                {databaseLimit > 0 && databases.length > 0 && (\n                                    <p css={tw`text-sm text-neutral-300 mb-4 sm:mr-6 sm:mb-0`}>\n                                        {databases.length} / {databaseLimit} 个数据库已为此服务器创建.\n                                    </p>\n                                )}\n                                {databaseLimit > 0 && databaseLimit !== databases.length && (\n                                    <CreateDatabaseButton css={tw`flex justify-end mt-6`} />\n                                )}\n                            </div>\n                        </Can>\n                    </>\n                </Fade>\n            )}\n        </ServerContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/databases/RotatePasswordButton.tsx",
    "content": "import React, { useState } from 'react';\nimport rotateDatabasePassword from '@/api/server/databases/rotateDatabasePassword';\nimport { Actions, useStoreActions } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport { ServerContext } from '@/state/server';\nimport { ServerDatabase } from '@/api/server/databases/getServerDatabases';\nimport { httpErrorToHuman } from '@/api/http';\nimport Button from '@/components/elements/Button';\nimport tw from 'twin.macro';\n\nexport default ({ databaseId, onUpdate }: { databaseId: string; onUpdate: (database: ServerDatabase) => void }) => {\n    const [loading, setLoading] = useState(false);\n    const { addFlash, clearFlashes } = useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n    const server = ServerContext.useStoreState((state) => state.server.data!);\n\n    if (!databaseId) {\n        return null;\n    }\n\n    const rotate = () => {\n        setLoading(true);\n        clearFlashes();\n\n        rotateDatabasePassword(server.uuid, databaseId)\n            .then((database) => onUpdate(database))\n            .catch((error) => {\n                console.error(error);\n                addFlash({\n                    type: 'error',\n                    title: '错误',\n                    message: httpErrorToHuman(error),\n                    key: 'database-connection-modal',\n                });\n            })\n            .then(() => setLoading(false));\n    };\n\n    return (\n        <Button isSecondary color={'primary'} css={tw`mr-2`} onClick={rotate} isLoading={loading}>\n            重新生成密码\n        </Button>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/events.ts",
    "content": "export enum SocketEvent {\n    DAEMON_MESSAGE = 'daemon message',\n    DAEMON_ERROR = 'daemon error',\n    INSTALL_OUTPUT = 'install output',\n    INSTALL_STARTED = 'install started',\n    INSTALL_COMPLETED = 'install completed',\n    CONSOLE_OUTPUT = 'console output',\n    STATUS = 'status',\n    STATS = 'stats',\n    TRANSFER_LOGS = 'transfer logs',\n    TRANSFER_STATUS = 'transfer status',\n    BACKUP_COMPLETED = 'backup completed',\n    BACKUP_RESTORE_COMPLETED = 'backup restore completed',\n}\n\nexport enum SocketRequest {\n    SEND_LOGS = 'send logs',\n    SEND_STATS = 'send stats',\n    SET_STATE = 'set state',\n}\n"
  },
  {
    "path": "resources/scripts/components/server/features/Features.tsx",
    "content": "import React, { useMemo } from 'react';\nimport features from './index';\nimport { getObjectKeys } from '@/lib/objects';\n\ntype ListItems = [string, React.ComponentType][];\n\nexport default ({ enabled }: { enabled: string[] }) => {\n    const mapped: ListItems = useMemo(() => {\n        return getObjectKeys(features)\n            .filter((key) => enabled.map((v) => v.toLowerCase()).includes(key.toLowerCase()))\n            .reduce((arr, key) => [...arr, [key, features[key]]], [] as ListItems);\n    }, [enabled]);\n\n    return (\n        <React.Suspense fallback={null}>\n            {mapped.map(([key, Component]) => (\n                <Component key={key} />\n            ))}\n        </React.Suspense>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/features/GSLTokenModalFeature.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { ServerContext } from '@/state/server';\nimport Modal from '@/components/elements/Modal';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport useFlash from '@/plugins/useFlash';\nimport { SocketEvent, SocketRequest } from '@/components/server/events';\nimport Field from '@/components/elements/Field';\nimport updateStartupVariable from '@/api/server/updateStartupVariable';\nimport { Form, Formik } from 'formik';\n\ninterface Values {\n    gslToken: string;\n}\n\nconst GSLTokenModalFeature = () => {\n    const [visible, setVisible] = useState(false);\n    const [loading, setLoading] = useState(false);\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const status = ServerContext.useStoreState((state) => state.status.value);\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const { connected, instance } = ServerContext.useStoreState((state) => state.socket);\n\n    useEffect(() => {\n        if (!connected || !instance || status === 'running') return;\n\n        const errors = ['(gsl token expired)', '(account not found)'];\n\n        const listener = (line: string) => {\n            if (errors.some((p) => line.toLowerCase().includes(p))) {\n                setVisible(true);\n            }\n        };\n\n        instance.addListener(SocketEvent.CONSOLE_OUTPUT, listener);\n\n        return () => {\n            instance.removeListener(SocketEvent.CONSOLE_OUTPUT, listener);\n        };\n    }, [connected, instance, status]);\n\n    const updateGSLToken = (values: Values) => {\n        setLoading(true);\n        clearFlashes('feature:gslToken');\n\n        updateStartupVariable(uuid, 'STEAM_ACC', values.gslToken)\n            .then(() => {\n                if (instance) {\n                    instance.send(SocketRequest.SET_STATE, 'restart');\n                }\n\n                setLoading(false);\n                setVisible(false);\n            })\n            .catch((error) => {\n                console.error(error);\n                clearAndAddHttpError({ key: 'feature:gslToken', error });\n            })\n            .then(() => setLoading(false));\n    };\n\n    useEffect(() => {\n        clearFlashes('feature:gslToken');\n    }, []);\n\n    return (\n        <Formik onSubmit={updateGSLToken} initialValues={{ gslToken: '' }}>\n            <Modal\n                visible={visible}\n                onDismissed={() => setVisible(false)}\n                closeOnBackground={false}\n                showSpinnerOverlay={loading}\n            >\n                <FlashMessageRender key={'feature:gslToken'} css={tw`mb-4`} />\n                <Form>\n                    <h2 css={tw`text-2xl mb-4 text-neutral-100`}>无效的 GSL 令牌！</h2>\n                    <p css={tw`mt-4`}>您的 Gameserver 登录令牌（GSL 令牌）似乎无效或已过期。</p>\n                    <p css={tw`mt-4`}>您可以生成一个新的并在下面输入，也可以将该字段留空以完全删除它。</p>\n                    <div css={tw`sm:flex items-center mt-4`}>\n                        <Field\n                            name={'gslToken'}\n                            label={'GSL Token'}\n                            description={'访问 https://steamcommunity.com/dev/managegameservers 以生成令牌。'}\n                            autoFocus\n                        />\n                    </div>\n                    <div css={tw`mt-8 sm:flex items-center justify-end`}>\n                        <Button type={'submit'} css={tw`mt-4 sm:mt-0 sm:ml-4 w-full sm:w-auto`}>\n                            更新 GSL 令牌\n                        </Button>\n                    </div>\n                </Form>\n            </Modal>\n        </Formik>\n    );\n};\n\nexport default GSLTokenModalFeature;\n"
  },
  {
    "path": "resources/scripts/components/server/features/HytaleOauthRequireFeature.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { ServerContext } from '@/state/server';\nimport Modal from '@/components/elements/Modal';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport useFlash from '@/plugins/useFlash';\nimport { SocketEvent } from '@/components/server/events';\n\nconst HytaleOauthRequireFeature = () => {\n    const [visible, setVisible] = useState(false);\n    const [link, setLink] = useState('');\n\n    const status = ServerContext.useStoreState((state) => state.status.value);\n    const { clearFlashes } = useFlash();\n    const { connected, instance } = ServerContext.useStoreState((state) => state.socket);\n\n    useEffect(() => {\n        if (!connected || !instance || status === 'running') return;\n\n        const listener = (line: string) => {\n            if (line.match(/https:\\/\\/oauth\\.accounts\\.hytale\\.com\\/oauth2\\/device\\/verify\\?user_code=(.*)/i)) {\n                setLink(line);\n                setVisible(true);\n            }\n        };\n\n        instance.addListener(SocketEvent.CONSOLE_OUTPUT, listener);\n\n        return () => {\n            instance.removeListener(SocketEvent.CONSOLE_OUTPUT, listener);\n        };\n    }, [connected, instance, status]);\n\n    useEffect(() => {\n        clearFlashes('feature:hytaleOauth');\n    }, []);\n\n    const handleLogin = () => {\n        if (link) {\n            window.open(link, '_blank', 'noopener,noreferrer');\n            setVisible(false);\n            setLink('');\n        }\n    };\n\n    return (\n        <Modal\n            visible={visible}\n            onDismissed={() => {\n                setVisible(false);\n                setLink('');\n            }}\n            closeOnBackground={false}\n            showSpinnerOverlay={false}\n        >\n            <FlashMessageRender key={'feature:hytaleOauth'} css={tw`mb-4`} />\n            <h2 css={tw`text-2xl mb-4 text-neutral-100`}>需要身份验证</h2>\n            <p css={tw`text-neutral-200`}>您需要使用 Hytale 账户进行身份验证才能下载或更新服务器文件，请登录后继续。</p>\n            <div css={tw`mt-8 sm:flex items-center justify-end`}>\n                <Button isSecondary onClick={() => setVisible(false)} css={tw`w-full sm:w-auto border-transparent`}>\n                    取消\n                </Button>\n                <Button onClick={handleLogin} css={tw`mt-4 sm:mt-0 sm:ml-4 w-full sm:w-auto`}>\n                    登录\n                </Button>\n            </div>\n        </Modal>\n    );\n};\n\nexport default HytaleOauthRequireFeature;\n"
  },
  {
    "path": "resources/scripts/components/server/features/JavaVersionModalFeature.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { ServerContext } from '@/state/server';\nimport Modal from '@/components/elements/Modal';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport setSelectedDockerImage from '@/api/server/setSelectedDockerImage';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport useFlash from '@/plugins/useFlash';\nimport { SocketEvent, SocketRequest } from '@/components/server/events';\nimport Select from '@/components/elements/Select';\nimport useWebsocketEvent from '@/plugins/useWebsocketEvent';\nimport Can from '@/components/elements/Can';\nimport getServerStartup from '@/api/swr/getServerStartup';\nimport InputSpinner from '@/components/elements/InputSpinner';\n\nconst MATCH_ERRORS = [\n    'minecraft 1.17 requires running the server with java 16 or above',\n    'minecraft 1.18 requires running the server with java 17 or above',\n    'java.lang.unsupportedclassversionerror',\n    'unsupported major.minor version',\n    'has been compiled by a more recent version of the java runtime',\n];\n\nconst JavaVersionModalFeature = () => {\n    const [visible, setVisible] = useState(false);\n    const [loading, setLoading] = useState(false);\n    const [selectedVersion, setSelectedVersion] = useState('');\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const status = ServerContext.useStoreState((state) => state.status.value);\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const { instance } = ServerContext.useStoreState((state) => state.socket);\n\n    const { data, isValidating, mutate } = getServerStartup(uuid, null, { revalidateOnMount: false });\n\n    useEffect(() => {\n        if (!visible) return;\n\n        mutate().then((value) => {\n            setSelectedVersion(Object.values(value?.dockerImages || [])[0] || '');\n        });\n    }, [visible]);\n\n    useWebsocketEvent(SocketEvent.CONSOLE_OUTPUT, (data) => {\n        if (status === 'running') return;\n\n        if (MATCH_ERRORS.some((p) => data.toLowerCase().includes(p.toLowerCase()))) {\n            setVisible(true);\n        }\n    });\n\n    const updateJava = () => {\n        setLoading(true);\n        clearFlashes('feature:javaVersion');\n\n        setSelectedDockerImage(uuid, selectedVersion)\n            .then(() => {\n                if (status === 'offline' && instance) {\n                    instance.send(SocketRequest.SET_STATE, 'restart');\n                }\n                setVisible(false);\n            })\n            .catch((error) => clearAndAddHttpError({ key: 'feature:javaVersion', error }))\n            .then(() => setLoading(false));\n    };\n\n    useEffect(() => {\n        clearFlashes('feature:javaVersion');\n    }, []);\n\n    return (\n        <Modal\n            visible={visible}\n            onDismissed={() => setVisible(false)}\n            closeOnBackground={false}\n            showSpinnerOverlay={loading}\n        >\n            <FlashMessageRender key={'feature:javaVersion'} css={tw`mb-4`} />\n            <h2 css={tw`text-2xl mb-4 text-neutral-100`}>此服务端程序不兼容该 Java 版本，更换 Docker 镜像吗?</h2>\n            <p css={tw`mt-4`}>\n                由于未满足所需的 Java 版本，此服务器无法启动.\n                <Can action={'startup.docker-image'}>\n                    &nbsp;请在下方选择合适的 JDK 版本 Docker 镜像以启动服务端程序.\n                </Can>\n            </p>\n            <Can action={'startup.docker-image'}>\n                <div css={tw`mt-4`}>\n                    <InputSpinner visible={!data || isValidating}>\n                        <Select disabled={!data} onChange={(e) => setSelectedVersion(e.target.value)}>\n                            {!data ? (\n                                <option disabled />\n                            ) : (\n                                Object.keys(data.dockerImages).map((key) => (\n                                    <option key={key} value={data.dockerImages[key]}>\n                                        {key}\n                                    </option>\n                                ))\n                            )}\n                        </Select>\n                    </InputSpinner>\n                </div>\n            </Can>\n            <div css={tw`mt-8 flex flex-col sm:flex-row justify-end sm:space-x-4 space-y-4 sm:space-y-0`}>\n                <Button isSecondary onClick={() => setVisible(false)} css={tw`w-full sm:w-auto`}>\n                    取消\n                </Button>\n                <Can action={'startup.docker-image'}>\n                    <Button onClick={updateJava} css={tw`w-full sm:w-auto`}>\n                        更新 Docker 镜像\n                    </Button>\n                </Can>\n            </div>\n        </Modal>\n    );\n};\n\nexport default JavaVersionModalFeature;\n"
  },
  {
    "path": "resources/scripts/components/server/features/PIDLimitModalFeature.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { ServerContext } from '@/state/server';\nimport Modal from '@/components/elements/Modal';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport useFlash from '@/plugins/useFlash';\nimport { SocketEvent } from '@/components/server/events';\nimport { useStoreState } from 'easy-peasy';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faExclamationTriangle } from '@fortawesome/free-solid-svg-icons';\n\nconst PIDLimitModalFeature = () => {\n    const [visible, setVisible] = useState(false);\n    const [loading] = useState(false);\n\n    const status = ServerContext.useStoreState((state) => state.status.value);\n    const { clearFlashes } = useFlash();\n    const { connected, instance } = ServerContext.useStoreState((state) => state.socket);\n    const isAdmin = useStoreState((state) => state.user.data!.rootAdmin);\n\n    useEffect(() => {\n        if (!connected || !instance || status === 'running') return;\n\n        const errors = [\n            'pthread_create failed',\n            'failed to create thread',\n            'unable to create thread',\n            'unable to create native thread',\n            'unable to create new native thread',\n            'exception in thread \"craft async scheduler management thread\"',\n        ];\n\n        const listener = (line: string) => {\n            if (errors.some((p) => line.toLowerCase().includes(p))) {\n                setVisible(true);\n            }\n        };\n\n        instance.addListener(SocketEvent.CONSOLE_OUTPUT, listener);\n\n        return () => {\n            instance.removeListener(SocketEvent.CONSOLE_OUTPUT, listener);\n        };\n    }, [connected, instance, status]);\n\n    useEffect(() => {\n        clearFlashes('feature:pidLimit');\n    }, []);\n\n    return (\n        <Modal\n            visible={visible}\n            onDismissed={() => setVisible(false)}\n            closeOnBackground={false}\n            showSpinnerOverlay={loading}\n        >\n            <FlashMessageRender key={'feature:pidLimit'} css={tw`mb-4`} />\n            {isAdmin ? (\n                <>\n                    <div css={tw`mt-4 sm:flex items-center`}>\n                        <FontAwesomeIcon css={tw`pr-4`} icon={faExclamationTriangle} color={'orange'} size={'4x'} />\n                        <h2 css={tw`text-2xl mb-4 text-neutral-100 `}>已达到内存或进程限制...</h2>\n                    </div>\n                    <p css={tw`mt-4`}>此服务器已达到最大进程或内存限制。</p>\n                    <p css={tw`mt-4`}>\n                        在 wings 的配置文件 <code css={tw`font-mono bg-neutral-900`}>config.yml</code> 中增加{' '}\n                        <code css={tw`font-mono bg-neutral-900`}>container_pid_limit</code>{' '}\n                        参数，可能有助于解决这个问题。\n                    </p>\n                    <p css={tw`mt-4`}>\n                        <b>注意：必须重新启动 Wings 才能使配置文件更改生效</b>\n                    </p>\n                    <div css={tw`mt-8 sm:flex items-center justify-end`}>\n                        <Button onClick={() => setVisible(false)} css={tw`w-full sm:w-auto border-transparent`}>\n                            关闭\n                        </Button>\n                    </div>\n                </>\n            ) : (\n                <>\n                    <div css={tw`mt-4 sm:flex items-center`}>\n                        <FontAwesomeIcon css={tw`pr-4`} icon={faExclamationTriangle} color={'orange'} size={'4x'} />\n                        <h2 css={tw`text-2xl mb-4 text-neutral-100`}>可能达到资源限制...</h2>\n                    </div>\n                    <p css={tw`mt-4`}>此服务器尝试使用的资源多于分配的资源。请联系管理员，并在下面给他们错误信息。</p>\n                    <p css={tw`mt-4`}>\n                        <code css={tw`font-mono bg-neutral-900`}>\n                            pthread_create 失败，可能内存不足或已达到进程/资源限制\n                        </code>\n                    </p>\n                    <div css={tw`mt-8 sm:flex items-center justify-end`}>\n                        <Button onClick={() => setVisible(false)} css={tw`w-full sm:w-auto border-transparent`}>\n                            关闭\n                        </Button>\n                    </div>\n                </>\n            )}\n        </Modal>\n    );\n};\n\nexport default PIDLimitModalFeature;\n"
  },
  {
    "path": "resources/scripts/components/server/features/SteamDiskSpaceFeature.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { ServerContext } from '@/state/server';\nimport Modal from '@/components/elements/Modal';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport useFlash from '@/plugins/useFlash';\nimport { SocketEvent } from '@/components/server/events';\nimport { useStoreState } from 'easy-peasy';\n\nconst SteamDiskSpaceFeature = () => {\n    const [visible, setVisible] = useState(false);\n    const [loading] = useState(false);\n\n    const status = ServerContext.useStoreState((state) => state.status.value);\n    const { clearFlashes } = useFlash();\n    const { connected, instance } = ServerContext.useStoreState((state) => state.socket);\n    const isAdmin = useStoreState((state) => state.user.data!.rootAdmin);\n\n    useEffect(() => {\n        if (!connected || !instance || status === 'running') return;\n\n        const errors = ['steamcmd needs 250mb of free disk space to update', '0x202 after update job'];\n\n        const listener = (line: string) => {\n            if (errors.some((p) => line.toLowerCase().includes(p))) {\n                setVisible(true);\n            }\n        };\n\n        instance.addListener(SocketEvent.CONSOLE_OUTPUT, listener);\n\n        return () => {\n            instance.removeListener(SocketEvent.CONSOLE_OUTPUT, listener);\n        };\n    }, [connected, instance, status]);\n\n    useEffect(() => {\n        clearFlashes('feature:steamDiskSpace');\n    }, []);\n\n    return (\n        <Modal\n            visible={visible}\n            onDismissed={() => setVisible(false)}\n            closeOnBackground={false}\n            showSpinnerOverlay={loading}\n        >\n            <FlashMessageRender key={'feature:steamDiskSpace'} css={tw`mb-4`} />\n            {isAdmin ? (\n                <>\n                    <div css={tw`mt-4 sm:flex items-center`}>\n                        <h2 css={tw`text-2xl mb-4 text-neutral-100 `}>可用存储空间不足...</h2>\n                    </div>\n                    <p css={tw`mt-4`}>此服务器已用完可用存储空间，无法完成安装或更新过程。</p>\n                    <p css={tw`mt-4`}>\n                        通过在托管此服务器的主机上输入{' '}\n                        <code css={tw`font-mono bg-neutral-900 rounded py-1 px-2`}>df -h</code>{' '}\n                        确保主机有足够的存储空间。删除文件或增加可用存储空间以解决问题。\n                    </p>\n                    <div css={tw`mt-8 sm:flex items-center justify-end`}>\n                        <Button onClick={() => setVisible(false)} css={tw`w-full sm:w-auto border-transparent`}>\n                            关闭\n                        </Button>\n                    </div>\n                </>\n            ) : (\n                <>\n                    <div css={tw`mt-4 sm:flex items-center`}>\n                        <h2 css={tw`text-2xl mb-4 text-neutral-100`}>可用存储空间不足...</h2>\n                    </div>\n                    <p css={tw`mt-4`}>\n                        此服务器已用完可用存储空间，无法完成安装或更新过程。 请与管理员联系并告知他们存储空间问题。\n                    </p>\n                    <div css={tw`mt-8 sm:flex items-center justify-end`}>\n                        <Button onClick={() => setVisible(false)} css={tw`w-full sm:w-auto border-transparent`}>\n                            关闭\n                        </Button>\n                    </div>\n                </>\n            )}\n        </Modal>\n    );\n};\n\nexport default SteamDiskSpaceFeature;\n"
  },
  {
    "path": "resources/scripts/components/server/features/eula/EulaModalFeature.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { ServerContext } from '@/state/server';\nimport Modal from '@/components/elements/Modal';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport saveFileContents from '@/api/server/files/saveFileContents';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport useFlash from '@/plugins/useFlash';\nimport { SocketEvent, SocketRequest } from '@/components/server/events';\n\nconst EulaModalFeature = () => {\n    const [visible, setVisible] = useState(false);\n    const [loading, setLoading] = useState(false);\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const status = ServerContext.useStoreState((state) => state.status.value);\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const { connected, instance } = ServerContext.useStoreState((state) => state.socket);\n\n    useEffect(() => {\n        if (!connected || !instance || status === 'running') return;\n\n        const listener = (line: string) => {\n            if (line.toLowerCase().indexOf('you need to agree to the eula in order to run the server') >= 0) {\n                setVisible(true);\n            }\n        };\n\n        instance.addListener(SocketEvent.CONSOLE_OUTPUT, listener);\n\n        return () => {\n            instance.removeListener(SocketEvent.CONSOLE_OUTPUT, listener);\n        };\n    }, [connected, instance, status]);\n\n    const onAcceptEULA = () => {\n        setLoading(true);\n        clearFlashes('feature:eula');\n\n        saveFileContents(uuid, 'eula.txt', 'eula=true')\n            .then(() => {\n                if (status === 'offline' && instance) {\n                    instance.send(SocketRequest.SET_STATE, 'restart');\n                }\n\n                setLoading(false);\n                setVisible(false);\n            })\n            .catch((error) => {\n                console.error(error);\n                clearAndAddHttpError({ key: 'feature:eula', error });\n            })\n            .then(() => setLoading(false));\n    };\n\n    useEffect(() => {\n        clearFlashes('feature:eula');\n    }, []);\n\n    return (\n        <Modal\n            visible={visible}\n            onDismissed={() => setVisible(false)}\n            closeOnBackground={false}\n            showSpinnerOverlay={loading}\n        >\n            <FlashMessageRender key={'feature:eula'} css={tw`mb-4`} />\n            <h2 css={tw`text-2xl mb-4 text-neutral-100`}>同意 Minecraft&reg; EULA 协议</h2>\n            <p css={tw`text-neutral-200`}>\n                请点击下面的 {'\"我接受\"'} 来表示你同意&nbsp;\n                <a\n                    target={'_blank'}\n                    css={tw`text-primary-300 underline transition-colors duration-150 hover:text-primary-400`}\n                    rel={'noreferrer noopener'}\n                    href='https://www.minecraft.net/eula'\n                >\n                    Minecraft&reg; EULA 协议\n                </a>\n                。否则服务器将无法正常启动 。\n            </p>\n            <div css={tw`mt-8 sm:flex items-center justify-end`}>\n                <Button isSecondary onClick={() => setVisible(false)} css={tw`w-full sm:w-auto border-transparent`}>\n                    不接受\n                </Button>\n                <Button onClick={onAcceptEULA} css={tw`mt-4 sm:mt-0 sm:ml-4 w-full sm:w-auto`}>\n                    我接受\n                </Button>\n            </div>\n        </Modal>\n    );\n};\n\nexport default EulaModalFeature;\n"
  },
  {
    "path": "resources/scripts/components/server/features/index.ts",
    "content": "import { ComponentType, lazy } from 'react';\n\n/**\n * Custom features should be registered here as lazy components so that they do\n * not impact the generated JS bundle size. They will be automatically loaded in\n * whenever they are actually loaded for the client (which may be never, depending\n * on the feature and the egg).\n */\nconst features: Record<string, ComponentType> = {\n    eula: lazy(() => import('@feature/eula/EulaModalFeature')),\n    java_version: lazy(() => import('@feature/JavaVersionModalFeature')),\n    gsl_token: lazy(() => import('@feature/GSLTokenModalFeature')),\n    pid_limit: lazy(() => import('@feature/PIDLimitModalFeature')),\n    steam_disk_space: lazy(() => import('@feature/SteamDiskSpaceFeature')),\n    hytale_oauth: lazy(() => import('@feature/HytaleOauthRequireFeature')),\n};\n\nexport default features;\n"
  },
  {
    "path": "resources/scripts/components/server/files/ChmodFileModal.tsx",
    "content": "import { fileBitsToString } from '@/helpers';\nimport useFileManagerSwr from '@/plugins/useFileManagerSwr';\nimport React from 'react';\nimport Modal, { RequiredModalProps } from '@/components/elements/Modal';\nimport { Form, Formik, FormikHelpers } from 'formik';\nimport Field from '@/components/elements/Field';\nimport chmodFiles from '@/api/server/files/chmodFiles';\nimport { ServerContext } from '@/state/server';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport useFlash from '@/plugins/useFlash';\n\ninterface FormikValues {\n    mode: string;\n}\n\ninterface File {\n    file: string;\n    mode: string;\n}\n\ntype OwnProps = RequiredModalProps & { files: File[] };\n\nconst ChmodFileModal = ({ files, ...props }: OwnProps) => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const { mutate } = useFileManagerSwr();\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n    const setSelectedFiles = ServerContext.useStoreActions((actions) => actions.files.setSelectedFiles);\n\n    const submit = ({ mode }: FormikValues, { setSubmitting }: FormikHelpers<FormikValues>) => {\n        clearFlashes('files');\n\n        mutate(\n            (data) =>\n                data.map((f) =>\n                    f.name === files[0].file ? { ...f, mode: fileBitsToString(mode, !f.isFile), modeBits: mode } : f\n                ),\n            false\n        );\n\n        const data = files.map((f) => ({ file: f.file, mode: mode }));\n\n        chmodFiles(uuid, directory, data)\n            .then((): Promise<any> => (files.length > 0 ? mutate() : Promise.resolve()))\n            .then(() => setSelectedFiles([]))\n            .catch((error) => {\n                mutate();\n                setSubmitting(false);\n                clearAndAddHttpError({ key: 'files', error });\n            })\n            .then(() => props.onDismissed());\n    };\n\n    return (\n        <Formik onSubmit={submit} initialValues={{ mode: files.length > 1 ? '' : files[0].mode || '' }}>\n            {({ isSubmitting }) => (\n                <Modal {...props} dismissable={!isSubmitting} showSpinnerOverlay={isSubmitting}>\n                    <Form css={tw`m-0`}>\n                        <div css={tw`flex flex-wrap items-end`}>\n                            <div css={tw`w-full sm:flex-1 sm:mr-4`}>\n                                <Field type={'string'} id={'file_mode'} name={'mode'} label={'文件模式'} autoFocus />\n                            </div>\n                            <div css={tw`w-full sm:w-auto mt-4 sm:mt-0`}>\n                                <Button css={tw`w-full`}>更新</Button>\n                            </div>\n                        </div>\n                    </Form>\n                </Modal>\n            )}\n        </Formik>\n    );\n};\n\nexport default ChmodFileModal;\n"
  },
  {
    "path": "resources/scripts/components/server/files/FileDropdownMenu.tsx",
    "content": "import React, { memo, useRef, useState } from 'react';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport {\n    faBoxOpen,\n    faCopy,\n    faEllipsisH,\n    faFileArchive,\n    faFileCode,\n    faFileDownload,\n    faLevelUpAlt,\n    faPencilAlt,\n    faTrashAlt,\n    IconDefinition,\n} from '@fortawesome/free-solid-svg-icons';\nimport RenameFileModal from '@/components/server/files/RenameFileModal';\nimport { ServerContext } from '@/state/server';\nimport { join } from 'pathe';\nimport deleteFiles from '@/api/server/files/deleteFiles';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport copyFile from '@/api/server/files/copyFile';\nimport Can from '@/components/elements/Can';\nimport getFileDownloadUrl from '@/api/server/files/getFileDownloadUrl';\nimport useFlash from '@/plugins/useFlash';\nimport tw from 'twin.macro';\nimport { FileObject } from '@/api/server/files/loadDirectory';\nimport useFileManagerSwr from '@/plugins/useFileManagerSwr';\nimport DropdownMenu from '@/components/elements/DropdownMenu';\nimport styled from 'styled-components/macro';\nimport useEventListener from '@/plugins/useEventListener';\nimport compressFiles from '@/api/server/files/compressFiles';\nimport decompressFiles from '@/api/server/files/decompressFiles';\nimport isEqual from 'react-fast-compare';\nimport ChmodFileModal from '@/components/server/files/ChmodFileModal';\nimport { Dialog } from '@/components/elements/dialog';\n\ntype ModalType = 'rename' | 'move' | 'chmod';\n\nconst StyledRow = styled.div<{ $danger?: boolean }>`\n    ${tw`p-2 flex items-center rounded`};\n    ${(props) =>\n        props.$danger ? tw`hover:bg-red-100 hover:text-red-700` : tw`hover:bg-neutral-100 hover:text-neutral-700`};\n`;\n\ninterface RowProps extends React.HTMLAttributes<HTMLDivElement> {\n    icon: IconDefinition;\n    title: string;\n    $danger?: boolean;\n}\n\nconst Row = ({ icon, title, ...props }: RowProps) => (\n    <StyledRow {...props}>\n        <FontAwesomeIcon icon={icon} css={tw`text-xs`} fixedWidth />\n        <span css={tw`ml-2`}>{title}</span>\n    </StyledRow>\n);\n\nconst FileDropdownMenu = ({ file }: { file: FileObject }) => {\n    const onClickRef = useRef<DropdownMenu>(null);\n    const [showSpinner, setShowSpinner] = useState(false);\n    const [modal, setModal] = useState<ModalType | null>(null);\n    const [showConfirmation, setShowConfirmation] = useState(false);\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const { mutate } = useFileManagerSwr();\n    const { clearAndAddHttpError, clearFlashes } = useFlash();\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n\n    useEventListener(`pterodactyl:files:ctx:${file.key}`, (e: CustomEvent) => {\n        if (onClickRef.current) {\n            onClickRef.current.triggerMenu(e.detail);\n        }\n    });\n\n    const doDeletion = () => {\n        clearFlashes('files');\n\n        // For UI speed, immediately remove the file from the listing before calling the deletion function.\n        // If the delete actually fails, we'll fetch the current directory contents again automatically.\n        mutate((files) => files.filter((f) => f.key !== file.key), false);\n\n        deleteFiles(uuid, directory, [file.name]).catch((error) => {\n            mutate();\n            clearAndAddHttpError({ key: 'files', error });\n        });\n    };\n\n    const doCopy = () => {\n        setShowSpinner(true);\n        clearFlashes('files');\n\n        copyFile(uuid, join(directory, file.name))\n            .then(() => mutate())\n            .catch((error) => clearAndAddHttpError({ key: 'files', error }))\n            .then(() => setShowSpinner(false));\n    };\n\n    const doDownload = () => {\n        setShowSpinner(true);\n        clearFlashes('files');\n\n        getFileDownloadUrl(uuid, join(directory, file.name))\n            .then((url) => {\n                // @ts-expect-error this is valid\n                window.location = url;\n            })\n            .catch((error) => clearAndAddHttpError({ key: 'files', error }))\n            .then(() => setShowSpinner(false));\n    };\n\n    const doArchive = () => {\n        setShowSpinner(true);\n        clearFlashes('files');\n\n        compressFiles(uuid, directory, [file.name])\n            .then(() => mutate())\n            .catch((error) => clearAndAddHttpError({ key: 'files', error }))\n            .then(() => setShowSpinner(false));\n    };\n\n    const doUnarchive = () => {\n        setShowSpinner(true);\n        clearFlashes('files');\n\n        decompressFiles(uuid, directory, file.name)\n            .then(() => mutate())\n            .catch((error) => clearAndAddHttpError({ key: 'files', error }))\n            .then(() => setShowSpinner(false));\n    };\n\n    return (\n        <>\n            <Dialog.Confirm\n                open={showConfirmation}\n                onClose={() => setShowConfirmation(false)}\n                title={`删除 ${file.isFile ? '文件' : '目录'}`}\n                confirm={'删除'}\n                onConfirmed={doDeletion}\n            >\n                一旦删除，您将永远无法恢复&nbsp;\n                <span className={'font-semibold text-gray-50'}>{file.name}</span> ，你确定要这样吗？\n            </Dialog.Confirm>\n            <DropdownMenu\n                ref={onClickRef}\n                renderToggle={(onClick) => (\n                    <div css={tw`px-4 py-2 hover:text-white`} onClick={onClick}>\n                        <FontAwesomeIcon icon={faEllipsisH} />\n                        {modal ? (\n                            modal === 'chmod' ? (\n                                <ChmodFileModal\n                                    visible\n                                    appear\n                                    files={[{ file: file.name, mode: file.modeBits }]}\n                                    onDismissed={() => setModal(null)}\n                                />\n                            ) : (\n                                <RenameFileModal\n                                    visible\n                                    appear\n                                    files={[file.name]}\n                                    useMoveTerminology={modal === 'move'}\n                                    onDismissed={() => setModal(null)}\n                                />\n                            )\n                        ) : null}\n                        <SpinnerOverlay visible={showSpinner} fixed size={'large'} />\n                    </div>\n                )}\n            >\n                <Can action={'file.update'}>\n                    <Row onClick={() => setModal('rename')} icon={faPencilAlt} title={'重命名'} />\n                    <Row onClick={() => setModal('move')} icon={faLevelUpAlt} title={'移动'} />\n                    <Row onClick={() => setModal('chmod')} icon={faFileCode} title={'权限'} />\n                </Can>\n                {file.isFile && (\n                    <Can action={'file.create'}>\n                        <Row onClick={doCopy} icon={faCopy} title={'复制'} />\n                    </Can>\n                )}\n                {file.isArchiveType() ? (\n                    <Can action={'file.create'}>\n                        <Row onClick={doUnarchive} icon={faBoxOpen} title={'解压'} />\n                    </Can>\n                ) : (\n                    <Can action={'file.archive'}>\n                        <Row onClick={doArchive} icon={faFileArchive} title={'压缩'} />\n                    </Can>\n                )}\n                {file.isFile && <Row onClick={doDownload} icon={faFileDownload} title={'下载'} />}\n                <Can action={'file.delete'}>\n                    <Row onClick={() => setShowConfirmation(true)} icon={faTrashAlt} title={'删除'} $danger />\n                </Can>\n            </DropdownMenu>\n        </>\n    );\n};\n\nexport default memo(FileDropdownMenu, isEqual);\n"
  },
  {
    "path": "resources/scripts/components/server/files/FileEditContainer.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport getFileContents from '@/api/server/files/getFileContents';\nimport { httpErrorToHuman } from '@/api/http';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport saveFileContents from '@/api/server/files/saveFileContents';\nimport FileManagerBreadcrumbs from '@/components/server/files/FileManagerBreadcrumbs';\nimport { useHistory, useLocation, useParams } from 'react-router';\nimport FileNameModal from '@/components/server/files/FileNameModal';\nimport Can from '@/components/elements/Can';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport PageContentBlock from '@/components/elements/PageContentBlock';\nimport { ServerError } from '@/components/elements/ScreenBlock';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport Select from '@/components/elements/Select';\nimport modes from '@/modes';\nimport useFlash from '@/plugins/useFlash';\nimport { ServerContext } from '@/state/server';\nimport ErrorBoundary from '@/components/elements/ErrorBoundary';\nimport { encodePathSegments, hashToPath } from '@/helpers';\nimport { dirname } from 'pathe';\nimport CodemirrorEditor from '@/components/elements/CodemirrorEditor';\n\nexport default () => {\n    const [error, setError] = useState('');\n    const { action } = useParams<{ action: 'new' | string }>();\n    const [loading, setLoading] = useState(action === 'edit');\n    const [content, setContent] = useState('');\n    const [modalVisible, setModalVisible] = useState(false);\n    const [mode, setMode] = useState('text/plain');\n\n    const history = useHistory();\n    const { hash } = useLocation();\n\n    const id = ServerContext.useStoreState((state) => state.server.data!.id);\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const setDirectory = ServerContext.useStoreActions((actions) => actions.files.setDirectory);\n    const { addError, clearFlashes } = useFlash();\n\n    let fetchFileContent: null | (() => Promise<string>) = null;\n\n    useEffect(() => {\n        if (action === 'new') return;\n\n        setError('');\n        setLoading(true);\n        const path = hashToPath(hash);\n        setDirectory(dirname(path));\n        getFileContents(uuid, path)\n            .then(setContent)\n            .catch((error) => {\n                console.error(error);\n                setError(httpErrorToHuman(error));\n            })\n            .then(() => setLoading(false));\n    }, [action, uuid, hash]);\n\n    const save = (name?: string) => {\n        if (!fetchFileContent) {\n            return;\n        }\n\n        setLoading(true);\n        clearFlashes('files:view');\n        fetchFileContent()\n            .then((content) => saveFileContents(uuid, name || hashToPath(hash), content))\n            .then(() => {\n                if (name) {\n                    history.push(`/server/${id}/files/edit#/${encodePathSegments(name)}`);\n                    return;\n                }\n\n                return Promise.resolve();\n            })\n            .catch((error) => {\n                console.error(error);\n                addError({ message: httpErrorToHuman(error), key: 'files:view' });\n            })\n            .then(() => setLoading(false));\n    };\n\n    if (error) {\n        return <ServerError message={error} onBack={() => history.goBack()} />;\n    }\n\n    return (\n        <PageContentBlock>\n            <FlashMessageRender byKey={'files:view'} css={tw`mb-4`} />\n            <ErrorBoundary>\n                <div css={tw`mb-4`}>\n                    <FileManagerBreadcrumbs withinFileEditor isNewFile={action !== 'edit'} />\n                </div>\n            </ErrorBoundary>\n            {hash.replace(/^#/, '').endsWith('.pteroignore') && (\n                <div css={tw`mb-4 p-4 border-l-4 bg-neutral-900 rounded border-cyan-400`}>\n                    <p css={tw`text-neutral-300 text-sm`}>\n                        你正在编辑一个 <code css={tw`font-mono bg-black rounded py-px px-1`}>.pteroignore</code> 文件.\n                        此处列出的任何文件或目录都将从备份中排除。通配符支持 使用星号 (\n                        <code css={tw`font-mono bg-black rounded py-px px-1`}>*</code>).\n                        你可以通过在前面加上感叹号来否定先前的规则 (\n                        <code css={tw`font-mono bg-black rounded py-px px-1`}>!</code>).\n                    </p>\n                </div>\n            )}\n            <FileNameModal\n                visible={modalVisible}\n                onDismissed={() => setModalVisible(false)}\n                onFileNamed={(name) => {\n                    setModalVisible(false);\n                    save(name);\n                }}\n            />\n            <div css={tw`relative`}>\n                <SpinnerOverlay visible={loading} />\n                <CodemirrorEditor\n                    mode={mode}\n                    filename={hash.replace(/^#/, '')}\n                    onModeChanged={setMode}\n                    initialContent={content}\n                    fetchContent={(value) => {\n                        fetchFileContent = value;\n                    }}\n                    onContentSaved={() => {\n                        if (action !== 'edit') {\n                            setModalVisible(true);\n                        } else {\n                            save();\n                        }\n                    }}\n                />\n            </div>\n            <div css={tw`flex justify-end mt-4`}>\n                <div css={tw`flex-1 sm:flex-none rounded bg-neutral-900 mr-4`}>\n                    <Select value={mode} onChange={(e) => setMode(e.currentTarget.value)}>\n                        {modes.map((mode) => (\n                            <option key={`${mode.name}_${mode.mime}`} value={mode.mime}>\n                                {mode.name}\n                            </option>\n                        ))}\n                    </Select>\n                </div>\n                {action === 'edit' ? (\n                    <Can action={'file.update'}>\n                        <Button css={tw`flex-1 sm:flex-none`} onClick={() => save()}>\n                            保存内容\n                        </Button>\n                    </Can>\n                ) : (\n                    <Can action={'file.create'}>\n                        <Button css={tw`flex-1 sm:flex-none`} onClick={() => setModalVisible(true)}>\n                            创建文件\n                        </Button>\n                    </Can>\n                )}\n            </div>\n        </PageContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/files/FileManagerBreadcrumbs.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { ServerContext } from '@/state/server';\nimport { NavLink, useLocation } from 'react-router-dom';\nimport { encodePathSegments, hashToPath } from '@/helpers';\nimport tw from 'twin.macro';\n\ninterface Props {\n    renderLeft?: JSX.Element;\n    withinFileEditor?: boolean;\n    isNewFile?: boolean;\n}\n\nexport default ({ renderLeft, withinFileEditor, isNewFile }: Props) => {\n    const [file, setFile] = useState<string | null>(null);\n    const id = ServerContext.useStoreState((state) => state.server.data!.id);\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n    const { hash } = useLocation();\n\n    useEffect(() => {\n        const path = hashToPath(hash);\n\n        if (withinFileEditor && !isNewFile) {\n            const name = path.split('/').pop() || null;\n            setFile(name);\n        }\n    }, [withinFileEditor, isNewFile, hash]);\n\n    const breadcrumbs = (): { name: string; path?: string }[] =>\n        directory\n            .split('/')\n            .filter((directory) => !!directory)\n            .map((directory, index, dirs) => {\n                if (!withinFileEditor && index === dirs.length - 1) {\n                    return { name: directory };\n                }\n\n                return { name: directory, path: `/${dirs.slice(0, index + 1).join('/')}` };\n            });\n\n    return (\n        <div css={tw`flex flex-grow-0 items-center text-sm text-neutral-500 overflow-x-hidden`}>\n            {renderLeft || <div css={tw`w-12`} />}/<span css={tw`px-1 text-neutral-300`}>home</span>/\n            <NavLink to={`/server/${id}/files`} css={tw`px-1 text-neutral-200 no-underline hover:text-neutral-100`}>\n                container\n            </NavLink>\n            /\n            {breadcrumbs().map((crumb, index) =>\n                crumb.path ? (\n                    <React.Fragment key={index}>\n                        <NavLink\n                            to={`/server/${id}/files#${encodePathSegments(crumb.path)}`}\n                            css={tw`px-1 text-neutral-200 no-underline hover:text-neutral-100`}\n                        >\n                            {crumb.name}\n                        </NavLink>\n                        /\n                    </React.Fragment>\n                ) : (\n                    <span key={index} css={tw`px-1 text-neutral-300`}>\n                        {crumb.name}\n                    </span>\n                )\n            )}\n            {file && (\n                <React.Fragment>\n                    <span css={tw`px-1 text-neutral-300`}>{file}</span>\n                </React.Fragment>\n            )}\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/files/FileManagerContainer.tsx",
    "content": "import React, { useEffect } from 'react';\nimport { httpErrorToHuman } from '@/api/http';\nimport { CSSTransition } from 'react-transition-group';\nimport Spinner from '@/components/elements/Spinner';\nimport FileObjectRow from '@/components/server/files/FileObjectRow';\nimport FileManagerBreadcrumbs from '@/components/server/files/FileManagerBreadcrumbs';\nimport { FileObject } from '@/api/server/files/loadDirectory';\nimport NewDirectoryButton from '@/components/server/files/NewDirectoryButton';\nimport { NavLink, useLocation } from 'react-router-dom';\nimport Can from '@/components/elements/Can';\nimport { ServerError } from '@/components/elements/ScreenBlock';\nimport tw from 'twin.macro';\nimport { Button } from '@/components/elements/button/index';\nimport { ServerContext } from '@/state/server';\nimport useFileManagerSwr from '@/plugins/useFileManagerSwr';\nimport FileManagerStatus from '@/components/server/files/FileManagerStatus';\nimport MassActionsBar from '@/components/server/files/MassActionsBar';\nimport UploadButton from '@/components/server/files/UploadButton';\nimport ServerContentBlock from '@/components/elements/ServerContentBlock';\nimport { useStoreActions } from '@/state/hooks';\nimport ErrorBoundary from '@/components/elements/ErrorBoundary';\nimport { FileActionCheckbox } from '@/components/server/files/SelectFileCheckbox';\nimport { hashToPath } from '@/helpers';\nimport style from './style.module.css';\n\nconst sortFiles = (files: FileObject[]): FileObject[] => {\n    const sortedFiles: FileObject[] = files\n        .sort((a, b) => a.name.localeCompare(b.name))\n        .sort((a, b) => (a.isFile === b.isFile ? 0 : a.isFile ? 1 : -1));\n    return sortedFiles.filter((file, index) => index === 0 || file.name !== sortedFiles[index - 1].name);\n};\n\nexport default () => {\n    const id = ServerContext.useStoreState((state) => state.server.data!.id);\n    const { hash } = useLocation();\n    const { data: files, error, mutate } = useFileManagerSwr();\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n    const clearFlashes = useStoreActions((actions) => actions.flashes.clearFlashes);\n    const setDirectory = ServerContext.useStoreActions((actions) => actions.files.setDirectory);\n\n    const setSelectedFiles = ServerContext.useStoreActions((actions) => actions.files.setSelectedFiles);\n    const selectedFilesLength = ServerContext.useStoreState((state) => state.files.selectedFiles.length);\n\n    useEffect(() => {\n        clearFlashes('files');\n        setSelectedFiles([]);\n        setDirectory(hashToPath(hash));\n    }, [hash]);\n\n    useEffect(() => {\n        mutate();\n    }, [directory]);\n\n    const onSelectAllClick = (e: React.ChangeEvent<HTMLInputElement>) => {\n        setSelectedFiles(e.currentTarget.checked ? files?.map((file) => file.name) || [] : []);\n    };\n\n    if (error) {\n        return <ServerError message={httpErrorToHuman(error)} onRetry={() => mutate()} />;\n    }\n\n    return (\n        <ServerContentBlock title={'文件管理器'} showFlashKey={'files'}>\n            <ErrorBoundary>\n                <div className={'flex flex-wrap-reverse md:flex-nowrap mb-4'}>\n                    <FileManagerBreadcrumbs\n                        renderLeft={\n                            <FileActionCheckbox\n                                type={'checkbox'}\n                                css={tw`mx-4`}\n                                checked={selectedFilesLength === (files?.length === 0 ? -1 : files?.length)}\n                                onChange={onSelectAllClick}\n                            />\n                        }\n                    />\n                    <Can action={'file.create'}>\n                        <div className={style.manager_actions}>\n                            <FileManagerStatus />\n                            <NewDirectoryButton />\n                            <UploadButton />\n                            <NavLink to={`/server/${id}/files/new${window.location.hash}`}>\n                                <Button>新文件</Button>\n                            </NavLink>\n                        </div>\n                    </Can>\n                </div>\n            </ErrorBoundary>\n            {!files ? (\n                <Spinner size={'large'} centered />\n            ) : (\n                <>\n                    {!files.length ? (\n                        <p css={tw`text-sm text-neutral-400 text-center`}>此目录为空.</p>\n                    ) : (\n                        <CSSTransition classNames={'fade'} timeout={150} appear in>\n                            <div>\n                                {files.length > 250 && (\n                                    <div css={tw`rounded bg-yellow-400 mb-px p-3`}>\n                                        <p css={tw`text-yellow-900 text-sm text-center`}>\n                                            此目录太大，无法在浏览器中显示， 将输出限制为前 250 个文件。\n                                        </p>\n                                    </div>\n                                )}\n                                {sortFiles(files.slice(0, 250)).map((file) => (\n                                    <FileObjectRow key={file.key} file={file} />\n                                ))}\n                                <MassActionsBar />\n                            </div>\n                        </CSSTransition>\n                    )}\n                </>\n            )}\n        </ServerContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/files/FileManagerStatus.tsx",
    "content": "import React, { useContext, useEffect } from 'react';\nimport { ServerContext } from '@/state/server';\nimport { CloudUploadIcon, XIcon } from '@heroicons/react/solid';\nimport asDialog from '@/hoc/asDialog';\nimport { Dialog, DialogWrapperContext } from '@/components/elements/dialog';\nimport { Button } from '@/components/elements/button/index';\nimport Tooltip from '@/components/elements/tooltip/Tooltip';\nimport Code from '@/components/elements/Code';\nimport { useSignal } from '@preact/signals-react';\n\nconst svgProps = {\n    cx: 16,\n    cy: 16,\n    r: 14,\n    strokeWidth: 3,\n    fill: 'none',\n    stroke: 'currentColor',\n};\n\nconst Spinner = ({ progress, className }: { progress: number; className?: string }) => (\n    <svg viewBox={'0 0 32 32'} className={className}>\n        <circle {...svgProps} className={'opacity-25'} />\n        <circle\n            {...svgProps}\n            stroke={'white'}\n            strokeDasharray={28 * Math.PI}\n            className={'rotate-[-90deg] origin-[50%_50%] transition-[stroke-dashoffset] duration-300'}\n            style={{ strokeDashoffset: ((100 - progress) / 100) * 28 * Math.PI }}\n        />\n    </svg>\n);\n\nconst FileUploadList = () => {\n    const { close } = useContext(DialogWrapperContext);\n    const cancelFileUpload = ServerContext.useStoreActions((actions) => actions.files.cancelFileUpload);\n    const clearFileUploads = ServerContext.useStoreActions((actions) => actions.files.clearFileUploads);\n    const uploads = ServerContext.useStoreState((state) =>\n        Object.entries(state.files.uploads).sort(([a], [b]) => a.localeCompare(b))\n    );\n\n    return (\n        <div className={'space-y-2 mt-6'}>\n            {uploads.map(([name, file]) => (\n                <div key={name} className={'flex items-center space-x-3 bg-gray-700 p-3 rounded'}>\n                    <Tooltip content={`${Math.floor((file.loaded / file.total) * 100)}%`} placement={'left'}>\n                        <div className={'flex-shrink-0'}>\n                            <Spinner progress={(file.loaded / file.total) * 100} className={'w-6 h-6'} />\n                        </div>\n                    </Tooltip>\n                    <Code className={'flex-1 truncate'}>{name}</Code>\n                    <button\n                        onClick={cancelFileUpload.bind(this, name)}\n                        className={'text-gray-500 hover:text-gray-200 transition-colors duration-75'}\n                    >\n                        <XIcon className={'w-5 h-5'} />\n                    </button>\n                </div>\n            ))}\n            <Dialog.Footer>\n                <Button.Danger variant={Button.Variants.Secondary} onClick={() => clearFileUploads()}>\n                    取消上传\n                </Button.Danger>\n                <Button.Text onClick={close}>关闭</Button.Text>\n            </Dialog.Footer>\n        </div>\n    );\n};\n\nconst FileUploadListDialog = asDialog({\n    title: '文件上传',\n    description: '正在将以下文件上传到您的服务器。',\n})(FileUploadList);\n\nexport default () => {\n    const open = useSignal(false);\n\n    const count = ServerContext.useStoreState((state) => Object.keys(state.files.uploads).length);\n    const progress = ServerContext.useStoreState((state) => ({\n        uploaded: Object.values(state.files.uploads).reduce((count, file) => count + file.loaded, 0),\n        total: Object.values(state.files.uploads).reduce((count, file) => count + file.total, 0),\n    }));\n\n    useEffect(() => {\n        if (count === 0) {\n            open.value = false;\n        }\n    }, [count]);\n\n    return (\n        <>\n            {count > 0 && (\n                <Tooltip content={`${count} 个文件正在上传，点击查看`}>\n                    <button\n                        className={'flex items-center justify-center w-10 h-10'}\n                        onClick={() => (open.value = true)}\n                    >\n                        <Spinner progress={(progress.uploaded / progress.total) * 100} className={'w-8 h-8'} />\n                        <CloudUploadIcon className={'h-3 absolute mx-auto animate-pulse'} />\n                    </button>\n                </Tooltip>\n            )}\n            <FileUploadListDialog open={open.value} onClose={() => (open.value = false)} />\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/files/FileNameModal.tsx",
    "content": "import React from 'react';\nimport Modal, { RequiredModalProps } from '@/components/elements/Modal';\nimport { Form, Formik, FormikHelpers } from 'formik';\nimport { object, string } from 'yup';\nimport Field from '@/components/elements/Field';\nimport { ServerContext } from '@/state/server';\nimport { join } from 'pathe';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\n\ntype Props = RequiredModalProps & {\n    onFileNamed: (name: string) => void;\n};\n\ninterface Values {\n    fileName: string;\n}\n\nexport default ({ onFileNamed, onDismissed, ...props }: Props) => {\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n\n    const submit = (values: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        onFileNamed(join(directory, values.fileName));\n        setSubmitting(false);\n    };\n\n    return (\n        <Formik\n            onSubmit={submit}\n            initialValues={{ fileName: '' }}\n            validationSchema={object().shape({\n                fileName: string().required().min(1),\n            })}\n        >\n            {({ resetForm }) => (\n                <Modal\n                    onDismissed={() => {\n                        resetForm();\n                        onDismissed();\n                    }}\n                    {...props}\n                >\n                    <Form>\n                        <Field\n                            id={'fileName'}\n                            name={'fileName'}\n                            label={'文件名'}\n                            description={'请输入此文件的文件名.'}\n                            autoFocus\n                        />\n                        <div css={tw`mt-6 text-right`}>\n                            <Button>创建文件</Button>\n                        </div>\n                    </Form>\n                </Modal>\n            )}\n        </Formik>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/files/FileObjectRow.tsx",
    "content": "import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faFileAlt, faFileArchive, faFileImport, faFolder } from '@fortawesome/free-solid-svg-icons';\nimport { encodePathSegments } from '@/helpers';\nimport { differenceInHours, format, formatDistanceToNow } from 'date-fns';\nimport { zhCN } from 'date-fns/locale';\nimport React, { memo } from 'react';\nimport { FileObject } from '@/api/server/files/loadDirectory';\nimport FileDropdownMenu from '@/components/server/files/FileDropdownMenu';\nimport { ServerContext } from '@/state/server';\nimport { NavLink, useRouteMatch } from 'react-router-dom';\nimport tw from 'twin.macro';\nimport isEqual from 'react-fast-compare';\nimport SelectFileCheckbox from '@/components/server/files/SelectFileCheckbox';\nimport { usePermissions } from '@/plugins/usePermissions';\nimport { join } from 'pathe';\nimport { bytesToString } from '@/lib/formatters';\nimport styles from './style.module.css';\n\nconst Clickable: React.FC<{ file: FileObject }> = memo(({ file, children }) => {\n    const [canRead] = usePermissions(['file.read']);\n    const [canReadContents] = usePermissions(['file.read-content']);\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n\n    const match = useRouteMatch();\n\n    return (file.isFile && (!file.isEditable() || !canReadContents)) || (!file.isFile && !canRead) ? (\n        <div className={styles.details}>{children}</div>\n    ) : (\n        <NavLink\n            className={styles.details}\n            to={`${match.url}${file.isFile ? '/edit' : ''}#${encodePathSegments(join(directory, file.name))}`}\n        >\n            {children}\n        </NavLink>\n    );\n}, isEqual);\n\nconst FileObjectRow = ({ file }: { file: FileObject }) => (\n    <div\n        className={styles.file_row}\n        key={file.name}\n        onContextMenu={(e) => {\n            e.preventDefault();\n            window.dispatchEvent(new CustomEvent(`pterodactyl:files:ctx:${file.key}`, { detail: e.clientX }));\n        }}\n    >\n        <SelectFileCheckbox name={file.name} />\n        <Clickable file={file}>\n            <div css={tw`flex-none text-neutral-400 ml-6 mr-4 text-lg pl-3`}>\n                {file.isFile ? (\n                    <FontAwesomeIcon\n                        icon={file.isSymlink ? faFileImport : file.isArchiveType() ? faFileArchive : faFileAlt}\n                    />\n                ) : (\n                    <FontAwesomeIcon icon={faFolder} />\n                )}\n            </div>\n            <div css={tw`flex-1 truncate`}>{file.name}</div>\n            {file.isFile && <div css={tw`w-1/6 text-right mr-4 hidden sm:block`}>{bytesToString(file.size)}</div>}\n            <div css={tw`w-1/5 text-right mr-4 hidden md:block`} title={file.modifiedAt.toString()}>\n                {Math.abs(differenceInHours(file.modifiedAt, new Date())) > 48\n                    ? format(file.modifiedAt, 'yyyy年M月d日 HH:mm')\n                    : formatDistanceToNow(file.modifiedAt, { addSuffix: true, locale: zhCN })}\n            </div>\n        </Clickable>\n        <FileDropdownMenu file={file} />\n    </div>\n);\n\nexport default memo(FileObjectRow, (prevProps, nextProps) => {\n    /* eslint-disable @typescript-eslint/no-unused-vars */\n    const { isArchiveType, isEditable, ...prevFile } = prevProps.file;\n    const { isArchiveType: nextIsArchiveType, isEditable: nextIsEditable, ...nextFile } = nextProps.file;\n    /* eslint-enable @typescript-eslint/no-unused-vars */\n\n    return isEqual(prevFile, nextFile);\n});\n"
  },
  {
    "path": "resources/scripts/components/server/files/MassActionsBar.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport tw from 'twin.macro';\nimport { Button } from '@/components/elements/button/index';\nimport Fade from '@/components/elements/Fade';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport useFileManagerSwr from '@/plugins/useFileManagerSwr';\nimport useFlash from '@/plugins/useFlash';\nimport compressFiles from '@/api/server/files/compressFiles';\nimport { ServerContext } from '@/state/server';\nimport deleteFiles from '@/api/server/files/deleteFiles';\nimport RenameFileModal from '@/components/server/files/RenameFileModal';\nimport Portal from '@/components/elements/Portal';\nimport { Dialog } from '@/components/elements/dialog';\n\nconst MassActionsBar = () => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n\n    const { mutate } = useFileManagerSwr();\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const [loading, setLoading] = useState(false);\n    const [loadingMessage, setLoadingMessage] = useState('');\n    const [showConfirm, setShowConfirm] = useState(false);\n    const [showMove, setShowMove] = useState(false);\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n\n    const selectedFiles = ServerContext.useStoreState((state) => state.files.selectedFiles);\n    const setSelectedFiles = ServerContext.useStoreActions((actions) => actions.files.setSelectedFiles);\n\n    useEffect(() => {\n        if (!loading) setLoadingMessage('');\n    }, [loading]);\n\n    const onClickCompress = () => {\n        setLoading(true);\n        clearFlashes('files');\n        setLoadingMessage('正在压缩文件...');\n\n        compressFiles(uuid, directory, selectedFiles)\n            .then(() => mutate())\n            .then(() => setSelectedFiles([]))\n            .catch((error) => clearAndAddHttpError({ key: 'files', error }))\n            .then(() => setLoading(false));\n    };\n\n    const onClickConfirmDeletion = () => {\n        setLoading(true);\n        setShowConfirm(false);\n        clearFlashes('files');\n        setLoadingMessage('正在删除文件...');\n\n        deleteFiles(uuid, directory, selectedFiles)\n            .then(() => {\n                mutate((files) => files.filter((f) => selectedFiles.indexOf(f.name) < 0), false);\n                setSelectedFiles([]);\n            })\n            .catch((error) => {\n                mutate();\n                clearAndAddHttpError({ key: 'files', error });\n            })\n            .then(() => setLoading(false));\n    };\n\n    return (\n        <>\n            <div css={tw`pointer-events-none fixed bottom-0 z-20 left-0 right-0 flex justify-center`}>\n                <SpinnerOverlay visible={loading} size={'large'} fixed>\n                    {loadingMessage}\n                </SpinnerOverlay>\n                <Dialog.Confirm\n                    title={'删除这些文件?'}\n                    open={showConfirm}\n                    confirm={'删除'}\n                    onClose={() => setShowConfirm(false)}\n                    onConfirmed={onClickConfirmDeletion}\n                >\n                    <p className={'mb-2'}>\n                        你确定删除这些共计&nbsp;\n                        <span className={'font-semibold text-gray-50'}>{selectedFiles.length}个文件/目录</span> 吗?\n                        这是不可逆转的操作，你将没有回头路！\n                    </p>\n                    {selectedFiles.slice(0, 15).map((file) => (\n                        <li key={file}>{file}</li>\n                    ))}\n                    {selectedFiles.length > 15 && <li>和另外 {selectedFiles.length - 15} 个</li>}\n                </Dialog.Confirm>\n                {showMove && (\n                    <RenameFileModal\n                        files={selectedFiles}\n                        visible\n                        appear\n                        useMoveTerminology\n                        onDismissed={() => setShowMove(false)}\n                    />\n                )}\n                <Portal>\n                    <div className={'pointer-events-none fixed bottom-0 mb-6 flex justify-center w-full z-50'}>\n                        <Fade timeout={75} in={selectedFiles.length > 0} unmountOnExit>\n                            <div css={tw`flex items-center space-x-4 pointer-events-auto rounded p-4 bg-black/50`}>\n                                <Button onClick={() => setShowMove(true)}>移动</Button>\n                                <Button onClick={onClickCompress}>压缩</Button>\n                                <Button.Danger variant={Button.Variants.Secondary} onClick={() => setShowConfirm(true)}>\n                                    删除\n                                </Button.Danger>\n                            </div>\n                        </Fade>\n                    </div>\n                </Portal>\n            </div>\n        </>\n    );\n};\n\nexport default MassActionsBar;\n"
  },
  {
    "path": "resources/scripts/components/server/files/NewDirectoryButton.tsx",
    "content": "import React, { useContext, useEffect, useState } from 'react';\nimport { ServerContext } from '@/state/server';\nimport { Form, Formik, FormikHelpers } from 'formik';\nimport Field from '@/components/elements/Field';\nimport { join } from 'pathe';\nimport { object, string } from 'yup';\nimport createDirectory from '@/api/server/files/createDirectory';\nimport tw from 'twin.macro';\nimport { Button } from '@/components/elements/button/index';\nimport { FileObject } from '@/api/server/files/loadDirectory';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport useFileManagerSwr from '@/plugins/useFileManagerSwr';\nimport { WithClassname } from '@/components/types';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport { Dialog, DialogWrapperContext } from '@/components/elements/dialog';\nimport Code from '@/components/elements/Code';\nimport asDialog from '@/hoc/asDialog';\n\ninterface Values {\n    directoryName: string;\n}\n\nconst schema = object().shape({\n    directoryName: string().required('必须提供有效的目录名称。'),\n});\n\nconst generateDirectoryData = (name: string): FileObject => ({\n    key: `dir_${name.split('/', 1)[0] ?? name}`,\n    name: name.replace(/^(\\/*)/, '').split('/', 1)[0] ?? name,\n    mode: 'drwxr-xr-x',\n    modeBits: '0755',\n    size: 0,\n    isFile: false,\n    isSymlink: false,\n    mimetype: '',\n    createdAt: new Date(),\n    modifiedAt: new Date(),\n    isArchiveType: () => false,\n    isEditable: () => false,\n});\n\nconst NewDirectoryDialog = asDialog({\n    title: '创建目录',\n})(() => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n\n    const { mutate } = useFileManagerSwr();\n    const { close } = useContext(DialogWrapperContext);\n    const { clearAndAddHttpError } = useFlashKey('files:directory-modal');\n\n    useEffect(() => {\n        return () => {\n            clearAndAddHttpError();\n        };\n    }, []);\n\n    const submit = ({ directoryName }: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        createDirectory(uuid, directory, directoryName)\n            .then(() => mutate((data) => [...data, generateDirectoryData(directoryName)], false))\n            .then(() => close())\n            .catch((error) => {\n                setSubmitting(false);\n                clearAndAddHttpError(error);\n            });\n    };\n\n    return (\n        <Formik onSubmit={submit} validationSchema={schema} initialValues={{ directoryName: '' }}>\n            {({ submitForm, values }) => (\n                <>\n                    <FlashMessageRender key={'files:directory-modal'} />\n                    <Form css={tw`m-0`}>\n                        <Field autoFocus id={'directoryName'} name={'directoryName'} label={'名称'} />\n                        <p css={tw`mt-2 text-sm md:text-base break-all`}>\n                            <span css={tw`text-neutral-200`}>该目录将被创建为&nbsp;</span>\n                            <Code>\n                                /home/container/\n                                <span css={tw`text-cyan-200`}>\n                                    {join(directory, values.directoryName).replace(/^(\\.\\.\\/|\\/)+/, '')}\n                                </span>\n                            </Code>\n                        </p>\n                    </Form>\n                    <Dialog.Footer>\n                        <Button.Text className={'w-full sm:w-auto'} onClick={close}>\n                            取消\n                        </Button.Text>\n                        <Button className={'w-full sm:w-auto'} onClick={submitForm}>\n                            创建\n                        </Button>\n                    </Dialog.Footer>\n                </>\n            )}\n        </Formik>\n    );\n});\n\nexport default ({ className }: WithClassname) => {\n    const [open, setOpen] = useState(false);\n\n    return (\n        <>\n            <NewDirectoryDialog open={open} onClose={setOpen.bind(this, false)} />\n            <Button.Text onClick={setOpen.bind(this, true)} className={className}>\n                创建目录\n            </Button.Text>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/files/RenameFileModal.tsx",
    "content": "import React from 'react';\nimport Modal, { RequiredModalProps } from '@/components/elements/Modal';\nimport { Form, Formik, FormikHelpers } from 'formik';\nimport Field from '@/components/elements/Field';\nimport { join } from 'pathe';\nimport renameFiles from '@/api/server/files/renameFiles';\nimport { ServerContext } from '@/state/server';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport useFileManagerSwr from '@/plugins/useFileManagerSwr';\nimport useFlash from '@/plugins/useFlash';\n\ninterface FormikValues {\n    name: string;\n}\n\ntype OwnProps = RequiredModalProps & { files: string[]; useMoveTerminology?: boolean };\n\nconst RenameFileModal = ({ files, useMoveTerminology, ...props }: OwnProps) => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const { mutate } = useFileManagerSwr();\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n    const setSelectedFiles = ServerContext.useStoreActions((actions) => actions.files.setSelectedFiles);\n\n    const submit = ({ name }: FormikValues, { setSubmitting }: FormikHelpers<FormikValues>) => {\n        clearFlashes('files');\n\n        const len = name.split('/').length;\n        if (files.length === 1) {\n            if (!useMoveTerminology && len === 1) {\n                // Rename the file within this directory.\n                mutate((data) => data.map((f) => (f.name === files[0] ? { ...f, name } : f)), false);\n            } else if (useMoveTerminology || len > 1) {\n                // Remove the file from this directory since they moved it elsewhere.\n                mutate((data) => data.filter((f) => f.name !== files[0]), false);\n            }\n        }\n\n        let data;\n        if (useMoveTerminology && files.length > 1) {\n            data = files.map((f) => ({ from: f, to: join(name, f) }));\n        } else {\n            data = files.map((f) => ({ from: f, to: name }));\n        }\n\n        renameFiles(uuid, directory, data)\n            .then((): Promise<any> => (files.length > 0 ? mutate() : Promise.resolve()))\n            .then(() => setSelectedFiles([]))\n            .catch((error) => {\n                mutate();\n                setSubmitting(false);\n                clearAndAddHttpError({ key: 'files', error });\n            })\n            .then(() => props.onDismissed());\n    };\n\n    return (\n        <Formik onSubmit={submit} initialValues={{ name: files.length > 1 ? '' : files[0] || '' }}>\n            {({ isSubmitting, values }) => (\n                <Modal {...props} dismissable={!isSubmitting} showSpinnerOverlay={isSubmitting}>\n                    <Form css={tw`m-0`}>\n                        <div css={[tw`flex flex-wrap`, useMoveTerminology ? tw`items-center` : tw`items-end`]}>\n                            <div css={tw`w-full sm:flex-1 sm:mr-4`}>\n                                <Field\n                                    type={'string'}\n                                    id={'file_name'}\n                                    name={'name'}\n                                    label={'文件名'}\n                                    description={\n                                        useMoveTerminology\n                                            ? '输入此文件或文件夹的新名称和目录，相对于当前目录.'\n                                            : undefined\n                                    }\n                                    autoFocus\n                                />\n                            </div>\n                            <div css={tw`w-full sm:w-auto mt-4 sm:mt-0`}>\n                                <Button css={tw`w-full`}>{useMoveTerminology ? '移动' : '重命名'}</Button>\n                            </div>\n                        </div>\n                        {useMoveTerminology && (\n                            <p css={tw`text-xs mt-2 text-neutral-400`}>\n                                <strong css={tw`text-neutral-200`}>新位置:</strong>\n                                &nbsp;/home/container/{join(directory, values.name).replace(/^(\\.\\.\\/|\\/)+/, '')}\n                            </p>\n                        )}\n                    </Form>\n                </Modal>\n            )}\n        </Formik>\n    );\n};\n\nexport default RenameFileModal;\n"
  },
  {
    "path": "resources/scripts/components/server/files/SelectFileCheckbox.tsx",
    "content": "import React from 'react';\nimport tw from 'twin.macro';\nimport { ServerContext } from '@/state/server';\nimport styled from 'styled-components/macro';\nimport Input from '@/components/elements/Input';\n\nexport const FileActionCheckbox = styled(Input)`\n    && {\n        ${tw`border-neutral-500 bg-transparent`};\n\n        &:not(:checked) {\n            ${tw`hover:border-neutral-300`};\n        }\n    }\n`;\n\nexport default ({ name }: { name: string }) => {\n    const isChecked = ServerContext.useStoreState((state) => state.files.selectedFiles.indexOf(name) >= 0);\n    const appendSelectedFile = ServerContext.useStoreActions((actions) => actions.files.appendSelectedFile);\n    const removeSelectedFile = ServerContext.useStoreActions((actions) => actions.files.removeSelectedFile);\n\n    return (\n        <label css={tw`flex-none px-4 py-2 absolute self-center z-30 cursor-pointer`}>\n            <FileActionCheckbox\n                name={'selectedFiles'}\n                value={name}\n                checked={isChecked}\n                type={'checkbox'}\n                onChange={(e: React.ChangeEvent<HTMLInputElement>) => {\n                    if (e.currentTarget.checked) {\n                        appendSelectedFile(name);\n                    } else {\n                        removeSelectedFile(name);\n                    }\n                }}\n            />\n        </label>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/files/UploadButton.tsx",
    "content": "import axios, { AxiosProgressEvent } from 'axios';\nimport getFileUploadUrl from '@/api/server/files/getFileUploadUrl';\nimport tw from 'twin.macro';\nimport { Button } from '@/components/elements/button/index';\nimport React, { useEffect, useRef } from 'react';\nimport { ModalMask } from '@/components/elements/Modal';\nimport Fade from '@/components/elements/Fade';\nimport useEventListener from '@/plugins/useEventListener';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport useFileManagerSwr from '@/plugins/useFileManagerSwr';\nimport { ServerContext } from '@/state/server';\nimport { WithClassname } from '@/components/types';\nimport Portal from '@/components/elements/Portal';\nimport { CloudUploadIcon } from '@heroicons/react/outline';\nimport { useSignal } from '@preact/signals-react';\n\nfunction isFileOrDirectory(event: DragEvent): boolean {\n    if (!event.dataTransfer?.types) {\n        return false;\n    }\n\n    return event.dataTransfer.types.some((value) => value.toLowerCase() === 'files');\n}\n\nexport default ({ className }: WithClassname) => {\n    const fileUploadInput = useRef<HTMLInputElement>(null);\n\n    const visible = useSignal(false);\n    const timeouts = useSignal<NodeJS.Timeout[]>([]);\n\n    const { mutate } = useFileManagerSwr();\n    const { addError, clearAndAddHttpError } = useFlashKey('files');\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n    const { clearFileUploads, removeFileUpload, pushFileUpload, setUploadProgress } = ServerContext.useStoreActions(\n        (actions) => actions.files\n    );\n\n    useEventListener(\n        'dragenter',\n        (e) => {\n            e.preventDefault();\n            e.stopPropagation();\n            if (isFileOrDirectory(e)) {\n                visible.value = true;\n            }\n        },\n        { capture: true }\n    );\n\n    useEventListener('dragexit', () => (visible.value = false), { capture: true });\n\n    useEventListener('keydown', () => (visible.value = false));\n\n    useEffect(() => {\n        return () => timeouts.value.forEach(clearTimeout);\n    }, []);\n\n    const onUploadProgress = (data: AxiosProgressEvent, name: string) => {\n        setUploadProgress({ name, loaded: data.loaded });\n    };\n\n    const onFileSubmission = (files: FileList) => {\n        clearAndAddHttpError();\n        const list = Array.from(files);\n        if (list.some((file) => !file.type && (!file.size || file.size === 4096))) {\n            return addError('目前不支持文件夹上传。', '错误');\n        }\n\n        const uploads = list.map((file) => {\n            const controller = new AbortController();\n            pushFileUpload({\n                name: file.name,\n                data: { abort: controller, loaded: 0, total: file.size },\n            });\n\n            return () =>\n                getFileUploadUrl(uuid).then((url) =>\n                    axios\n                        .post(\n                            url,\n                            { files: file },\n                            {\n                                signal: controller.signal,\n                                headers: { 'Content-Type': 'multipart/form-data' },\n                                params: { directory },\n                                onUploadProgress: (data) => onUploadProgress(data, file.name),\n                            }\n                        )\n                        .then(() => timeouts.value.push(setTimeout(() => removeFileUpload(file.name), 500)))\n                );\n        });\n\n        Promise.all(uploads.map((fn) => fn()))\n            .then(() => mutate())\n            .catch((error) => {\n                clearFileUploads();\n                clearAndAddHttpError(error);\n            });\n    };\n\n    return (\n        <>\n            <Portal>\n                <Fade appear in={visible.value} timeout={75} key={'upload_modal_mask'} unmountOnExit>\n                    <ModalMask\n                        onClick={() => (visible.value = false)}\n                        onDragOver={(e) => e.preventDefault()}\n                        onDrop={(e) => {\n                            e.preventDefault();\n                            e.stopPropagation();\n\n                            visible.value = false;\n                            if (!e.dataTransfer?.files.length) return;\n\n                            onFileSubmission(e.dataTransfer.files);\n                        }}\n                    >\n                        <div className={'w-full flex items-center justify-center pointer-events-none'}>\n                            <div\n                                className={\n                                    'flex items-center space-x-4 bg-black w-full ring-4 ring-blue-200 ring-opacity-60 rounded p-6 mx-10 max-w-sm'\n                                }\n                            >\n                                <CloudUploadIcon className={'w-10 h-10 flex-shrink-0'} />\n                                <p className={'font-header flex-1 text-lg text-neutral-100 text-center'}>\n                                    拖放文件以上传。\n                                </p>\n                            </div>\n                        </div>\n                    </ModalMask>\n                </Fade>\n            </Portal>\n            <input\n                type={'file'}\n                ref={fileUploadInput}\n                css={tw`hidden`}\n                onChange={(e) => {\n                    if (!e.currentTarget.files) return;\n\n                    onFileSubmission(e.currentTarget.files);\n                    if (fileUploadInput.current) {\n                        fileUploadInput.current.files = null;\n                    }\n                }}\n                multiple\n            />\n            <Button className={className} onClick={() => fileUploadInput.current && fileUploadInput.current.click()}>\n                上传\n            </Button>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/files/style.module.css",
    "content": ".manager_actions {\n    @apply grid grid-cols-2 sm:grid-cols-3 w-full gap-4 mb-4;\n\n    & button {\n        @apply w-full first:col-span-2 sm:first:col-span-1;\n    }\n\n    @screen md {\n        @apply flex flex-1 justify-end mb-0;\n\n        & button {\n            @apply w-auto;\n        }\n    }\n}\n\n.file_row {\n    @apply flex items-center cursor-pointer bg-neutral-700 rounded-sm mb-px text-sm no-underline;\n    @apply hover:text-neutral-100 hover:bg-neutral-600;\n\n    & > .details {\n        @apply flex flex-1 items-center text-neutral-300 no-underline px-4 py-2 overflow-hidden truncate;\n\n        &:not(a) {\n            @apply cursor-default;\n        }\n    }\n}\n"
  },
  {
    "path": "resources/scripts/components/server/network/AllocationRow.tsx",
    "content": "import React, { memo, useCallback, useState } from 'react';\nimport isEqual from 'react-fast-compare';\nimport tw from 'twin.macro';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faNetworkWired } from '@fortawesome/free-solid-svg-icons';\nimport InputSpinner from '@/components/elements/InputSpinner';\nimport { Textarea } from '@/components/elements/Input';\nimport Can from '@/components/elements/Can';\nimport { Button } from '@/components/elements/button/index';\nimport GreyRowBox from '@/components/elements/GreyRowBox';\nimport { Allocation } from '@/api/server/getServer';\nimport styled from 'styled-components/macro';\nimport { debounce } from 'debounce';\nimport setServerAllocationNotes from '@/api/server/network/setServerAllocationNotes';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport { ServerContext } from '@/state/server';\nimport CopyOnClick from '@/components/elements/CopyOnClick';\nimport DeleteAllocationButton from '@/components/server/network/DeleteAllocationButton';\nimport setPrimaryServerAllocation from '@/api/server/network/setPrimaryServerAllocation';\nimport getServerAllocations from '@/api/swr/getServerAllocations';\nimport { ip } from '@/lib/formatters';\nimport Code from '@/components/elements/Code';\n\nconst Label = styled.label`\n    ${tw`uppercase text-xs mt-1 text-neutral-400 block px-1 select-none transition-colors duration-150`}\n`;\n\ninterface Props {\n    allocation: Allocation;\n}\n\nconst AllocationRow = ({ allocation }: Props) => {\n    const [loading, setLoading] = useState(false);\n    const { clearFlashes, clearAndAddHttpError } = useFlashKey('server:network');\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const { mutate } = getServerAllocations();\n\n    const onNotesChanged = useCallback((id: number, notes: string) => {\n        mutate((data) => data?.map((a) => (a.id === id ? { ...a, notes } : a)), false);\n    }, []);\n\n    const setAllocationNotes = debounce((notes: string) => {\n        setLoading(true);\n        clearFlashes();\n\n        setServerAllocationNotes(uuid, allocation.id, notes)\n            .then(() => onNotesChanged(allocation.id, notes))\n            .catch((error) => clearAndAddHttpError(error))\n            .then(() => setLoading(false));\n    }, 750);\n\n    const setPrimaryAllocation = () => {\n        clearFlashes();\n        mutate((data) => data?.map((a) => ({ ...a, isDefault: a.id === allocation.id })), false);\n\n        setPrimaryServerAllocation(uuid, allocation.id).catch((error) => {\n            clearAndAddHttpError(error);\n            mutate();\n        });\n    };\n\n    return (\n        <GreyRowBox $hoverable={false} className={'flex-wrap md:flex-nowrap mt-2'}>\n            <div className={'flex items-center w-full md:w-auto'}>\n                <div className={'pl-4 pr-6 text-neutral-400'}>\n                    <FontAwesomeIcon icon={faNetworkWired} />\n                </div>\n                <div className={'mr-4 flex-1 md:w-40'}>\n                    {allocation.alias ? (\n                        <CopyOnClick text={allocation.alias}>\n                            <Code dark className={'w-40 truncate'}>\n                                {allocation.alias}\n                            </Code>\n                        </CopyOnClick>\n                    ) : (\n                        <CopyOnClick text={ip(allocation.ip)}>\n                            <Code dark>{ip(allocation.ip)}</Code>\n                        </CopyOnClick>\n                    )}\n                    <Label>{allocation.alias ? '域名' : 'IP 地址'}</Label>\n                </div>\n                <div className={'w-16 md:w-24 overflow-hidden'}>\n                    <Code dark>{allocation.port}</Code>\n                    <Label>端口</Label>\n                </div>\n            </div>\n            <div className={'mt-4 w-full md:mt-0 md:flex-1 md:w-auto'}>\n                <InputSpinner visible={loading}>\n                    <Textarea\n                        className={'bg-neutral-800 hover:border-neutral-600 border-transparent'}\n                        placeholder={'备注'}\n                        defaultValue={allocation.notes || undefined}\n                        onChange={(e) => setAllocationNotes(e.currentTarget.value)}\n                    />\n                </InputSpinner>\n            </div>\n            <div className={'flex justify-end space-x-4 mt-4 w-full md:mt-0 md:w-48'}>\n                {allocation.isDefault ? (\n                    <Button size={Button.Sizes.Small} className={'!text-gray-50 !bg-blue-600'} disabled>\n                        首选\n                    </Button>\n                ) : (\n                    <>\n                        <Can action={'allocation.delete'}>\n                            <DeleteAllocationButton allocation={allocation.id} />\n                        </Can>\n                        <Can action={'allocation.update'}>\n                            <Button.Text size={Button.Sizes.Small} onClick={setPrimaryAllocation}>\n                                设为首选\n                            </Button.Text>\n                        </Can>\n                    </>\n                )}\n            </div>\n        </GreyRowBox>\n    );\n};\n\nexport default memo(AllocationRow, isEqual);\n"
  },
  {
    "path": "resources/scripts/components/server/network/DeleteAllocationButton.tsx",
    "content": "import React, { useState } from 'react';\nimport { faTrashAlt } from '@fortawesome/free-solid-svg-icons';\nimport tw from 'twin.macro';\nimport Icon from '@/components/elements/Icon';\nimport { ServerContext } from '@/state/server';\nimport deleteServerAllocation from '@/api/server/network/deleteServerAllocation';\nimport getServerAllocations from '@/api/swr/getServerAllocations';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport { Dialog } from '@/components/elements/dialog';\nimport { Button } from '@/components/elements/button/index';\n\ninterface Props {\n    allocation: number;\n}\n\nconst DeleteAllocationButton = ({ allocation }: Props) => {\n    const [confirm, setConfirm] = useState(false);\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const setServerFromState = ServerContext.useStoreActions((actions) => actions.server.setServerFromState);\n\n    const { mutate } = getServerAllocations();\n    const { clearFlashes, clearAndAddHttpError } = useFlashKey('server:network');\n\n    const deleteAllocation = () => {\n        clearFlashes();\n\n        mutate((data) => data?.filter((a) => a.id !== allocation), false);\n        setServerFromState((s) => ({ ...s, allocations: s.allocations.filter((a) => a.id !== allocation) }));\n\n        deleteServerAllocation(uuid, allocation).catch((error) => {\n            clearAndAddHttpError(error);\n            mutate();\n        });\n    };\n\n    return (\n        <>\n            <Dialog.Confirm\n                open={confirm}\n                onClose={() => setConfirm(false)}\n                title={'删除此分配?'}\n                confirm={'删除'}\n                onConfirmed={deleteAllocation}\n            >\n                此分配将立即从您的服务器中删除。你确定你要继续吗？\n            </Dialog.Confirm>\n            <Button.Danger\n                variant={Button.Variants.Secondary}\n                size={Button.Sizes.Small}\n                shape={Button.Shapes.IconSquare}\n                type={'button'}\n                onClick={() => setConfirm(true)}\n            >\n                <Icon icon={faTrashAlt} css={tw`w-3 h-auto`} />\n            </Button.Danger>\n        </>\n    );\n};\n\nexport default DeleteAllocationButton;\n"
  },
  {
    "path": "resources/scripts/components/server/network/NetworkContainer.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport Spinner from '@/components/elements/Spinner';\nimport { useFlashKey } from '@/plugins/useFlash';\nimport ServerContentBlock from '@/components/elements/ServerContentBlock';\nimport { ServerContext } from '@/state/server';\nimport AllocationRow from '@/components/server/network/AllocationRow';\nimport Button from '@/components/elements/Button';\nimport createServerAllocation from '@/api/server/network/createServerAllocation';\nimport tw from 'twin.macro';\nimport Can from '@/components/elements/Can';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport getServerAllocations from '@/api/swr/getServerAllocations';\nimport isEqual from 'react-fast-compare';\nimport { useDeepCompareEffect } from '@/plugins/useDeepCompareEffect';\nimport { useStoreState } from 'easy-peasy';\n\nconst NetworkContainer = () => {\n    const [loading, setLoading] = useState(false);\n    const [consecutiveCount, setConsecutiveCount] = useState(1);\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const allocationLimit = ServerContext.useStoreState((state) => state.server.data!.featureLimits.allocations);\n    const allocations = ServerContext.useStoreState((state) => state.server.data!.allocations, isEqual);\n    const setServerFromState = ServerContext.useStoreActions((actions) => actions.server.setServerFromState);\n    const consecutiveEnabled = useStoreState((state) => state.settings.data?.allocations?.consecutiveEnabled ?? false);\n    const consecutiveLimit = useStoreState((state) => state.settings.data?.allocations?.consecutiveLimit ?? 3);\n\n    const { clearFlashes, clearAndAddHttpError } = useFlashKey('server:network');\n    const { data, error, mutate } = getServerAllocations();\n\n    useEffect(() => {\n        mutate(allocations);\n    }, []);\n\n    useEffect(() => {\n        clearAndAddHttpError(error);\n    }, [error]);\n\n    useDeepCompareEffect(() => {\n        if (!data) return;\n\n        setServerFromState((state) => ({ ...state, allocations: data }));\n    }, [data]);\n\n    const onCreateAllocation = () => {\n        clearFlashes();\n\n        const count = consecutiveEnabled && consecutiveCount > 1 ? consecutiveCount : undefined;\n        setLoading(true);\n        createServerAllocation(uuid, count)\n            .then((newAllocations) => {\n                setServerFromState((s) => ({ ...s, allocations: s.allocations.concat(newAllocations) }));\n                return mutate(data?.concat(newAllocations), false);\n            })\n            .catch((error) => clearAndAddHttpError(error))\n            .then(() => setLoading(false));\n    };\n\n    return (\n        <ServerContentBlock showFlashKey={'server:network'} title={'网络'}>\n            {!data ? (\n                <Spinner size={'large'} centered />\n            ) : (\n                <>\n                    {data.map((allocation) => (\n                        <AllocationRow key={`${allocation.ip}:${allocation.port}`} allocation={allocation} />\n                    ))}\n                    {allocationLimit > 0 && (\n                        <Can action={'allocation.create'}>\n                            <SpinnerOverlay visible={loading} />\n                            <div css={tw`mt-6 sm:flex items-center justify-end`}>\n                                <p css={tw`text-sm text-neutral-300 mb-4 sm:mr-6 sm:mb-0`}>\n                                    你正在使用 {data.length} / {allocationLimit} 个允许的网络设置。\n                                </p>\n                                {allocationLimit > data.length && (\n                                    <div css={tw`flex items-center space-x-3`}>\n                                        {consecutiveEnabled && (\n                                            <div css={tw`flex items-center space-x-2`}>\n                                                <label css={tw`text-sm text-neutral-300 whitespace-nowrap`}>\n                                                    连续端口数:\n                                                </label>\n                                                <input\n                                                    type={'number'}\n                                                    min={1}\n                                                    max={Math.min(consecutiveLimit, allocationLimit - data.length)}\n                                                    value={consecutiveCount}\n                                                    onChange={(e) =>\n                                                        setConsecutiveCount(\n                                                            Math.max(\n                                                                1,\n                                                                Math.min(\n                                                                    consecutiveLimit,\n                                                                    parseInt(e.target.value) || 1\n                                                                )\n                                                            )\n                                                        )\n                                                    }\n                                                    css={tw`w-16 bg-neutral-800 text-neutral-200 border border-neutral-600 rounded px-2 py-1 text-sm`}\n                                                />\n                                            </div>\n                                        )}\n                                        <Button\n                                            css={tw`w-full sm:w-auto`}\n                                            color={'primary'}\n                                            onClick={onCreateAllocation}\n                                        >\n                                            创建新的网络设置\n                                        </Button>\n                                    </div>\n                                )}\n                            </div>\n                        </Can>\n                    )}\n                </>\n            )}\n        </ServerContentBlock>\n    );\n};\n\nexport default NetworkContainer;\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/DeleteScheduleButton.tsx",
    "content": "import React, { useState } from 'react';\nimport deleteSchedule from '@/api/server/schedules/deleteSchedule';\nimport { ServerContext } from '@/state/server';\nimport { Actions, useStoreActions } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport { httpErrorToHuman } from '@/api/http';\nimport { Button } from '@/components/elements/button/index';\nimport { Dialog } from '@/components/elements/dialog';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\n\ninterface Props {\n    scheduleId: number;\n    onDeleted: () => void;\n}\n\nexport default ({ scheduleId, onDeleted }: Props) => {\n    const [visible, setVisible] = useState(false);\n    const [isLoading, setIsLoading] = useState(false);\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const { addError, clearFlashes } = useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n\n    const onDelete = () => {\n        setIsLoading(true);\n        clearFlashes('schedules');\n        deleteSchedule(uuid, scheduleId)\n            .then(() => {\n                setIsLoading(false);\n                onDeleted();\n            })\n            .catch((error) => {\n                console.error(error);\n\n                addError({ key: 'schedules', message: httpErrorToHuman(error) });\n                setIsLoading(false);\n                setVisible(false);\n            });\n    };\n\n    return (\n        <>\n            <Dialog.Confirm\n                open={visible}\n                onClose={() => setVisible(false)}\n                title={'删除计划?'}\n                confirm={'是'}\n                onConfirmed={onDelete}\n            >\n                <SpinnerOverlay visible={isLoading} />\n                确定要删除此计划吗？ 将删除所有计划下的任务和任何正在运行的进程将被终止。\n            </Dialog.Confirm>\n            <Button.Danger\n                variant={Button.Variants.Secondary}\n                className={'flex-1 sm:flex-none mr-4 border-transparent'}\n                onClick={() => setVisible(true)}\n            >\n                删除\n            </Button.Danger>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/EditScheduleModal.tsx",
    "content": "import React, { useContext, useEffect, useState } from 'react';\nimport { Schedule } from '@/api/server/schedules/getServerSchedules';\nimport Field from '@/components/elements/Field';\nimport { Form, Formik, FormikHelpers } from 'formik';\nimport FormikSwitch from '@/components/elements/FormikSwitch';\nimport createOrUpdateSchedule from '@/api/server/schedules/createOrUpdateSchedule';\nimport { ServerContext } from '@/state/server';\nimport { httpErrorToHuman } from '@/api/http';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport useFlash from '@/plugins/useFlash';\nimport tw from 'twin.macro';\nimport { Button } from '@/components/elements/button/index';\nimport ModalContext from '@/context/ModalContext';\nimport asModal from '@/hoc/asModal';\nimport Switch from '@/components/elements/Switch';\nimport ScheduleCheatsheetCards from '@/components/server/schedules/ScheduleCheatsheetCards';\nimport ScheduleSimpleForm from '@/components/server/schedules/ScheduleSimpleForm';\n\ninterface Props {\n    schedule?: Schedule;\n}\n\ninterface Values {\n    name: string;\n    dayOfWeek: string;\n    month: string;\n    dayOfMonth: string;\n    hour: string;\n    minute: string;\n    enabled: boolean;\n    onlyWhenOnline: boolean;\n}\n\nconst EditScheduleModal = ({ schedule }: Props) => {\n    const { addError, clearFlashes } = useFlash();\n    const { dismiss } = useContext(ModalContext);\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const appendSchedule = ServerContext.useStoreActions((actions) => actions.schedules.appendSchedule);\n    const [showCheatsheet, setShowCheetsheet] = useState(false);\n    const [simpleMode, setSimpleMode] = useState(() => {\n        const stored = localStorage.getItem('schedule_editor_simple_mode');\n        return stored !== null ? stored === 'true' : true;\n    });\n\n    const toggleSimpleMode = () => {\n        setSimpleMode((s) => {\n            const next = !s;\n            localStorage.setItem('schedule_editor_simple_mode', String(next));\n            return next;\n        });\n    };\n\n    useEffect(() => {\n        return () => {\n            clearFlashes('schedule:edit');\n        };\n    }, []);\n\n    const submit = (values: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        clearFlashes('schedule:edit');\n        createOrUpdateSchedule(uuid, {\n            id: schedule?.id,\n            name: values.name,\n            cron: {\n                minute: values.minute,\n                hour: values.hour,\n                dayOfWeek: values.dayOfWeek,\n                month: values.month,\n                dayOfMonth: values.dayOfMonth,\n            },\n            onlyWhenOnline: values.onlyWhenOnline,\n            isActive: values.enabled,\n        })\n            .then((schedule) => {\n                setSubmitting(false);\n                appendSchedule(schedule);\n                dismiss();\n            })\n            .catch((error) => {\n                console.error(error);\n\n                setSubmitting(false);\n                addError({ key: 'schedule:edit', message: httpErrorToHuman(error) });\n            });\n    };\n\n    return (\n        <Formik\n            onSubmit={submit}\n            initialValues={\n                {\n                    name: schedule?.name || '',\n                    minute: schedule?.cron.minute || '*/5',\n                    hour: schedule?.cron.hour || '*',\n                    dayOfMonth: schedule?.cron.dayOfMonth || '*',\n                    month: schedule?.cron.month || '*',\n                    dayOfWeek: schedule?.cron.dayOfWeek || '*',\n                    enabled: schedule?.isActive ?? true,\n                    onlyWhenOnline: schedule?.onlyWhenOnline ?? true,\n                } as Values\n            }\n        >\n            {({ isSubmitting, setFieldValue, values }) => (\n                <Form>\n                    <h3 css={tw`text-2xl mb-6`}>{schedule ? '编辑计划' : '创建新计划'}</h3>\n                    <FlashMessageRender byKey={'schedule:edit'} css={tw`mb-6`} />\n                    <Field name={'name'} label={'计划名'} description={'此计划的名字'} />\n                    {simpleMode ? (\n                        <ScheduleSimpleForm\n                            initialCron={{\n                                minute: values.minute,\n                                hour: values.hour,\n                                dayOfMonth: values.dayOfMonth,\n                                month: values.month,\n                                dayOfWeek: values.dayOfWeek,\n                            }}\n                            onChange={(v) => {\n                                setFieldValue('minute', v.minute);\n                                setFieldValue('hour', v.hour);\n                                setFieldValue('dayOfMonth', v.dayOfMonth);\n                                setFieldValue('month', v.month);\n                                setFieldValue('dayOfWeek', v.dayOfWeek);\n                            }}\n                        />\n                    ) : (\n                        <>\n                            <div css={tw`grid grid-cols-2 sm:grid-cols-5 gap-4 mt-6`}>\n                                <Field name={'minute'} label={'分钟'} />\n                                <Field name={'hour'} label={'小时'} />\n                                <Field name={'dayOfMonth'} label={'每月的某一天'} />\n                                <Field name={'month'} label={'月'} />\n                                <Field name={'dayOfWeek'} label={'每周的某一天'} />\n                            </div>\n                            <p css={tw`text-neutral-400 text-xs mt-2`}>\n                                计划系统支持在定义任务何时开始运行时使用 Cronjob\n                                语法。使用上面的字段来指定这些计划任务应该何时开始运行。\n                            </p>\n                            <div css={tw`mt-6 bg-neutral-700 border border-neutral-800 shadow-inner p-4 rounded`}>\n                                <Switch\n                                    name={'show_cheatsheet'}\n                                    description={'显示 cronjob 的一些例子'}\n                                    label={'显示例子'}\n                                    defaultChecked={showCheatsheet}\n                                    onChange={() => setShowCheetsheet((s) => !s)}\n                                />\n                                {showCheatsheet && (\n                                    <div css={tw`block md:flex w-full`}>\n                                        <ScheduleCheatsheetCards />\n                                    </div>\n                                )}\n                            </div>\n                        </>\n                    )}\n                    <div css={tw`mt-6 bg-neutral-700 border border-neutral-800 shadow-inner p-4 rounded`}>\n                        <Switch\n                            name={'simple_mode'}\n                            description={simpleMode ? '直接编辑 Cron 表达式' : '使用简单的时间选择器设置执行频率'}\n                            label={simpleMode ? '高级模式' : '简单模式'}\n                            checked={!simpleMode}\n                            onChange={toggleSimpleMode}\n                        />\n                    </div>\n                    <div css={tw`mt-6 bg-neutral-700 border border-neutral-800 shadow-inner p-4 rounded`}>\n                        <FormikSwitch\n                            name={'onlyWhenOnline'}\n                            description={'仅在服务器处于运行状态时执行此计划。'}\n                            label={'仅当服务器在线运行时'}\n                        />\n                    </div>\n                    <div css={tw`mt-6 bg-neutral-700 border border-neutral-800 shadow-inner p-4 rounded`}>\n                        <FormikSwitch\n                            name={'enabled'}\n                            description={'如果启用，此计划将自动执行。'}\n                            label={'计划已启用'}\n                        />\n                    </div>\n                    <div css={tw`mt-6 text-right`}>\n                        <Button className={'w-full sm:w-auto'} type={'submit'} disabled={isSubmitting}>\n                            {schedule ? '保存更改' : '创建计划'}\n                        </Button>\n                    </div>\n                </Form>\n            )}\n        </Formik>\n    );\n};\n\nexport default asModal<Props>()(EditScheduleModal);\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/NewTaskButton.tsx",
    "content": "import React, { useState } from 'react';\nimport { Schedule } from '@/api/server/schedules/getServerSchedules';\nimport TaskDetailsModal from '@/components/server/schedules/TaskDetailsModal';\nimport { Button } from '@/components/elements/button/index';\n\ninterface Props {\n    schedule: Schedule;\n}\n\nexport default ({ schedule }: Props) => {\n    const [visible, setVisible] = useState(false);\n\n    return (\n        <>\n            <TaskDetailsModal schedule={schedule} visible={visible} onModalDismissed={() => setVisible(false)} />\n            <Button onClick={() => setVisible(true)} className={'flex-1'}>\n                新任务\n            </Button>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/RunScheduleButton.tsx",
    "content": "import React, { useCallback, useState } from 'react';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport { Button } from '@/components/elements/button/index';\nimport triggerScheduleExecution from '@/api/server/schedules/triggerScheduleExecution';\nimport { ServerContext } from '@/state/server';\nimport useFlash from '@/plugins/useFlash';\nimport { Schedule } from '@/api/server/schedules/getServerSchedules';\n\nconst RunScheduleButton = ({ schedule }: { schedule: Schedule }) => {\n    const [loading, setLoading] = useState(false);\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n\n    const id = ServerContext.useStoreState((state) => state.server.data!.id);\n    const appendSchedule = ServerContext.useStoreActions((actions) => actions.schedules.appendSchedule);\n\n    const onTriggerExecute = useCallback(() => {\n        clearFlashes('schedule');\n        setLoading(true);\n        triggerScheduleExecution(id, schedule.id)\n            .then(() => {\n                setLoading(false);\n                appendSchedule({ ...schedule, isProcessing: true });\n            })\n            .catch((error) => {\n                console.error(error);\n                clearAndAddHttpError({ error, key: 'schedules' });\n            })\n            .then(() => setLoading(false));\n    }, []);\n\n    return (\n        <>\n            <SpinnerOverlay visible={loading} size={'large'} />\n            <Button\n                variant={Button.Variants.Secondary}\n                className={'flex-1 sm:flex-none'}\n                disabled={schedule.isProcessing}\n                onClick={onTriggerExecute}\n            >\n                立即运行\n            </Button>\n        </>\n    );\n};\n\nexport default RunScheduleButton;\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/ScheduleCheatsheetCards.tsx",
    "content": "import React from 'react';\nimport tw from 'twin.macro';\n\nexport default () => {\n    return (\n        <>\n            <div css={tw`md:w-1/2 h-full bg-neutral-600`}>\n                <div css={tw`flex flex-col`}>\n                    <h2 css={tw`py-4 px-6 font-bold`}>例子</h2>\n                    <div css={tw`flex py-4 px-6 bg-neutral-500`}>\n                        <div css={tw`w-1/2`}>*/5 * * * *</div>\n                        <div css={tw`w-1/2`}>每 5 分钟</div>\n                    </div>\n                    <div css={tw`flex py-4 px-6`}>\n                        <div css={tw`w-1/2`}>0 */1 * * *</div>\n                        <div css={tw`w-1/2`}>每隔一小时</div>\n                    </div>\n                    <div css={tw`flex py-4 px-6 bg-neutral-500`}>\n                        <div css={tw`w-1/2`}>0 8-12 * * *</div>\n                        <div css={tw`w-1/2`}>小时范围</div>\n                    </div>\n                    <div css={tw`flex py-4 px-6`}>\n                        <div css={tw`w-1/2`}>0 0 * * *</div>\n                        <div css={tw`w-1/2`}>一天一次</div>\n                    </div>\n                    <div css={tw`flex py-4 px-6 bg-neutral-500`}>\n                        <div css={tw`w-1/2`}>0 0 * * MON</div>\n                        <div css={tw`w-1/2`}>每个星期一</div>\n                    </div>\n                </div>\n            </div>\n            <div css={tw`md:w-1/2 h-full bg-neutral-600`}>\n                <h2 css={tw`py-4 px-6 font-bold`}>特殊字符</h2>\n                <div css={tw`flex flex-col`}>\n                    <div css={tw`flex py-4 px-6 bg-neutral-500`}>\n                        <div css={tw`w-1/2`}>*</div>\n                        <div css={tw`w-1/2`}>任何值</div>\n                    </div>\n                    <div css={tw`flex py-4 px-6`}>\n                        <div css={tw`w-1/2`}>,</div>\n                        <div css={tw`w-1/2`}>数值列表分隔符</div>\n                    </div>\n                    <div css={tw`flex py-4 px-6 bg-neutral-500`}>\n                        <div css={tw`w-1/2`}>-</div>\n                        <div css={tw`w-1/2`}>范围值</div>\n                    </div>\n                    <div css={tw`flex py-4 px-6`}>\n                        <div css={tw`w-1/2`}>/</div>\n                        <div css={tw`w-1/2`}>步进值</div>\n                    </div>\n                </div>\n            </div>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/ScheduleContainer.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport getServerSchedules from '@/api/server/schedules/getServerSchedules';\nimport { ServerContext } from '@/state/server';\nimport Spinner from '@/components/elements/Spinner';\nimport { useHistory, useRouteMatch } from 'react-router-dom';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport ScheduleRow from '@/components/server/schedules/ScheduleRow';\nimport { httpErrorToHuman } from '@/api/http';\nimport EditScheduleModal from '@/components/server/schedules/EditScheduleModal';\nimport Can from '@/components/elements/Can';\nimport useFlash from '@/plugins/useFlash';\nimport tw from 'twin.macro';\nimport GreyRowBox from '@/components/elements/GreyRowBox';\nimport { Button } from '@/components/elements/button/index';\nimport ServerContentBlock from '@/components/elements/ServerContentBlock';\n\nexport default () => {\n    const match = useRouteMatch();\n    const history = useHistory();\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const { clearFlashes, addError } = useFlash();\n    const [loading, setLoading] = useState(true);\n    const [visible, setVisible] = useState(false);\n\n    const schedules = ServerContext.useStoreState((state) => state.schedules.data);\n    const setSchedules = ServerContext.useStoreActions((actions) => actions.schedules.setSchedules);\n\n    useEffect(() => {\n        clearFlashes('schedules');\n        getServerSchedules(uuid)\n            .then((schedules) => setSchedules(schedules))\n            .catch((error) => {\n                addError({ message: httpErrorToHuman(error), key: 'schedules' });\n                console.error(error);\n            })\n            .then(() => setLoading(false));\n    }, []);\n\n    return (\n        <ServerContentBlock title={'计划'}>\n            <FlashMessageRender byKey={'schedules'} css={tw`mb-4`} />\n            {!schedules.length && loading ? (\n                <Spinner size={'large'} centered />\n            ) : (\n                <>\n                    {schedules.length === 0 ? (\n                        <p css={tw`text-sm text-center text-neutral-300`}>此服务器未创建计划。</p>\n                    ) : (\n                        schedules.map((schedule) => (\n                            <GreyRowBox\n                                as={'a'}\n                                key={schedule.id}\n                                href={`${match.url}/${schedule.id}`}\n                                css={tw`cursor-pointer mb-2 flex-wrap`}\n                                onClick={(e: any) => {\n                                    e.preventDefault();\n                                    history.push(`${match.url}/${schedule.id}`);\n                                }}\n                            >\n                                <ScheduleRow schedule={schedule} />\n                            </GreyRowBox>\n                        ))\n                    )}\n                    <Can action={'schedule.create'}>\n                        <div css={tw`mt-8 flex justify-end`}>\n                            <EditScheduleModal visible={visible} onModalDismissed={() => setVisible(false)} />\n                            <Button type={'button'} onClick={() => setVisible(true)}>\n                                创建计划\n                            </Button>\n                        </div>\n                    </Can>\n                </>\n            )}\n        </ServerContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/ScheduleCronRow.tsx",
    "content": "import React from 'react';\nimport { Schedule } from '@/api/server/schedules/getServerSchedules';\nimport classNames from 'classnames';\n\ninterface Props {\n    cron: Schedule['cron'];\n    className?: string;\n}\n\nconst ScheduleCronRow = ({ cron, className }: Props) => (\n    <div className={classNames('flex', className)}>\n        <div className={'w-1/5 sm:w-auto text-center'}>\n            <p className={'font-medium'}>{cron.minute}</p>\n            <p className={'text-2xs text-neutral-500 uppercase'}>分钟</p>\n        </div>\n        <div className={'w-1/5 sm:w-auto text-center ml-4'}>\n            <p className={'font-medium'}>{cron.hour}</p>\n            <p className={'text-2xs text-neutral-500 uppercase'}>小时</p>\n        </div>\n        <div className={'w-1/5 sm:w-auto text-center ml-4'}>\n            <p className={'font-medium'}>{cron.dayOfMonth}</p>\n            <p className={'text-2xs text-neutral-500 uppercase'}>天（每月）</p>\n        </div>\n        <div className={'w-1/5 sm:w-auto text-center ml-4'}>\n            <p className={'font-medium'}>{cron.month}</p>\n            <p className={'text-2xs text-neutral-500 uppercase'}>月</p>\n        </div>\n        <div className={'w-1/5 sm:w-auto text-center ml-4'}>\n            <p className={'font-medium'}>{cron.dayOfWeek}</p>\n            <p className={'text-2xs text-neutral-500 uppercase'}>天（每周）</p>\n        </div>\n    </div>\n);\n\nexport default ScheduleCronRow;\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/ScheduleEditContainer.tsx",
    "content": "import React, { useCallback, useEffect, useState } from 'react';\nimport { useHistory, useParams } from 'react-router-dom';\nimport getServerSchedule from '@/api/server/schedules/getServerSchedule';\nimport Spinner from '@/components/elements/Spinner';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport EditScheduleModal from '@/components/server/schedules/EditScheduleModal';\nimport NewTaskButton from '@/components/server/schedules/NewTaskButton';\nimport DeleteScheduleButton from '@/components/server/schedules/DeleteScheduleButton';\nimport Can from '@/components/elements/Can';\nimport useFlash from '@/plugins/useFlash';\nimport { ServerContext } from '@/state/server';\nimport PageContentBlock from '@/components/elements/PageContentBlock';\nimport tw from 'twin.macro';\nimport { Button } from '@/components/elements/button/index';\nimport ScheduleTaskRow from '@/components/server/schedules/ScheduleTaskRow';\nimport isEqual from 'react-fast-compare';\nimport { format } from 'date-fns';\nimport ScheduleCronRow from '@/components/server/schedules/ScheduleCronRow';\nimport RunScheduleButton from '@/components/server/schedules/RunScheduleButton';\n\ninterface Params {\n    id: string;\n}\n\nconst CronBox = ({ title, value }: { title: string; value: string }) => (\n    <div css={tw`bg-neutral-700 rounded p-3`}>\n        <p css={tw`text-neutral-300 text-sm`}>{title}</p>\n        <p css={tw`text-xl font-medium text-neutral-100`}>{value}</p>\n    </div>\n);\n\nconst ActivePill = ({ active }: { active: boolean }) => (\n    <span\n        css={[\n            tw`rounded-full px-2 py-px text-xs ml-4 uppercase`,\n            active ? tw`bg-green-600 text-green-100` : tw`bg-red-600 text-red-100`,\n        ]}\n    >\n        {active ? '已激活' : '未激活'}\n    </span>\n);\n\nexport default () => {\n    const history = useHistory();\n    const { id: scheduleId } = useParams<Params>();\n\n    const id = ServerContext.useStoreState((state) => state.server.data!.id);\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const [isLoading, setIsLoading] = useState(true);\n    const [showEditModal, setShowEditModal] = useState(false);\n\n    const schedule = ServerContext.useStoreState(\n        (st) => st.schedules.data.find((s) => s.id === Number(scheduleId)),\n        isEqual\n    );\n    const appendSchedule = ServerContext.useStoreActions((actions) => actions.schedules.appendSchedule);\n\n    useEffect(() => {\n        if (schedule?.id === Number(scheduleId)) {\n            setIsLoading(false);\n            return;\n        }\n\n        clearFlashes('schedules');\n        getServerSchedule(uuid, Number(scheduleId))\n            .then((schedule) => appendSchedule(schedule))\n            .catch((error) => {\n                console.error(error);\n                clearAndAddHttpError({ error, key: 'schedules' });\n            })\n            .then(() => setIsLoading(false));\n    }, [scheduleId]);\n\n    const toggleEditModal = useCallback(() => {\n        setShowEditModal((s) => !s);\n    }, []);\n\n    return (\n        <PageContentBlock title={'计划表'}>\n            <FlashMessageRender byKey={'schedules'} css={tw`mb-4`} />\n            {!schedule || isLoading ? (\n                <Spinner size={'large'} centered />\n            ) : (\n                <>\n                    <ScheduleCronRow cron={schedule.cron} css={tw`sm:hidden bg-neutral-700 rounded mb-4 p-3`} />\n                    <div css={tw`rounded shadow`}>\n                        <div\n                            css={tw`sm:flex items-center bg-neutral-900 p-3 sm:p-6 border-b-4 border-neutral-600 rounded-t`}\n                        >\n                            <div css={tw`flex-1`}>\n                                <h3 css={tw`flex items-center text-neutral-100 text-2xl`}>\n                                    {schedule.name}\n                                    {schedule.isProcessing ? (\n                                        <span\n                                            css={tw`flex items-center rounded-full px-2 py-px text-xs ml-4 uppercase bg-neutral-600 text-white`}\n                                        >\n                                            <Spinner css={tw`w-3! h-3! mr-2`} />\n                                            正在运行\n                                        </span>\n                                    ) : (\n                                        <ActivePill active={schedule.isActive} />\n                                    )}\n                                </h3>\n                                <p css={tw`mt-1 text-sm text-neutral-200`}>\n                                    上次运行于:&nbsp;\n                                    {schedule.lastRunAt ? (\n                                        format(schedule.lastRunAt, 'yyyy年M月d日 HH:mm')\n                                    ) : (\n                                        <span css={tw`text-neutral-300`}>n/a</span>\n                                    )}\n                                    <span css={tw`ml-4 pl-4 border-l-4 border-neutral-600 py-px`}>\n                                        下次运行于:&nbsp;\n                                        {schedule.nextRunAt ? (\n                                            format(schedule.nextRunAt, 'yyyy年M月d日 HH:mm')\n                                        ) : (\n                                            <span css={tw`text-neutral-300`}>n/a</span>\n                                        )}\n                                    </span>\n                                </p>\n                            </div>\n                            <div css={tw`flex sm:block mt-3 sm:mt-0`}>\n                                <Can action={'schedule.update'}>\n                                    <Button.Text className={'flex-1 mr-4'} onClick={toggleEditModal}>\n                                        编辑\n                                    </Button.Text>\n                                    <NewTaskButton schedule={schedule} />\n                                </Can>\n                            </div>\n                        </div>\n                        <div css={tw`hidden sm:grid grid-cols-5 md:grid-cols-5 gap-4 mb-4 mt-4`}>\n                            <CronBox title={'分钟'} value={schedule.cron.minute} />\n                            <CronBox title={'小时'} value={schedule.cron.hour} />\n                            <CronBox title={'天（每个月）'} value={schedule.cron.dayOfMonth} />\n                            <CronBox title={'月'} value={schedule.cron.month} />\n                            <CronBox title={'天（每周）'} value={schedule.cron.dayOfWeek} />\n                        </div>\n                        <div css={tw`bg-neutral-700 rounded-b`}>\n                            {schedule.tasks.length > 0\n                                ? schedule.tasks\n                                      .sort((a, b) =>\n                                          a.sequenceId === b.sequenceId ? 0 : a.sequenceId > b.sequenceId ? 1 : -1\n                                      )\n                                      .map((task) => (\n                                          <ScheduleTaskRow\n                                              key={`${schedule.id}_${task.id}`}\n                                              task={task}\n                                              schedule={schedule}\n                                          />\n                                      ))\n                                : null}\n                        </div>\n                    </div>\n                    <EditScheduleModal visible={showEditModal} schedule={schedule} onModalDismissed={toggleEditModal} />\n                    <div css={tw`mt-6 flex sm:justify-end`}>\n                        <Can action={'schedule.delete'}>\n                            <DeleteScheduleButton\n                                scheduleId={schedule.id}\n                                onDeleted={() => history.push(`/server/${id}/schedules`)}\n                            />\n                        </Can>\n                        {schedule.tasks.length > 0 && (\n                            <Can action={'schedule.update'}>\n                                <RunScheduleButton schedule={schedule} />\n                            </Can>\n                        )}\n                    </div>\n                </>\n            )}\n        </PageContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/ScheduleRow.tsx",
    "content": "import React from 'react';\nimport { Schedule } from '@/api/server/schedules/getServerSchedules';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faCalendarAlt } from '@fortawesome/free-solid-svg-icons';\nimport { format } from 'date-fns';\nimport tw from 'twin.macro';\nimport ScheduleCronRow from '@/components/server/schedules/ScheduleCronRow';\n\nexport default ({ schedule }: { schedule: Schedule }) => (\n    <>\n        <div css={tw`hidden md:block`}>\n            <FontAwesomeIcon icon={faCalendarAlt} fixedWidth />\n        </div>\n        <div css={tw`flex-1 md:ml-4`}>\n            <p>{schedule.name}</p>\n            <p css={tw`text-xs text-neutral-400`}>\n                上次运行于: {schedule.lastRunAt ? format(schedule.lastRunAt, 'yyyy年M月d日 HH:mm') : 'never'}\n            </p>\n        </div>\n        <div>\n            <p\n                css={[\n                    tw`py-1 px-3 rounded text-xs uppercase text-white sm:hidden`,\n                    schedule.isActive ? tw`bg-green-600` : tw`bg-neutral-400`,\n                ]}\n            >\n                {schedule.isActive ? '正在运行' : '未在运行'}\n            </p>\n        </div>\n        <ScheduleCronRow cron={schedule.cron} css={tw`mx-auto sm:mx-8 w-full sm:w-auto mt-4 sm:mt-0`} />\n        <div>\n            <p\n                css={[\n                    tw`py-1 px-3 rounded text-xs uppercase text-white hidden sm:block`,\n                    schedule.isActive && !schedule.isProcessing ? tw`bg-green-600` : tw`bg-neutral-400`,\n                ]}\n            >\n                {schedule.isProcessing ? '正在处理' : schedule.isActive ? '正在运行' : '未在运行'}\n            </p>\n        </div>\n    </>\n);\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/ScheduleSimpleForm.tsx",
    "content": "import React, { useEffect, useRef, useState } from 'react';\nimport Select from '@/components/elements/Select';\nimport Label from '@/components/elements/Label';\nimport tw from 'twin.macro';\n\ntype FrequencyType = 'minutely' | 'hourly' | 'daily' | 'weekly' | 'monthly';\n\ninterface CronValues {\n    minute: string;\n    hour: string;\n    dayOfMonth: string;\n    month: string;\n    dayOfWeek: string;\n}\n\ninterface Props {\n    initialCron?: CronValues;\n    onChange: (values: CronValues) => void;\n}\n\nconst range = (start: number, end: number): number[] => Array.from({ length: end - start + 1 }, (_, i) => start + i);\n\nconst MINUTE_INTERVALS = range(1, 59);\nconst HOUR_INTERVALS = range(1, 23);\nconst DAYS_OF_WEEK = ['星期日', '星期一', '星期二', '星期三', '星期四', '星期五', '星期六'];\n\nconst parseInitialState = (\n    cron?: CronValues\n): {\n    frequency: FrequencyType;\n    minuteInterval: number;\n    hourInterval: number;\n    hourOffset: number;\n    dayHour: number;\n    dayMinute: number;\n    weekDay: number;\n    weekHour: number;\n    weekMinute: number;\n    monthDay: number;\n    monthHour: number;\n    monthMinute: number;\n} => {\n    const defaults = {\n        frequency: 'daily' as FrequencyType,\n        minuteInterval: 5,\n        hourInterval: 1,\n        hourOffset: 0,\n        dayHour: 0,\n        dayMinute: 0,\n        weekDay: 0,\n        weekHour: 0,\n        weekMinute: 0,\n        monthDay: 1,\n        monthHour: 0,\n        monthMinute: 0,\n    };\n    if (!cron) return defaults;\n\n    const minuteMatch = /^\\*\\/(\\d+)$/.exec(cron.minute);\n    const hourMatch = /^\\*\\/(\\d+)$/.exec(cron.hour);\n\n    // minutely: */X * * * *\n    if (minuteMatch && cron.hour === '*' && cron.dayOfMonth === '*' && cron.month === '*' && cron.dayOfWeek === '*') {\n        const interval = Number(minuteMatch[1]);\n        return {\n            ...defaults,\n            frequency: 'minutely',\n            minuteInterval: interval >= 1 && interval <= 59 ? interval : 5,\n        };\n    }\n\n    // hourly: M */H * * * or M * * * *\n    const hourNum = /^\\d+$/.test(cron.hour) ? Number(cron.hour) : -1;\n    const minuteNum = /^\\d+$/.test(cron.minute) ? Number(cron.minute) : -1;\n    if (\n        minuteNum >= 0 &&\n        (hourMatch || cron.hour === '*') &&\n        cron.dayOfMonth === '*' &&\n        cron.month === '*' &&\n        cron.dayOfWeek === '*' &&\n        hourNum < 0\n    ) {\n        const interval = hourMatch ? Number(hourMatch[1]) : 1;\n        return {\n            ...defaults,\n            frequency: 'hourly',\n            hourOffset: minuteNum,\n            hourInterval: interval >= 1 && interval <= 23 ? interval : 1,\n        };\n    }\n\n    const domNum = /^\\d+$/.test(cron.dayOfMonth) ? Number(cron.dayOfMonth) : -1;\n    const dowNum = /^\\d+$/.test(cron.dayOfWeek) ? Number(cron.dayOfWeek) : -1;\n\n    // monthly: M H D * *\n    if (minuteNum >= 0 && hourNum >= 0 && domNum >= 1 && cron.month === '*' && cron.dayOfWeek === '*') {\n        return {\n            ...defaults,\n            frequency: 'monthly',\n            monthMinute: minuteNum,\n            monthHour: hourNum,\n            monthDay: domNum <= 31 ? domNum : 1,\n        };\n    }\n\n    // weekly: M H * * DOW\n    if (minuteNum >= 0 && hourNum >= 0 && cron.dayOfMonth === '*' && cron.month === '*' && dowNum >= 0) {\n        return {\n            ...defaults,\n            frequency: 'weekly',\n            weekMinute: minuteNum,\n            weekHour: hourNum,\n            weekDay: dowNum <= 6 ? dowNum : 0,\n        };\n    }\n\n    // daily: M H * * *\n    if (minuteNum >= 0 && hourNum >= 0 && cron.dayOfMonth === '*' && cron.month === '*' && cron.dayOfWeek === '*') {\n        return { ...defaults, frequency: 'daily', dayMinute: minuteNum, dayHour: hourNum };\n    }\n\n    return defaults;\n};\n\nexport default ({ initialCron, onChange }: Props) => {\n    const init = parseInitialState(initialCron);\n    const [frequency, setFrequency] = useState<FrequencyType>(init.frequency);\n    const [minuteInterval, setMinuteInterval] = useState(init.minuteInterval);\n    const [hourInterval, setHourInterval] = useState(init.hourInterval);\n    const [hourOffset, setHourOffset] = useState(init.hourOffset);\n    const [dayHour, setDayHour] = useState(init.dayHour);\n    const [dayMinute, setDayMinute] = useState(init.dayMinute);\n    const [weekDay, setWeekDay] = useState(init.weekDay);\n    const [weekHour, setWeekHour] = useState(init.weekHour);\n    const [weekMinute, setWeekMinute] = useState(init.weekMinute);\n    const [monthDay, setMonthDay] = useState(init.monthDay);\n    const [monthHour, setMonthHour] = useState(init.monthHour);\n    const [monthMinute, setMonthMinute] = useState(init.monthMinute);\n\n    // Use a ref so the effect doesn't need `onChange` as a dependency, avoiding\n    // potential infinite update loops when an unstable callback reference is passed.\n    const onChangeRef = useRef(onChange);\n    useEffect(() => {\n        onChangeRef.current = onChange;\n    });\n\n    useEffect(() => {\n        let values: CronValues;\n        switch (frequency) {\n            case 'minutely':\n                values = {\n                    minute: `*/${minuteInterval}`,\n                    hour: '*',\n                    dayOfMonth: '*',\n                    month: '*',\n                    dayOfWeek: '*',\n                };\n                break;\n            case 'hourly':\n                values = {\n                    minute: String(hourOffset),\n                    hour: hourInterval === 1 ? '*' : `*/${hourInterval}`,\n                    dayOfMonth: '*',\n                    month: '*',\n                    dayOfWeek: '*',\n                };\n                break;\n            case 'daily':\n                values = {\n                    minute: String(dayMinute),\n                    hour: String(dayHour),\n                    dayOfMonth: '*',\n                    month: '*',\n                    dayOfWeek: '*',\n                };\n                break;\n            case 'weekly':\n                values = {\n                    minute: String(weekMinute),\n                    hour: String(weekHour),\n                    dayOfMonth: '*',\n                    month: '*',\n                    dayOfWeek: String(weekDay),\n                };\n                break;\n            case 'monthly':\n                values = {\n                    minute: String(monthMinute),\n                    hour: String(monthHour),\n                    dayOfMonth: String(monthDay),\n                    month: '*',\n                    dayOfWeek: '*',\n                };\n                break;\n        }\n        onChangeRef.current(values);\n    }, [\n        frequency,\n        minuteInterval,\n        hourInterval,\n        hourOffset,\n        dayHour,\n        dayMinute,\n        weekDay,\n        weekHour,\n        weekMinute,\n        monthDay,\n        monthHour,\n        monthMinute,\n    ]);\n\n    const currentHour = frequency === 'daily' ? dayHour : frequency === 'weekly' ? weekHour : monthHour;\n    const currentMinute = frequency === 'daily' ? dayMinute : frequency === 'weekly' ? weekMinute : monthMinute;\n\n    return (\n        <div css={tw`mt-6`}>\n            <div css={tw`grid grid-cols-2 sm:grid-cols-4 gap-4`}>\n                <div>\n                    <Label>执行频率</Label>\n                    <Select value={frequency} onChange={(e) => setFrequency(e.target.value as FrequencyType)}>\n                        <option value={'minutely'}>按分钟</option>\n                        <option value={'hourly'}>按小时</option>\n                        <option value={'daily'}>每天</option>\n                        <option value={'weekly'}>每周</option>\n                        <option value={'monthly'}>每月</option>\n                    </Select>\n                </div>\n\n                {frequency === 'minutely' && (\n                    <div>\n                        <Label>间隔（分钟）</Label>\n                        <Select value={minuteInterval} onChange={(e) => setMinuteInterval(Number(e.target.value))}>\n                            {MINUTE_INTERVALS.map((m) => (\n                                <option key={m} value={m}>\n                                    {m}\n                                </option>\n                            ))}\n                        </Select>\n                    </div>\n                )}\n\n                {frequency === 'hourly' && (\n                    <>\n                        <div>\n                            <Label>间隔（小时）</Label>\n                            <Select value={hourInterval} onChange={(e) => setHourInterval(Number(e.target.value))}>\n                                {HOUR_INTERVALS.map((h) => (\n                                    <option key={h} value={h}>\n                                        {h}\n                                    </option>\n                                ))}\n                            </Select>\n                        </div>\n                        <div>\n                            <Label>偏移（分钟）</Label>\n                            <Select value={hourOffset} onChange={(e) => setHourOffset(Number(e.target.value))}>\n                                {range(0, 59).map((m) => (\n                                    <option key={m} value={m}>\n                                        {String(m).padStart(2, '0')}\n                                    </option>\n                                ))}\n                            </Select>\n                        </div>\n                    </>\n                )}\n\n                {frequency === 'weekly' && (\n                    <div>\n                        <Label>星期</Label>\n                        <Select value={weekDay} onChange={(e) => setWeekDay(Number(e.target.value))}>\n                            {DAYS_OF_WEEK.map((day, i) => (\n                                <option key={i} value={i}>\n                                    {day}\n                                </option>\n                            ))}\n                        </Select>\n                    </div>\n                )}\n\n                {frequency === 'monthly' && (\n                    <div>\n                        <Label>日期</Label>\n                        <Select value={monthDay} onChange={(e) => setMonthDay(Number(e.target.value))}>\n                            {range(1, 31).map((d) => (\n                                <option key={d} value={d}>\n                                    {d}\n                                </option>\n                            ))}\n                        </Select>\n                    </div>\n                )}\n\n                {(frequency === 'daily' || frequency === 'weekly' || frequency === 'monthly') && (\n                    <>\n                        <div>\n                            <Label>小时</Label>\n                            <Select\n                                value={currentHour}\n                                onChange={(e) => {\n                                    const v = Number(e.target.value);\n                                    if (frequency === 'daily') setDayHour(v);\n                                    else if (frequency === 'weekly') setWeekHour(v);\n                                    else setMonthHour(v);\n                                }}\n                            >\n                                {range(0, 23).map((h) => (\n                                    <option key={h} value={h}>\n                                        {String(h).padStart(2, '0')}\n                                    </option>\n                                ))}\n                            </Select>\n                        </div>\n                        <div>\n                            <Label>分钟</Label>\n                            <Select\n                                value={currentMinute}\n                                onChange={(e) => {\n                                    const v = Number(e.target.value);\n                                    if (frequency === 'daily') setDayMinute(v);\n                                    else if (frequency === 'weekly') setWeekMinute(v);\n                                    else setMonthMinute(v);\n                                }}\n                            >\n                                {range(0, 59).map((m) => (\n                                    <option key={m} value={m}>\n                                        {String(m).padStart(2, '0')}\n                                    </option>\n                                ))}\n                            </Select>\n                        </div>\n                    </>\n                )}\n            </div>\n            {frequency === 'monthly' && monthDay > 28 && (\n                <p css={tw`text-neutral-400 text-xs mt-2`}>\n                    注意：所选日期在部分月份可能不存在（如2月），届时该任务将跳过执行。\n                </p>\n            )}\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/ScheduleTaskRow.tsx",
    "content": "import React, { useState } from 'react';\nimport { Schedule, Task } from '@/api/server/schedules/getServerSchedules';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport {\n    faArrowCircleDown,\n    faClock,\n    faCode,\n    faFileArchive,\n    faPencilAlt,\n    faToggleOn,\n    faTrashAlt,\n} from '@fortawesome/free-solid-svg-icons';\nimport deleteScheduleTask from '@/api/server/schedules/deleteScheduleTask';\nimport { httpErrorToHuman } from '@/api/http';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport TaskDetailsModal from '@/components/server/schedules/TaskDetailsModal';\nimport Can from '@/components/elements/Can';\nimport useFlash from '@/plugins/useFlash';\nimport { ServerContext } from '@/state/server';\nimport tw from 'twin.macro';\nimport ConfirmationModal from '@/components/elements/ConfirmationModal';\nimport Icon from '@/components/elements/Icon';\n\ninterface Props {\n    schedule: Schedule;\n    task: Task;\n}\n\nconst getActionDetails = (action: string): [string, any] => {\n    switch (action) {\n        case 'command':\n            return ['发送指令', faCode];\n        case 'power':\n            return ['发送电源操作', faToggleOn];\n        case 'backup':\n            return ['创建备份', faFileArchive];\n        default:\n            return ['其他', faCode];\n    }\n};\n\nexport default ({ schedule, task }: Props) => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const { clearFlashes, addError } = useFlash();\n    const [visible, setVisible] = useState(false);\n    const [isLoading, setIsLoading] = useState(false);\n    const [isEditing, setIsEditing] = useState(false);\n    const appendSchedule = ServerContext.useStoreActions((actions) => actions.schedules.appendSchedule);\n\n    const onConfirmDeletion = () => {\n        setIsLoading(true);\n        clearFlashes('schedules');\n        deleteScheduleTask(uuid, schedule.id, task.id)\n            .then(() =>\n                appendSchedule({\n                    ...schedule,\n                    tasks: schedule.tasks.filter((t) => t.id !== task.id),\n                })\n            )\n            .catch((error) => {\n                console.error(error);\n                setIsLoading(false);\n                addError({ message: httpErrorToHuman(error), key: 'schedules' });\n            });\n    };\n\n    const [title, icon] = getActionDetails(task.action);\n\n    return (\n        <div css={tw`sm:flex items-center p-3 sm:p-6 border-b border-neutral-800`}>\n            <SpinnerOverlay visible={isLoading} fixed size={'large'} />\n            <TaskDetailsModal\n                schedule={schedule}\n                task={task}\n                visible={isEditing}\n                onModalDismissed={() => setIsEditing(false)}\n            />\n            <ConfirmationModal\n                title={'确定'}\n                buttonText={'删除任务'}\n                onConfirmed={onConfirmDeletion}\n                visible={visible}\n                onModalDismissed={() => setVisible(false)}\n            >\n                您确定要删除此任务吗？ 此操作无法撤消。\n            </ConfirmationModal>\n            <FontAwesomeIcon icon={icon} css={tw`text-lg text-white hidden md:block`} />\n            <div css={tw`flex-none sm:flex-1 w-full sm:w-auto overflow-x-auto`}>\n                <p css={tw`md:ml-6 text-neutral-200 uppercase text-sm`}>{title}</p>\n                {task.payload && (\n                    <div css={tw`md:ml-6 mt-2`}>\n                        {task.action === 'backup' && (\n                            <p css={tw`text-xs uppercase text-neutral-400 mb-1`}>忽略的文件和文件夹:</p>\n                        )}\n                        <div\n                            css={tw`font-mono bg-neutral-800 rounded py-1 px-2 text-sm w-auto inline-block whitespace-pre-wrap break-all`}\n                        >\n                            {task.payload}\n                        </div>\n                    </div>\n                )}\n            </div>\n            <div css={tw`mt-3 sm:mt-0 flex items-center w-full sm:w-auto`}>\n                {task.continueOnFailure && (\n                    <div css={tw`mr-6`}>\n                        <div css={tw`flex items-center px-2 py-1 bg-yellow-500 text-yellow-800 text-sm rounded-full`}>\n                            <Icon icon={faArrowCircleDown} css={tw`w-3 h-3 mr-2`} />\n                            即使失败也继续运行\n                        </div>\n                    </div>\n                )}\n                {task.sequenceId > 1 && task.timeOffset > 0 && (\n                    <div css={tw`mr-6`}>\n                        <div css={tw`flex items-center px-2 py-1 bg-neutral-500 text-sm rounded-full`}>\n                            <Icon icon={faClock} css={tw`w-3 h-3 mr-2`} />\n                            {task.timeOffset} 秒后\n                        </div>\n                    </div>\n                )}\n                <Can action={'schedule.update'}>\n                    <button\n                        type={'button'}\n                        aria-label={'编辑计划任务'}\n                        css={tw`block text-sm p-2 text-neutral-500 hover:text-neutral-100 transition-colors duration-150 mr-4 ml-auto sm:ml-0`}\n                        onClick={() => setIsEditing(true)}\n                    >\n                        <FontAwesomeIcon icon={faPencilAlt} />\n                    </button>\n                </Can>\n                <Can action={'schedule.update'}>\n                    <button\n                        type={'button'}\n                        aria-label={'删除计划任务'}\n                        css={tw`block text-sm p-2 text-neutral-500 hover:text-red-600 transition-colors duration-150`}\n                        onClick={() => setVisible(true)}\n                    >\n                        <FontAwesomeIcon icon={faTrashAlt} />\n                    </button>\n                </Can>\n            </div>\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/schedules/TaskDetailsModal.tsx",
    "content": "import React, { useContext, useEffect } from 'react';\nimport { Schedule, Task } from '@/api/server/schedules/getServerSchedules';\nimport { Field as FormikField, Form, Formik, FormikHelpers, useField } from 'formik';\nimport { ServerContext } from '@/state/server';\nimport createOrUpdateScheduleTask from '@/api/server/schedules/createOrUpdateScheduleTask';\nimport { httpErrorToHuman } from '@/api/http';\nimport Field from '@/components/elements/Field';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport { boolean, number, object, string } from 'yup';\nimport useFlash from '@/plugins/useFlash';\nimport FormikFieldWrapper from '@/components/elements/FormikFieldWrapper';\nimport tw from 'twin.macro';\nimport Label from '@/components/elements/Label';\nimport { Textarea } from '@/components/elements/Input';\nimport { Button } from '@/components/elements/button/index';\nimport Select from '@/components/elements/Select';\nimport ModalContext from '@/context/ModalContext';\nimport asModal from '@/hoc/asModal';\nimport FormikSwitch from '@/components/elements/FormikSwitch';\n\ninterface Props {\n    schedule: Schedule;\n    // If a task is provided we can assume we're editing it. If not provided,\n    // we are creating a new one.\n    task?: Task;\n}\n\ninterface Values {\n    action: string;\n    payload: string;\n    timeOffset: string;\n    continueOnFailure: boolean;\n}\n\nconst schema = object().shape({\n    action: string().required().oneOf(['command', 'power', 'backup']),\n    payload: string().when('action', {\n        is: (v) => v !== 'backup',\n        then: string().required('必须提供有效的任务操作。'),\n        otherwise: string(),\n    }),\n    continueOnFailure: boolean(),\n    timeOffset: number()\n        .typeError('时间偏移必须是 0 到 900 之间的有效数字。')\n        .required('必须提供时间偏移值。')\n        .min(0, '时间偏移至少为 0 秒。')\n        .max(900, '时间偏移必须小于 900 秒。'),\n});\n\nconst ActionListener = () => {\n    const [{ value }, { initialValue: initialAction }] = useField<string>('action');\n    const [, { initialValue: initialPayload }, { setValue, setTouched }] = useField<string>('payload');\n\n    useEffect(() => {\n        if (value !== initialAction) {\n            setValue(value === 'power' ? 'start' : '');\n            setTouched(false);\n        } else {\n            setValue(initialPayload || '');\n            setTouched(false);\n        }\n    }, [value]);\n\n    return null;\n};\n\nconst TaskDetailsModal = ({ schedule, task }: Props) => {\n    const { dismiss } = useContext(ModalContext);\n    const { clearFlashes, addError } = useFlash();\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const appendSchedule = ServerContext.useStoreActions((actions) => actions.schedules.appendSchedule);\n    const backupLimit = ServerContext.useStoreState((state) => state.server.data!.featureLimits.backups);\n\n    useEffect(() => {\n        return () => {\n            clearFlashes('schedule:task');\n        };\n    }, []);\n\n    const submit = (values: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        clearFlashes('schedule:task');\n        if (backupLimit === 0 && values.action === 'backup') {\n            setSubmitting(false);\n            addError({\n                message: '当服务器的备份限制设置为 0 时，无法创建备份任务。',\n                key: 'schedule:task',\n            });\n        } else {\n            createOrUpdateScheduleTask(uuid, schedule.id, task?.id, values)\n                .then((task) => {\n                    let tasks = schedule.tasks.map((t) => (t.id === task.id ? task : t));\n                    if (!schedule.tasks.find((t) => t.id === task.id)) {\n                        tasks = [...tasks, task];\n                    }\n\n                    appendSchedule({ ...schedule, tasks });\n                    dismiss();\n                })\n                .catch((error) => {\n                    console.error(error);\n                    setSubmitting(false);\n                    addError({ message: httpErrorToHuman(error), key: 'schedule:task' });\n                });\n        }\n    };\n\n    return (\n        <Formik\n            onSubmit={submit}\n            validationSchema={schema}\n            initialValues={{\n                action: task?.action || 'command',\n                payload: task?.payload || '',\n                timeOffset: task?.timeOffset.toString() || '0',\n                continueOnFailure: task?.continueOnFailure || false,\n            }}\n        >\n            {({ isSubmitting, values }) => (\n                <Form css={tw`m-0`}>\n                    <FlashMessageRender byKey={'schedule:task'} css={tw`mb-4`} />\n                    <h2 css={tw`text-2xl mb-6`}>{task ? '编辑任务' : '创建任务'}</h2>\n                    <div css={tw`flex`}>\n                        <div css={tw`mr-2 w-1/3`}>\n                            <Label>动作</Label>\n                            <ActionListener />\n                            <FormikFieldWrapper name={'action'}>\n                                <FormikField as={Select} name={'action'}>\n                                    <option value={'command'}>发送指令</option>\n                                    <option value={'power'}>发送电源操作</option>\n                                    <option value={'backup'}>创建备份</option>\n                                </FormikField>\n                            </FormikFieldWrapper>\n                        </div>\n                        <div css={tw`flex-1 ml-6`}>\n                            <Field\n                                name={'timeOffset'}\n                                label={'时间偏移（以秒为单位）'}\n                                description={\n                                    '上一个任务执行后在运行此任务之前等待的时间。如果这是计划中的第一个任务，则不会应用该任务。'\n                                }\n                            />\n                        </div>\n                    </div>\n                    <div css={tw`mt-6`}>\n                        {values.action === 'command' ? (\n                            <div>\n                                <Label>任务操作</Label>\n                                <FormikFieldWrapper name={'payload'}>\n                                    <FormikField as={Textarea} name={'payload'} rows={6} />\n                                </FormikFieldWrapper>\n                            </div>\n                        ) : values.action === 'power' ? (\n                            <div>\n                                <Label>任务操作</Label>\n                                <FormikFieldWrapper name={'payload'}>\n                                    <FormikField as={Select} name={'payload'}>\n                                        <option value={'start'}>启动服务器</option>\n                                        <option value={'restart'}>重启服务器</option>\n                                        <option value={'stop'}>关闭服务器</option>\n                                        <option value={'kill'}>停止服务器</option>\n                                    </FormikField>\n                                </FormikFieldWrapper>\n                            </div>\n                        ) : (\n                            <div>\n                                <Label>被忽略的文件</Label>\n                                <FormikFieldWrapper\n                                    name={'payload'}\n                                    description={\n                                        '可选的。包括要在此备份中排除的文件和文件夹。默认情况下，将使用 .pteroignore 文件的内容。如果您已达到备份限制，则将轮换最早的备份。'\n                                    }\n                                >\n                                    <FormikField as={Textarea} name={'payload'} rows={6} />\n                                </FormikFieldWrapper>\n                            </div>\n                        )}\n                    </div>\n                    <div css={tw`mt-6 bg-neutral-700 border border-neutral-800 shadow-inner p-4 rounded`}>\n                        <FormikSwitch\n                            name={'continueOnFailure'}\n                            description={'当此任务失败时，将运行未来的任务。'}\n                            label={'即使失败也继续执行'}\n                        />\n                    </div>\n                    <div css={tw`flex justify-end mt-6`}>\n                        <Button type={'submit'} disabled={isSubmitting}>\n                            {task ? '保存更改' : '创建任务'}\n                        </Button>\n                    </div>\n                </Form>\n            )}\n        </Formik>\n    );\n};\n\nexport default asModal<Props>()(TaskDetailsModal);\n"
  },
  {
    "path": "resources/scripts/components/server/settings/ReinstallServerBox.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { ServerContext } from '@/state/server';\nimport TitledGreyBox from '@/components/elements/TitledGreyBox';\nimport reinstallServer from '@/api/server/reinstallServer';\nimport { Actions, useStoreActions } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport { httpErrorToHuman } from '@/api/http';\nimport tw from 'twin.macro';\nimport { Button } from '@/components/elements/button/index';\nimport { Dialog } from '@/components/elements/dialog';\n\nexport default () => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const [modalVisible, setModalVisible] = useState(false);\n    const { addFlash, clearFlashes } = useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n\n    const reinstall = () => {\n        clearFlashes('settings');\n        reinstallServer(uuid)\n            .then(() => {\n                addFlash({\n                    key: 'settings',\n                    type: 'success',\n                    message: '您的服务器已开始重新安装过程。',\n                });\n            })\n            .catch((error) => {\n                console.error(error);\n\n                addFlash({ key: 'settings', type: 'error', message: httpErrorToHuman(error) });\n            })\n            .then(() => setModalVisible(false));\n    };\n\n    useEffect(() => {\n        clearFlashes();\n    }, []);\n\n    return (\n        <TitledGreyBox title={'重新安装服务器'} css={tw`relative`}>\n            <Dialog.Confirm\n                open={modalVisible}\n                title={'确认服务器重新安装'}\n                confirm={'确认,重装服务器'}\n                onClose={() => setModalVisible(false)}\n                onConfirmed={reinstall}\n            >\n                在此过程中，您的服务器将停止运行，并且某些文件可能会被删除或修改，您确定要继续吗？\n            </Dialog.Confirm>\n            <p css={tw`text-sm`}>\n                重新安装您的服务器将停止它，然后重新运行最初设置它的安装脚本.&nbsp;\n                <strong css={tw`font-medium`}>在此过程中可能会删除或修改某些文件，请在继续之前备份您的数据。</strong>\n            </p>\n            <div css={tw`mt-6 text-right`}>\n                <Button.Danger variant={Button.Variants.Secondary} onClick={() => setModalVisible(true)}>\n                    重新安装服务器\n                </Button.Danger>\n            </div>\n        </TitledGreyBox>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/settings/RenameServerBox.tsx",
    "content": "import React from 'react';\nimport { ServerContext } from '@/state/server';\nimport TitledGreyBox from '@/components/elements/TitledGreyBox';\nimport { Field as FormikField, Form, Formik, FormikHelpers, useFormikContext } from 'formik';\nimport { Actions, useStoreActions } from 'easy-peasy';\nimport renameServer from '@/api/server/renameServer';\nimport Field from '@/components/elements/Field';\nimport { object, string } from 'yup';\nimport SpinnerOverlay from '@/components/elements/SpinnerOverlay';\nimport { ApplicationStore } from '@/state';\nimport { httpErrorToHuman } from '@/api/http';\nimport { Button } from '@/components/elements/button/index';\nimport tw from 'twin.macro';\nimport Label from '@/components/elements/Label';\nimport FormikFieldWrapper from '@/components/elements/FormikFieldWrapper';\nimport { Textarea } from '@/components/elements/Input';\n\ninterface Values {\n    name: string;\n    description: string;\n}\n\nconst RenameServerBox = () => {\n    const { isSubmitting } = useFormikContext<Values>();\n\n    return (\n        <TitledGreyBox title={'更改服务器详细信息'} css={tw`relative`}>\n            <SpinnerOverlay visible={isSubmitting} />\n            <Form css={tw`mb-0`}>\n                <Field id={'name'} name={'name'} label={'服务器名称'} type={'text'} />\n                <div css={tw`mt-6`}>\n                    <Label>服务器描述</Label>\n                    <FormikFieldWrapper name={'description'}>\n                        <FormikField as={Textarea} name={'description'} rows={3} />\n                    </FormikFieldWrapper>\n                </div>\n                <div css={tw`mt-6 text-right`}>\n                    <Button type={'submit'}>保存</Button>\n                </div>\n            </Form>\n        </TitledGreyBox>\n    );\n};\n\nexport default () => {\n    const server = ServerContext.useStoreState((state) => state.server.data!);\n    const setServer = ServerContext.useStoreActions((actions) => actions.server.setServer);\n    const { addError, clearFlashes } = useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n\n    const submit = ({ name, description }: Values, { setSubmitting }: FormikHelpers<Values>) => {\n        clearFlashes('settings');\n        renameServer(server.uuid, name, description)\n            .then(() => setServer({ ...server, name, description }))\n            .catch((error) => {\n                console.error(error);\n                addError({ key: 'settings', message: httpErrorToHuman(error) });\n            })\n            .then(() => setSubmitting(false));\n    };\n\n    return (\n        <Formik\n            onSubmit={submit}\n            initialValues={{\n                name: server.name,\n                description: server.description,\n            }}\n            validationSchema={object().shape({\n                name: string().required().min(1),\n                description: string().nullable(),\n            })}\n        >\n            <RenameServerBox />\n        </Formik>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/settings/SettingsContainer.tsx",
    "content": "import React from 'react';\nimport TitledGreyBox from '@/components/elements/TitledGreyBox';\nimport { ServerContext } from '@/state/server';\nimport { useStoreState } from 'easy-peasy';\nimport RenameServerBox from '@/components/server/settings/RenameServerBox';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport Can from '@/components/elements/Can';\nimport ReinstallServerBox from '@/components/server/settings/ReinstallServerBox';\nimport tw from 'twin.macro';\nimport Input from '@/components/elements/Input';\nimport Label from '@/components/elements/Label';\nimport ServerContentBlock from '@/components/elements/ServerContentBlock';\nimport isEqual from 'react-fast-compare';\nimport CopyOnClick from '@/components/elements/CopyOnClick';\nimport { ip } from '@/lib/formatters';\nimport { Button } from '@/components/elements/button/index';\n\nexport default () => {\n    const username = useStoreState((state) => state.user.data!.username);\n    const id = ServerContext.useStoreState((state) => state.server.data!.id);\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const node = ServerContext.useStoreState((state) => state.server.data!.node);\n    const sftp = ServerContext.useStoreState((state) => state.server.data!.sftpDetails, isEqual);\n\n    return (\n        <ServerContentBlock title={'设置'}>\n            <FlashMessageRender byKey={'settings'} css={tw`mb-4`} />\n            <div css={tw`md:flex`}>\n                <div css={tw`w-full md:flex-1 md:mr-10`}>\n                    <Can action={'file.sftp'}>\n                        <TitledGreyBox title={'SFTP 连接信息'} css={tw`mb-6 md:mb-10`}>\n                            <div>\n                                <Label>服务器地址</Label>\n                                <CopyOnClick text={`sftp://${ip(sftp.ip)}:${sftp.port}`}>\n                                    <Input type={'text'} value={`sftp://${ip(sftp.ip)}:${sftp.port}`} readOnly />\n                                </CopyOnClick>\n                            </div>\n                            <div css={tw`mt-6`}>\n                                <Label>用户名</Label>\n                                <CopyOnClick text={`${username}.${id}`}>\n                                    <Input type={'text'} value={`${username}.${id}`} readOnly />\n                                </CopyOnClick>\n                            </div>\n                            <div css={tw`mt-6 flex items-center`}>\n                                <div css={tw`flex-1`}>\n                                    <div css={tw`border-l-4 border-cyan-500 p-3`}>\n                                        <p css={tw`text-xs text-neutral-200`}>\n                                            您的 SFTP 密码与您目前使用的账户密码相同。\n                                        </p>\n                                    </div>\n                                </div>\n                                <div css={tw`ml-4`}>\n                                    <a href={`sftp://${username}.${id}@${ip(sftp.ip)}:${sftp.port}`}>\n                                        <Button.Text variant={Button.Variants.Secondary}>启动 SFTP</Button.Text>\n                                    </a>\n                                </div>\n                            </div>\n                        </TitledGreyBox>\n                    </Can>\n                    <TitledGreyBox title={'Debug 调试信息'} css={tw`mb-6 md:mb-10`}>\n                        <div css={tw`flex items-center justify-between text-sm`}>\n                            <p>节点</p>\n                            <code css={tw`font-mono bg-neutral-900 rounded py-1 px-2`}>{node}</code>\n                        </div>\n                        <CopyOnClick text={uuid}>\n                            <div css={tw`flex items-center justify-between mt-2 text-sm`}>\n                                <p>服务器 ID</p>\n                                <code css={tw`font-mono bg-neutral-900 rounded py-1 px-2`}>{uuid}</code>\n                            </div>\n                        </CopyOnClick>\n                    </TitledGreyBox>\n                </div>\n                <div css={tw`w-full mt-6 md:flex-1 md:mt-0`}>\n                    <Can action={'settings.rename'}>\n                        <div css={tw`mb-6 md:mb-10`}>\n                            <RenameServerBox />\n                        </div>\n                    </Can>\n                    <Can action={'settings.reinstall'}>\n                        <ReinstallServerBox />\n                    </Can>\n                </div>\n            </div>\n        </ServerContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/startup/StartupContainer.tsx",
    "content": "import React, { useCallback, useEffect, useState } from 'react';\nimport TitledGreyBox from '@/components/elements/TitledGreyBox';\nimport tw from 'twin.macro';\nimport VariableBox from '@/components/server/startup/VariableBox';\nimport ServerContentBlock from '@/components/elements/ServerContentBlock';\nimport getServerStartup from '@/api/swr/getServerStartup';\nimport Spinner from '@/components/elements/Spinner';\nimport { ServerError } from '@/components/elements/ScreenBlock';\nimport { httpErrorToHuman } from '@/api/http';\nimport { ServerContext } from '@/state/server';\nimport { useDeepCompareEffect } from '@/plugins/useDeepCompareEffect';\nimport Select from '@/components/elements/Select';\nimport isEqual from 'react-fast-compare';\nimport Input from '@/components/elements/Input';\nimport setSelectedDockerImage from '@/api/server/setSelectedDockerImage';\nimport InputSpinner from '@/components/elements/InputSpinner';\nimport useFlash from '@/plugins/useFlash';\nimport updateStartupEgg from '@/api/server/updateStartupEgg';\nimport { usePermissions } from '@/plugins/usePermissions';\nimport FlashMessageRender from '@/components/FlashMessageRender';\n\nconst StartupContainer = () => {\n    const [loading, setLoading] = useState(false);\n    const [eggLoading, setEggLoading] = useState(false);\n    const [selectedNestId, setSelectedNestId] = useState<number | undefined>(undefined);\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const variables = ServerContext.useStoreState(\n        ({ server }) => ({\n            variables: server.data!.variables,\n            invocation: server.data!.invocation,\n            dockerImage: server.data!.dockerImage,\n        }),\n        isEqual\n    );\n\n    const { data, error, isValidating, mutate } = getServerStartup(uuid, {\n        ...variables,\n        dockerImages: { [variables.dockerImage]: variables.dockerImage },\n    });\n\n    const setServerFromState = ServerContext.useStoreActions((actions) => actions.server.setServerFromState);\n    const isCustomImage =\n        data &&\n        !Object.values(data.dockerImages)\n            .map((v) => v.toLowerCase())\n            .includes(variables.dockerImage.toLowerCase());\n\n    const [canChangeEgg] = usePermissions(['startup.egg-change']);\n\n    // Sync selectedNestId with data.currentNestId on first load only (when selectedNestId is undefined)\n    useEffect(() => {\n        if (data?.currentNestId !== undefined && selectedNestId === undefined) {\n            setSelectedNestId(data.currentNestId);\n        }\n    }, [data?.currentNestId, selectedNestId]);\n\n    useEffect(() => {\n        // Since we're passing in initial data this will not trigger on mount automatically. We\n        // want to always fetch fresh information from the API however when we're loading the startup\n        // information.\n        mutate();\n    }, []);\n\n    useDeepCompareEffect(() => {\n        if (!data) return;\n\n        setServerFromState((s) => ({\n            ...s,\n            invocation: data.invocation,\n            variables: data.variables,\n        }));\n    }, [data]);\n\n    const updateSelectedDockerImage = useCallback(\n        (v: React.ChangeEvent<HTMLSelectElement>) => {\n            setLoading(true);\n            clearFlashes('startup:image');\n\n            const image = v.currentTarget.value;\n            setSelectedDockerImage(uuid, image)\n                .then(() => setServerFromState((s) => ({ ...s, dockerImage: image })))\n                .catch((error) => {\n                    console.error(error);\n                    clearAndAddHttpError({ key: 'startup:image', error });\n                })\n                .then(() => setLoading(false));\n        },\n        [uuid]\n    );\n\n    const handleEggChange = useCallback(\n        (eggId: number) => {\n            setEggLoading(true);\n            clearFlashes('startup:egg');\n\n            updateStartupEgg(uuid, eggId)\n                .then((response) => {\n                    // Pick first docker image from the new egg as the current image\n                    const firstDockerImage = Object.values(response.dockerImages)[0] || variables.dockerImage;\n\n                    setSelectedNestId(response.currentNestId);\n                    mutate(\n                        () => ({\n                            invocation: response.invocation,\n                            variables: response.variables,\n                            dockerImages: response.dockerImages,\n                            eggChangeMode: response.eggChangeMode,\n                            nests: response.nests,\n                            currentEggId: response.currentEggId,\n                            currentNestId: response.currentNestId,\n                        }),\n                        false\n                    );\n                    // Fix: also update dockerImage so the Docker image section reflects the new egg\n                    setServerFromState((s) => ({\n                        ...s,\n                        invocation: response.invocation,\n                        variables: response.variables,\n                        dockerImage: firstDockerImage,\n                    }));\n                })\n                .catch((error) => {\n                    console.error(error);\n                    clearAndAddHttpError({ key: 'startup:egg', error });\n                })\n                .then(() => setEggLoading(false));\n        },\n        [uuid]\n    );\n\n    // Handle nest group change:\n    // - In all modes that show the nest dropdown, switching nest auto-applies the first egg.\n    const handleNestChange = useCallback(\n        (nestId: number) => {\n            setSelectedNestId(nestId);\n            const nest = data?.nests?.find((n) => n.id === nestId);\n            if (nest && nest.eggs.length > 0) {\n                handleEggChange(nest.eggs[0].id);\n            }\n        },\n        [data, handleEggChange]\n    );\n\n    const eggChangeMode = data?.eggChangeMode;\n    const showNestDropdown = eggChangeMode === 'both';\n    const showEggDropdown = eggChangeMode === 'egg_only' || eggChangeMode === 'both';\n    const showEggChangeSection = canChangeEgg && eggChangeMode && data?.nests;\n\n    const currentNest = data?.nests?.find((n) => n.id === selectedNestId);\n\n    return !data ? (\n        !error || (error && isValidating) ? (\n            <Spinner centered size={Spinner.Size.LARGE} />\n        ) : (\n            <ServerError title={'卧槽!'} message={httpErrorToHuman(error)} onRetry={() => mutate()} />\n        )\n    ) : (\n        <ServerContentBlock title={'启动设置'} showFlashKey={'startup:image'}>\n            <FlashMessageRender byKey={'startup:egg'} css={tw`mb-4`} />\n            <div css={tw`md:flex`}>\n                <TitledGreyBox title={'启动命令'} css={tw`flex-1`}>\n                    <div css={tw`px-1 py-2`}>\n                        <p css={tw`font-mono bg-neutral-900 rounded py-2 px-4`}>{data.invocation}</p>\n                    </div>\n                </TitledGreyBox>\n                <TitledGreyBox title={'Docker 镜像'} css={tw`flex-1 lg:flex-none lg:w-1/3 mt-8 md:mt-0 md:ml-10`}>\n                    {Object.keys(data.dockerImages).length > 1 && !isCustomImage ? (\n                        <>\n                            <InputSpinner visible={loading}>\n                                <Select\n                                    disabled={Object.keys(data.dockerImages).length < 2}\n                                    onChange={updateSelectedDockerImage}\n                                    value={variables.dockerImage}\n                                >\n                                    {Object.keys(data.dockerImages).map((key) => (\n                                        <option key={data.dockerImages[key]} value={data.dockerImages[key]}>\n                                            {key}\n                                        </option>\n                                    ))}\n                                </Select>\n                            </InputSpinner>\n                            <p css={tw`text-xs text-neutral-300 mt-2`}>\n                                这是一项高级设置，其允许您选择在运行此服务器时使用的 Docker 映像。\n                            </p>\n                        </>\n                    ) : (\n                        <>\n                            <Input disabled readOnly value={variables.dockerImage} />\n                            {isCustomImage && (\n                                <p css={tw`text-xs text-neutral-300 mt-2`}>\n                                    这个服务器的 Docker 镜像已由管理员手动设置，无法通过此界面更改。\n                                </p>\n                            )}\n                        </>\n                    )}\n                </TitledGreyBox>\n            </div>\n            {showEggChangeSection && (\n                <div css={tw`mt-8`}>\n                    <TitledGreyBox title={'切换预设'}>\n                        <InputSpinner visible={eggLoading}>\n                            <div css={tw`md:flex md:gap-4`}>\n                                {showNestDropdown && (\n                                    <div css={tw`flex-1`}>\n                                        <label css={tw`block text-xs text-neutral-300 mb-1`}>预设组</label>\n                                        <Select\n                                            value={selectedNestId}\n                                            onChange={(e) => handleNestChange(parseInt(e.currentTarget.value))}\n                                        >\n                                            {data.nests!.map((nest) => (\n                                                <option key={nest.id} value={nest.id}>\n                                                    {nest.name}\n                                                </option>\n                                            ))}\n                                        </Select>\n                                    </div>\n                                )}\n                                {showEggDropdown && (\n                                    <div css={[tw`flex-1`, showNestDropdown && tw`mt-4 md:mt-0`]}>\n                                        <label css={tw`block text-xs text-neutral-300 mb-1`}>预设</label>\n                                        <Select\n                                            value={data.currentEggId}\n                                            onChange={(e) => handleEggChange(parseInt(e.currentTarget.value))}\n                                        >\n                                            {(\n                                                currentNest || data.nests!.find((n) => n.id === data.currentNestId)\n                                            )?.eggs.map((egg) => (\n                                                <option key={egg.id} value={egg.id}>\n                                                    {egg.name}\n                                                </option>\n                                            ))}\n                                        </Select>\n                                    </div>\n                                )}\n                            </div>\n                        </InputSpinner>\n                        <p css={tw`text-xs text-neutral-300 mt-2`}>\n                            切换预设后服务器将使用新预设的启动命令，您可能需要重新安装服务器以应用更改。\n                        </p>\n                    </TitledGreyBox>\n                </div>\n            )}\n            <h3 css={tw`mt-8 mb-2 text-2xl`}>变量</h3>\n            <div css={tw`grid gap-8 md:grid-cols-2`}>\n                {data.variables.map((variable) => (\n                    <VariableBox key={variable.envVariable} variable={variable} />\n                ))}\n            </div>\n        </ServerContentBlock>\n    );\n};\n\nexport default StartupContainer;\n"
  },
  {
    "path": "resources/scripts/components/server/startup/VariableBox.tsx",
    "content": "import React, { memo, useState } from 'react';\nimport { ServerEggVariable } from '@/api/server/types';\nimport TitledGreyBox from '@/components/elements/TitledGreyBox';\nimport { usePermissions } from '@/plugins/usePermissions';\nimport InputSpinner from '@/components/elements/InputSpinner';\nimport Input from '@/components/elements/Input';\nimport Switch from '@/components/elements/Switch';\nimport { debounce } from 'debounce';\nimport updateStartupVariable from '@/api/server/updateStartupVariable';\nimport useFlash from '@/plugins/useFlash';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport getServerStartup from '@/api/swr/getServerStartup';\nimport Select from '@/components/elements/Select';\nimport isEqual from 'react-fast-compare';\nimport { ServerContext } from '@/state/server';\n\ninterface Props {\n    variable: ServerEggVariable;\n}\n\nconst VariableBox = ({ variable }: Props) => {\n    const FLASH_KEY = `server:startup:${variable.envVariable}`;\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const [loading, setLoading] = useState(false);\n    const [canEdit] = usePermissions(['startup.update']);\n    const { clearFlashes, clearAndAddHttpError } = useFlash();\n    const { mutate } = getServerStartup(uuid);\n\n    const setVariableValue = debounce((value: string) => {\n        setLoading(true);\n        clearFlashes(FLASH_KEY);\n\n        updateStartupVariable(uuid, variable.envVariable, value)\n            .then(([response, invocation]) =>\n                mutate(\n                    (data) => ({\n                        ...data,\n                        invocation,\n                        variables: (data.variables || []).map((v) =>\n                            v.envVariable === response.envVariable ? response : v\n                        ),\n                    }),\n                    false\n                )\n            )\n            .catch((error) => {\n                console.error(error);\n                clearAndAddHttpError({ error, key: FLASH_KEY });\n            })\n            .then(() => setLoading(false));\n    }, 500);\n\n    const useSwitch = variable.rules.some(\n        (v) => v === 'boolean' || v === 'in:0,1' || v === 'in:1,0' || v === 'in:true,false' || v === 'in:false,true'\n    );\n    const isStringSwitch = variable.rules.some((v) => v === 'string');\n    const selectValues = variable.rules.find((v) => v.startsWith('in:'))?.split(',') || [];\n\n    return (\n        <TitledGreyBox\n            title={\n                <p className='text-sm uppercase'>\n                    {!variable.isEditable && (\n                        <span className='bg-neutral-700 text-xs py-1 px-2 rounded-full mr-2 mb-1'>只读</span>\n                    )}\n                    {variable.name}\n                </p>\n            }\n        >\n            <FlashMessageRender byKey={FLASH_KEY} className='mb-2 md:mb-4' />\n            <InputSpinner visible={loading}>\n                {useSwitch ? (\n                    <>\n                        <Switch\n                            readOnly={!canEdit || !variable.isEditable}\n                            name={variable.envVariable}\n                            defaultChecked={\n                                isStringSwitch ? variable.serverValue === 'true' : variable.serverValue === '1'\n                            }\n                            onChange={() => {\n                                if (canEdit && variable.isEditable) {\n                                    if (isStringSwitch) {\n                                        setVariableValue(variable.serverValue === 'true' ? 'false' : 'true');\n                                    } else {\n                                        setVariableValue(variable.serverValue === '1' ? '0' : '1');\n                                    }\n                                }\n                            }}\n                        />\n                    </>\n                ) : (\n                    <>\n                        {selectValues.length > 0 ? (\n                            <>\n                                <Select\n                                    onChange={(e) => setVariableValue(e.target.value)}\n                                    name={variable.envVariable}\n                                    defaultValue={variable.serverValue ?? variable.defaultValue}\n                                    disabled={!canEdit || !variable.isEditable}\n                                >\n                                    {selectValues.map((selectValue) => (\n                                        <option\n                                            key={selectValue.replace('in:', '')}\n                                            value={selectValue.replace('in:', '')}\n                                        >\n                                            {selectValue.replace('in:', '')}\n                                        </option>\n                                    ))}\n                                </Select>\n                            </>\n                        ) : (\n                            <>\n                                <Input\n                                    onKeyUp={(e) => {\n                                        if (canEdit && variable.isEditable) {\n                                            setVariableValue(e.currentTarget.value);\n                                        }\n                                    }}\n                                    readOnly={!canEdit || !variable.isEditable}\n                                    name={variable.envVariable}\n                                    defaultValue={variable.serverValue ?? ''}\n                                    placeholder={variable.defaultValue}\n                                />\n                            </>\n                        )}\n                    </>\n                )}\n            </InputSpinner>\n\n            <p className='mt-1 text-xs text-neutral-300'>{variable.description}</p>\n        </TitledGreyBox>\n    );\n};\n\nexport default memo(VariableBox, isEqual);\n"
  },
  {
    "path": "resources/scripts/components/server/users/AddSubuserButton.tsx",
    "content": "import React, { useState } from 'react';\nimport EditSubuserModal from '@/components/server/users/EditSubuserModal';\nimport { Button } from '@/components/elements/button/index';\n\nexport default () => {\n    const [visible, setVisible] = useState(false);\n\n    return (\n        <>\n            <EditSubuserModal visible={visible} onModalDismissed={() => setVisible(false)} />\n            <Button onClick={() => setVisible(true)}>新用户</Button>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/users/EditSubuserModal.tsx",
    "content": "import React, { useContext, useEffect, useRef } from 'react';\nimport { Subuser } from '@/state/server/subusers';\nimport { Form, Formik } from 'formik';\nimport { array, object, string } from 'yup';\nimport Field from '@/components/elements/Field';\nimport { Actions, useStoreActions, useStoreState } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport createOrUpdateSubuser from '@/api/server/users/createOrUpdateSubuser';\nimport { ServerContext } from '@/state/server';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport Can from '@/components/elements/Can';\nimport { usePermissions } from '@/plugins/usePermissions';\nimport { useDeepCompareMemo } from '@/plugins/useDeepCompareMemo';\nimport tw from 'twin.macro';\nimport Button from '@/components/elements/Button';\nimport PermissionTitleBox from '@/components/server/users/PermissionTitleBox';\nimport asModal from '@/hoc/asModal';\nimport PermissionRow from '@/components/server/users/PermissionRow';\nimport ModalContext from '@/context/ModalContext';\n\ntype Props = {\n    subuser?: Subuser;\n};\n\ninterface Values {\n    email: string;\n    permissions: string[];\n}\n\nconst EditSubuserModal = ({ subuser }: Props) => {\n    const ref = useRef<HTMLHeadingElement>(null);\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const appendSubuser = ServerContext.useStoreActions((actions) => actions.subusers.appendSubuser);\n    const { clearFlashes, clearAndAddHttpError } = useStoreActions(\n        (actions: Actions<ApplicationStore>) => actions.flashes\n    );\n    const { dismiss, setPropOverrides } = useContext(ModalContext);\n\n    const isRootAdmin = useStoreState((state) => state.user.data!.rootAdmin);\n    const permissions = useStoreState((state) => state.permissions.data);\n    // The currently logged in user's permissions. We're going to filter out any permissions\n    // that they should not need.\n    const loggedInPermissions = ServerContext.useStoreState((state) => state.server.permissions);\n    const [canEditUser] = usePermissions(subuser ? ['user.update'] : ['user.create']);\n\n    // The permissions that can be modified by this user.\n    const editablePermissions = useDeepCompareMemo(() => {\n        const cleaned = Object.keys(permissions).map((key) =>\n            Object.keys(permissions[key].keys).map((pkey) => `${key}.${pkey}`)\n        );\n\n        const list: string[] = ([] as string[]).concat.apply([], Object.values(cleaned));\n\n        if (isRootAdmin || (loggedInPermissions.length === 1 && loggedInPermissions[0] === '*')) {\n            return list;\n        }\n\n        return list.filter((key) => loggedInPermissions.indexOf(key) >= 0);\n    }, [isRootAdmin, permissions, loggedInPermissions]);\n\n    const submit = (values: Values) => {\n        setPropOverrides({ showSpinnerOverlay: true });\n        clearFlashes('user:edit');\n\n        createOrUpdateSubuser(uuid, values, subuser)\n            .then((subuser) => {\n                appendSubuser(subuser);\n                dismiss();\n            })\n            .catch((error) => {\n                console.error(error);\n                setPropOverrides(null);\n                clearAndAddHttpError({ key: 'user:edit', error });\n\n                if (ref.current) {\n                    ref.current.scrollIntoView();\n                }\n            });\n    };\n\n    useEffect(\n        () => () => {\n            clearFlashes('user:edit');\n        },\n        []\n    );\n\n    return (\n        <Formik\n            onSubmit={submit}\n            initialValues={\n                {\n                    email: subuser?.email || '',\n                    permissions: subuser?.permissions || [],\n                } as Values\n            }\n            validationSchema={object().shape({\n                email: string()\n                    .max(191, '电子邮箱地址不得超过 191 个字符。')\n                    .email('必须提供有效的电子邮箱地址。')\n                    .required('必须提供有效的电子邮箱地址。'),\n                permissions: array().of(string()),\n            })}\n        >\n            <Form>\n                <div css={tw`flex justify-between`}>\n                    <h2 css={tw`text-2xl`} ref={ref}>\n                        {subuser ? `${canEditUser ? '修改' : '查看'} ${subuser.email} 的权限` : '创建新子用户'}\n                    </h2>\n                    <div>\n                        <Button type={'submit'} css={tw`w-full sm:w-auto`}>\n                            {subuser ? '保存' : '邀请用户'}\n                        </Button>\n                    </div>\n                </div>\n                <FlashMessageRender byKey={'user:edit'} css={tw`mt-4`} />\n                {!isRootAdmin && loggedInPermissions[0] !== '*' && (\n                    <div css={tw`mt-4 pl-4 py-2 border-l-4 border-cyan-400`}>\n                        <p css={tw`text-sm text-neutral-300`}>创建或修改其他用户时，只能选择您帐户当前分配的权限。</p>\n                    </div>\n                )}\n                {!subuser && (\n                    <div css={tw`mt-6`}>\n                        <Field\n                            name={'email'}\n                            label={'用户邮箱地址'}\n                            description={'输入您希望邀请为该服务器子用户的用户的电子邮箱地址。'}\n                        />\n                    </div>\n                )}\n                <div css={tw`my-6`}>\n                    {Object.keys(permissions)\n                        .filter((key) => key !== 'websocket')\n                        .map((key, index) => (\n                            <PermissionTitleBox\n                                key={`permission_${key}`}\n                                title={key}\n                                isEditable={canEditUser}\n                                permissions={Object.keys(permissions[key].keys).map((pkey) => `${key}.${pkey}`)}\n                                css={index > 0 ? tw`mt-4` : undefined}\n                            >\n                                <p css={tw`text-sm text-neutral-400 mb-4`}>{permissions[key].description}</p>\n                                {Object.keys(permissions[key].keys).map((pkey) => (\n                                    <PermissionRow\n                                        key={`permission_${key}.${pkey}`}\n                                        permission={`${key}.${pkey}`}\n                                        disabled={!canEditUser || editablePermissions.indexOf(`${key}.${pkey}`) < 0}\n                                    />\n                                ))}\n                            </PermissionTitleBox>\n                        ))}\n                </div>\n                <Can action={subuser ? 'user.update' : 'user.create'}>\n                    <div css={tw`pb-6 flex justify-end`}>\n                        <Button type={'submit'} css={tw`w-full sm:w-auto`}>\n                            {subuser ? '保存' : '邀请用户'}\n                        </Button>\n                    </div>\n                </Can>\n            </Form>\n        </Formik>\n    );\n};\n\nexport default asModal<Props>({\n    top: false,\n})(EditSubuserModal);\n"
  },
  {
    "path": "resources/scripts/components/server/users/PermissionRow.tsx",
    "content": "import styled from 'styled-components/macro';\nimport tw from 'twin.macro';\nimport Checkbox from '@/components/elements/Checkbox';\nimport React from 'react';\nimport { useStoreState } from 'easy-peasy';\nimport Label from '@/components/elements/Label';\n\nconst Container = styled.label`\n    ${tw`flex items-center border border-transparent rounded md:p-2 transition-colors duration-75`};\n    text-transform: none;\n\n    &:not(.disabled) {\n        ${tw`cursor-pointer`};\n\n        &:hover {\n            ${tw`border-neutral-500 bg-neutral-800`};\n        }\n    }\n\n    &:not(:first-of-type) {\n        ${tw`mt-4 sm:mt-2`};\n    }\n\n    &.disabled {\n        ${tw`opacity-50`};\n\n        & input[type='checkbox']:not(:checked) {\n            ${tw`border-0`};\n        }\n    }\n`;\n\ninterface Props {\n    permission: string;\n    disabled: boolean;\n}\n\nconst PermissionRow = ({ permission, disabled }: Props) => {\n    const [key, pkey] = permission.split('.', 2);\n    const permissions = useStoreState((state) => state.permissions.data);\n\n    return (\n        <Container htmlFor={`permission_${permission}`} className={disabled ? 'disabled' : undefined}>\n            <div css={tw`p-2`}>\n                <Checkbox\n                    id={`permission_${permission}`}\n                    name={'permissions'}\n                    value={permission}\n                    css={tw`w-5 h-5 mr-2`}\n                    disabled={disabled}\n                />\n            </div>\n            <div css={tw`flex-1`}>\n                <Label as={'p'} css={tw`font-medium`}>\n                    {pkey}\n                </Label>\n                {permissions[key].keys[pkey].length > 0 && (\n                    <p css={tw`text-xs text-neutral-400 mt-1`}>{permissions[key].keys[pkey]}</p>\n                )}\n            </div>\n        </Container>\n    );\n};\n\nexport default PermissionRow;\n"
  },
  {
    "path": "resources/scripts/components/server/users/PermissionTitleBox.tsx",
    "content": "import React, { memo, useCallback } from 'react';\nimport { useField } from 'formik';\nimport TitledGreyBox from '@/components/elements/TitledGreyBox';\nimport tw from 'twin.macro';\nimport Input from '@/components/elements/Input';\nimport isEqual from 'react-fast-compare';\n\ninterface Props {\n    isEditable: boolean;\n    title: string;\n    permissions: string[];\n    className?: string;\n}\n\nconst PermissionTitleBox: React.FC<Props> = memo(({ isEditable, title, permissions, className, children }) => {\n    const [{ value }, , { setValue }] = useField<string[]>('permissions');\n\n    const onCheckboxClicked = useCallback(\n        (e: React.ChangeEvent<HTMLInputElement>) => {\n            if (e.currentTarget.checked) {\n                setValue([...value, ...permissions.filter((p) => !value.includes(p))]);\n            } else {\n                setValue(value.filter((p) => !permissions.includes(p)));\n            }\n        },\n        [permissions, value]\n    );\n\n    return (\n        <TitledGreyBox\n            title={\n                <div css={tw`flex items-center`}>\n                    <p css={tw`text-sm uppercase flex-1`}>{title}</p>\n                    {isEditable && (\n                        <Input\n                            type={'checkbox'}\n                            checked={permissions.every((p) => value.includes(p))}\n                            onChange={onCheckboxClicked}\n                        />\n                    )}\n                </div>\n            }\n            className={className}\n        >\n            {children}\n        </TitledGreyBox>\n    );\n}, isEqual);\n\nexport default PermissionTitleBox;\n"
  },
  {
    "path": "resources/scripts/components/server/users/RemoveSubuserButton.tsx",
    "content": "import React, { useState } from 'react';\nimport ConfirmationModal from '@/components/elements/ConfirmationModal';\nimport { ServerContext } from '@/state/server';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faTrashAlt } from '@fortawesome/free-solid-svg-icons';\nimport { Subuser } from '@/state/server/subusers';\nimport deleteSubuser from '@/api/server/users/deleteSubuser';\nimport { Actions, useStoreActions } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport { httpErrorToHuman } from '@/api/http';\nimport tw from 'twin.macro';\n\nexport default ({ subuser }: { subuser: Subuser }) => {\n    const [loading, setLoading] = useState(false);\n    const [showConfirmation, setShowConfirmation] = useState(false);\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const removeSubuser = ServerContext.useStoreActions((actions) => actions.subusers.removeSubuser);\n    const { addError, clearFlashes } = useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n\n    const doDeletion = () => {\n        setLoading(true);\n        clearFlashes('users');\n        deleteSubuser(uuid, subuser.uuid)\n            .then(() => {\n                setLoading(false);\n                removeSubuser(subuser.uuid);\n            })\n            .catch((error) => {\n                console.error(error);\n                addError({ key: 'users', message: httpErrorToHuman(error) });\n                setShowConfirmation(false);\n            });\n    };\n\n    return (\n        <>\n            <ConfirmationModal\n                title={'删除此子用户?'}\n                buttonText={'确定'}\n                visible={showConfirmation}\n                showSpinnerOverlay={loading}\n                onConfirmed={() => doDeletion()}\n                onModalDismissed={() => setShowConfirmation(false)}\n            >\n                您确定要删除此子用户吗？ 他们将立即失去对该服务器的所有访问权限。\n            </ConfirmationModal>\n            <button\n                type={'button'}\n                aria-label={'删除子用户'}\n                css={tw`block text-sm p-2 text-neutral-500 hover:text-red-600 transition-colors duration-150`}\n                onClick={() => setShowConfirmation(true)}\n            >\n                <FontAwesomeIcon icon={faTrashAlt} />\n            </button>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/users/UserRow.tsx",
    "content": "import React, { useState } from 'react';\nimport { Subuser } from '@/state/server/subusers';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faPencilAlt, faUnlockAlt, faUserLock } from '@fortawesome/free-solid-svg-icons';\nimport RemoveSubuserButton from '@/components/server/users/RemoveSubuserButton';\nimport EditSubuserModal from '@/components/server/users/EditSubuserModal';\nimport Can from '@/components/elements/Can';\nimport { useStoreState } from 'easy-peasy';\nimport tw from 'twin.macro';\nimport GreyRowBox from '@/components/elements/GreyRowBox';\n\ninterface Props {\n    subuser: Subuser;\n}\n\nexport default ({ subuser }: Props) => {\n    const uuid = useStoreState((state) => state.user!.data!.uuid);\n    const [visible, setVisible] = useState(false);\n\n    return (\n        <GreyRowBox css={tw`mb-2`}>\n            <EditSubuserModal subuser={subuser} visible={visible} onModalDismissed={() => setVisible(false)} />\n            <div css={tw`w-10 h-10 rounded-full bg-white border-2 border-neutral-800 overflow-hidden hidden md:block`}>\n                <img css={tw`w-full h-full`} src={`${subuser.image}?s=400`} />\n            </div>\n            <div css={tw`ml-4 flex-1 overflow-hidden`}>\n                <p css={tw`text-sm truncate`}>{subuser.email}</p>\n            </div>\n            <div css={tw`ml-4`}>\n                <p css={tw`font-medium text-center`}>\n                    &nbsp;\n                    <FontAwesomeIcon\n                        icon={subuser.twoFactorEnabled ? faUserLock : faUnlockAlt}\n                        fixedWidth\n                        css={!subuser.twoFactorEnabled ? tw`text-red-400` : undefined}\n                    />\n                    &nbsp;\n                </p>\n                <p css={tw`text-2xs text-neutral-500 uppercase hidden md:block`}>动态口令认证已启用</p>\n            </div>\n            <div css={tw`ml-4 hidden md:block`}>\n                <p css={tw`font-medium text-center`}>\n                    {subuser.permissions.filter((permission) => permission !== 'websocket.connect').length}\n                </p>\n                <p css={tw`text-2xs text-neutral-500 uppercase`}>权限</p>\n            </div>\n            {subuser.uuid !== uuid && (\n                <>\n                    <Can action={'user.update'}>\n                        <button\n                            type={'button'}\n                            aria-label={'编辑子用户'}\n                            css={tw`block text-sm p-1 md:p-2 text-neutral-500 hover:text-neutral-100 transition-colors duration-150 mx-4`}\n                            onClick={() => setVisible(true)}\n                        >\n                            <FontAwesomeIcon icon={faPencilAlt} />\n                        </button>\n                    </Can>\n                    <Can action={'user.delete'}>\n                        <RemoveSubuserButton subuser={subuser} />\n                    </Can>\n                </>\n            )}\n        </GreyRowBox>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/server/users/UsersContainer.tsx",
    "content": "import React, { useEffect, useState } from 'react';\nimport { ServerContext } from '@/state/server';\nimport { Actions, useStoreActions, useStoreState } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\nimport Spinner from '@/components/elements/Spinner';\nimport AddSubuserButton from '@/components/server/users/AddSubuserButton';\nimport UserRow from '@/components/server/users/UserRow';\nimport FlashMessageRender from '@/components/FlashMessageRender';\nimport getServerSubusers from '@/api/server/users/getServerSubusers';\nimport { httpErrorToHuman } from '@/api/http';\nimport Can from '@/components/elements/Can';\nimport ServerContentBlock from '@/components/elements/ServerContentBlock';\nimport tw from 'twin.macro';\n\nexport default () => {\n    const [loading, setLoading] = useState(true);\n\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const subusers = ServerContext.useStoreState((state) => state.subusers.data);\n    const setSubusers = ServerContext.useStoreActions((actions) => actions.subusers.setSubusers);\n\n    const permissions = useStoreState((state: ApplicationStore) => state.permissions.data);\n    const getPermissions = useStoreActions((actions: Actions<ApplicationStore>) => actions.permissions.getPermissions);\n    const { addError, clearFlashes } = useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n\n    useEffect(() => {\n        clearFlashes('users');\n        getServerSubusers(uuid)\n            .then((subusers) => {\n                setSubusers(subusers);\n                setLoading(false);\n            })\n            .catch((error) => {\n                console.error(error);\n                addError({ key: 'users', message: httpErrorToHuman(error) });\n            });\n    }, []);\n\n    useEffect(() => {\n        getPermissions().catch((error) => {\n            addError({ key: 'users', message: httpErrorToHuman(error) });\n            console.error(error);\n        });\n    }, []);\n\n    if (!subusers.length && (loading || !Object.keys(permissions).length)) {\n        return <Spinner size={'large'} centered />;\n    }\n\n    return (\n        <ServerContentBlock title={'子用户管理'}>\n            <FlashMessageRender byKey={'users'} css={tw`mb-4`} />\n            {!subusers.length ? (\n                <p css={tw`text-center text-sm text-neutral-300`}>看起来您没有任何子用户。</p>\n            ) : (\n                subusers.map((subuser) => <UserRow key={subuser.uuid} subuser={subuser} />)\n            )}\n            <Can action={'user.create'}>\n                <div css={tw`flex justify-end mt-6`}>\n                    <AddSubuserButton />\n                </div>\n            </Can>\n        </ServerContentBlock>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/components/types.ts",
    "content": "export interface WithClassname {\n    className?: string;\n}\n"
  },
  {
    "path": "resources/scripts/context/ModalContext.ts",
    "content": "import React from 'react';\nimport { SettableModalProps } from '@/hoc/asModal';\n\nexport interface ModalContextValues {\n    dismiss: () => void;\n    setPropOverrides: (\n        value:\n            | ((current: Readonly<Partial<SettableModalProps>>) => Partial<SettableModalProps>)\n            | Partial<SettableModalProps>\n            | null\n    ) => void;\n}\n\nconst ModalContext = React.createContext<ModalContextValues>({\n    dismiss: () => null,\n    setPropOverrides: () => null,\n});\n\nModalContext.displayName = 'ModalContext';\n\nexport default ModalContext;\n"
  },
  {
    "path": "resources/scripts/easy-peasy.d.ts",
    "content": "// noinspection ES6UnusedImports\n// eslint-disable-next-line @typescript-eslint/no-unused-vars\nimport EasyPeasy, { Actions, State } from 'easy-peasy';\nimport { ApplicationStore } from '@/state';\n\ndeclare module 'easy-peasy' {\n    export function useStoreState<Result>(mapState: (state: State<ApplicationStore>) => Result): Result;\n\n    export function useStoreActions<Result>(mapActions: (actions: Actions<ApplicationStore>) => Result): Result;\n}\n"
  },
  {
    "path": "resources/scripts/globals.d.ts",
    "content": "declare module '*.jpg';\ndeclare module '*.png';\ndeclare module '*.svg';\ndeclare module '*.css';\n"
  },
  {
    "path": "resources/scripts/helpers.ts",
    "content": "export const randomInt = (low: number, high: number) => Math.floor(Math.random() * (high - low) + low);\n\nexport const cleanDirectoryPath = (path: string) => path.replace(/(\\/(\\/*))|(^$)/g, '/');\n\nexport function fileBitsToString(mode: string, directory: boolean): string {\n    const m = parseInt(mode, 8);\n\n    let buf = '';\n    'dalTLDpSugct?'.split('').forEach((c, i) => {\n        if ((m & (1 << (32 - 1 - i))) !== 0) {\n            buf = buf + c;\n        }\n    });\n\n    if (buf.length === 0) {\n        // If the file is directory, make sure it has the directory flag.\n        if (directory) {\n            buf = 'd';\n        } else {\n            buf = '-';\n        }\n    }\n\n    'rwxrwxrwx'.split('').forEach((c, i) => {\n        if ((m & (1 << (9 - 1 - i))) !== 0) {\n            buf = buf + c;\n        } else {\n            buf = buf + '-';\n        }\n    });\n\n    return buf;\n}\n\n/**\n * URL-encodes the segments of a path.\n * This allows to use the path as part of a URL while preserving the slashes.\n * @param path the path to encode\n */\nexport function encodePathSegments(path: string): string {\n    return path\n        .split('/')\n        .map((s) => encodeURIComponent(s))\n        .join('/');\n}\n\nexport function hashToPath(hash: string): string {\n    return hash.length > 0 ? decodeURIComponent(hash.substr(1)) : '/';\n}\n"
  },
  {
    "path": "resources/scripts/hoc/RequireServerPermission.tsx",
    "content": "import React from 'react';\nimport Can from '@/components/elements/Can';\nimport { ServerError } from '@/components/elements/ScreenBlock';\n\nexport interface RequireServerPermissionProps {\n    permissions: string | string[];\n}\n\nconst RequireServerPermission: React.FC<RequireServerPermissionProps> = ({ children, permissions }) => {\n    return (\n        <Can action={permissions} renderOnError={<ServerError title={'拒绝访问'} message={'您没有权限访问此页面。'} />}>\n            {children}\n        </Can>\n    );\n};\n\nexport default RequireServerPermission;\n"
  },
  {
    "path": "resources/scripts/hoc/asDialog.tsx",
    "content": "import React, { useState } from 'react';\nimport { Dialog, DialogProps, DialogWrapperContext, WrapperProps } from '@/components/elements/dialog';\n\nfunction asDialog(\n    initialProps?: WrapperProps\n    // eslint-disable-next-line @typescript-eslint/ban-types\n): <P extends {}>(C: React.ComponentType<P>) => React.FunctionComponent<P & DialogProps> {\n    return function (Component) {\n        return function ({ open, onClose, ...rest }) {\n            const [props, setProps] = useState<WrapperProps>(initialProps || {});\n\n            return (\n                <DialogWrapperContext.Provider value={{ props, setProps, close: onClose }}>\n                    <Dialog {...props} open={open} onClose={onClose}>\n                        <Component {...(rest as React.ComponentProps<typeof Component>)} />\n                    </Dialog>\n                </DialogWrapperContext.Provider>\n            );\n        };\n    };\n}\n\nexport default asDialog;\n"
  },
  {
    "path": "resources/scripts/hoc/asModal.tsx",
    "content": "import React from 'react';\nimport PortaledModal, { ModalProps } from '@/components/elements/Modal';\nimport ModalContext, { ModalContextValues } from '@/context/ModalContext';\nimport isEqual from 'react-fast-compare';\n\nexport interface AsModalProps {\n    visible: boolean;\n    onModalDismissed?: () => void;\n}\n\nexport type SettableModalProps = Omit<ModalProps, 'appear' | 'visible' | 'onDismissed'>;\n\ninterface State {\n    render: boolean;\n    visible: boolean;\n    propOverrides: Partial<SettableModalProps>;\n}\n\ntype ExtendedComponentType<T> = (C: React.ComponentType<T>) => React.ComponentType<T & AsModalProps>;\n\n// eslint-disable-next-line @typescript-eslint/ban-types\nfunction asModal<P extends {}>(\n    modalProps?: SettableModalProps | ((props: P) => SettableModalProps)\n): ExtendedComponentType<P> {\n    return function (Component) {\n        return class extends React.PureComponent<P & AsModalProps, State> {\n            static displayName = `asModal(${Component.displayName})`;\n\n            constructor(props: P & AsModalProps) {\n                super(props);\n\n                this.state = {\n                    render: props.visible,\n                    visible: props.visible,\n                    propOverrides: {},\n                };\n            }\n\n            get computedModalProps(): Readonly<SettableModalProps & { visible: boolean }> {\n                return {\n                    ...(typeof modalProps === 'function' ? modalProps(this.props) : modalProps),\n                    ...this.state.propOverrides,\n                    visible: this.state.visible,\n                };\n            }\n\n            /**\n             * @this {React.PureComponent<P & AsModalProps, State>}\n             */\n            componentDidUpdate(prevProps: Readonly<P & AsModalProps>, prevState: Readonly<State>) {\n                if (prevProps.visible && !this.props.visible) {\n                    this.setState({ visible: false, propOverrides: {} });\n                } else if (!prevProps.visible && this.props.visible) {\n                    this.setState({ render: true, visible: true });\n                }\n                if (!this.state.render && !isEqual(prevState.propOverrides, this.state.propOverrides)) {\n                    this.setState({ propOverrides: {} });\n                }\n            }\n\n            dismiss = () => this.setState({ visible: false });\n\n            setPropOverrides: ModalContextValues['setPropOverrides'] = (value) =>\n                this.setState((state) => ({\n                    propOverrides: !value ? {} : typeof value === 'function' ? value(state.propOverrides) : value,\n                }));\n\n            /**\n             * @this {React.PureComponent<P & AsModalProps, State>}\n             */\n            render() {\n                if (!this.state.render) return null;\n\n                return (\n                    <PortaledModal\n                        appear\n                        onDismissed={() =>\n                            this.setState({ render: false }, () => {\n                                if (typeof this.props.onModalDismissed === 'function') {\n                                    this.props.onModalDismissed();\n                                }\n                            })\n                        }\n                        {...this.computedModalProps}\n                    >\n                        <ModalContext.Provider\n                            value={{\n                                dismiss: this.dismiss.bind(this),\n                                setPropOverrides: this.setPropOverrides.bind(this),\n                            }}\n                        >\n                            <Component {...this.props} />\n                        </ModalContext.Provider>\n                    </PortaledModal>\n                );\n            }\n        };\n    };\n}\n\nexport default asModal;\n"
  },
  {
    "path": "resources/scripts/i18n.ts",
    "content": "import i18n from 'i18next';\nimport { initReactI18next } from 'react-i18next';\nimport I18NextHttpBackend, { HttpBackendOptions } from 'i18next-http-backend';\nimport I18NextMultiloadBackendAdapter from 'i18next-multiload-backend-adapter';\n\n// If we're using HMR use a unique hash per page reload so that we're always\n// doing cache busting. Otherwise just use the builder provided hash value in\n// the URL to allow cache busting to occur whenever the front-end is rebuilt.\nconst hash = module.hot ? Date.now().toString(16) : process.env.WEBPACK_BUILD_HASH;\n\ni18n.use(I18NextMultiloadBackendAdapter)\n    .use(initReactI18next)\n    .init({\n        debug: process.env.DEBUG === 'true',\n        lng: 'zh',\n        fallbackLng: 'zh',\n        keySeparator: '.',\n        backend: {\n            backend: I18NextHttpBackend,\n            backendOption: {\n                loadPath: '/locales/locale.json?locale={{lng}}&namespace={{ns}}',\n                queryStringParams: { hash },\n                allowMultiLoading: true,\n            } as HttpBackendOptions,\n        } as Record<string, any>,\n        interpolation: {\n            // Per i18n-react documentation: this is not needed since React is already\n            // handling escapes for us.\n            escapeValue: false,\n        },\n    });\n\nexport default i18n;\n"
  },
  {
    "path": "resources/scripts/index.tsx",
    "content": "import React from 'react';\nimport ReactDOM from 'react-dom';\nimport App from '@/components/App';\nimport { setConfig } from 'react-hot-loader';\n\n// Enable language support.\nimport './i18n';\n\n// Prevents page reloads while making component changes which\n// also avoids triggering constant loading indicators all over\n// the place in development.\n//\n// @see https://github.com/gaearon/react-hot-loader#hook-support\nsetConfig({ reloadHooks: false });\n\nReactDOM.render(<App />, document.getElementById('app'));\n\n// 这条信息你不可以将之删除，一是记录了版本信息，二是为了原项目指向，如果你将之删除，那你需要承担相应的责任。否则请不要使用我们的汉化！\nconsole.log(\n    '\\n %c pterodactyl-china ' + ' %c https://github.com/pterodactyl-china/panel \\n\\n',\n    'background: #35495e; padding: 1px; border-radius: 3px 0 0 3px; color: #fff',\n    'background: #fadfa3; padding: 1px; border-radius: 0 3px 3px 0; color: #fff'\n);\n"
  },
  {
    "path": "resources/scripts/lib/formatters.spec.ts",
    "content": "import { bytesToString, ip, mbToBytes } from '@/lib/formatters';\n\ndescribe('@/lib/formatters.ts', function () {\n    describe('mbToBytes()', function () {\n        it('should convert from MB to Bytes', function () {\n            expect(mbToBytes(1)).toBe(1_048_576);\n            expect(mbToBytes(0)).toBe(0);\n            expect(mbToBytes(0.1)).toBe(104_857);\n            expect(mbToBytes(0.001)).toBe(1_048);\n            expect(mbToBytes(1024)).toBe(1_073_741_824);\n        });\n    });\n\n    describe('bytesToString()', function () {\n        it.each([\n            [0, '0 Bytes'],\n            [0.5, '0 Bytes'],\n            [0.9, '0 Bytes'],\n            [100, '100 Bytes'],\n            [100.25, '100.25 Bytes'],\n            [100.998, '101 Bytes'],\n            [512, '512 Bytes'],\n            [1000, '1000 Bytes'],\n            [1024, '1 KiB'],\n            [5068, '4.95 KiB'],\n            [10_000, '9.77 KiB'],\n            [10_240, '10 KiB'],\n            [11_864, '11.59 KiB'],\n            [1_000_000, '976.56 KiB'],\n            [1_024_000, '1000 KiB'],\n            [1_025_000, '1000.98 KiB'],\n            [1_048_576, '1 MiB'],\n            [1_356_000, '1.29 MiB'],\n            [1_000_000_000, '953.67 MiB'],\n            [1_070_000_100, '1020.43 MiB'],\n            [1_073_741_824, '1 GiB'],\n            [1_678_342_000, '1.56 GiB'],\n            [1_000_000_000_000, '931.32 GiB'],\n            [1_099_511_627_776, '1 TiB'],\n        ])('should format %d bytes as \"%s\"', function (input, output) {\n            expect(bytesToString(input)).toBe(output);\n        });\n    });\n\n    describe('ip()', function () {\n        it('should format an IPv4 address', function () {\n            expect(ip('127.0.0.1')).toBe('127.0.0.1');\n        });\n\n        it('should format an IPv6 address', function () {\n            expect(ip(':::1')).toBe('[:::1]');\n            expect(ip('2001:db8::')).toBe('[2001:db8::]');\n        });\n\n        it('should handle random inputs', function () {\n            expect(ip('1')).toBe('1');\n            expect(ip('foobar')).toBe('foobar');\n            expect(ip('127.0.0.1:25565')).toBe('[127.0.0.1:25565]');\n        });\n    });\n});\n"
  },
  {
    "path": "resources/scripts/lib/formatters.ts",
    "content": "const _CONVERSION_UNIT = 1024;\n\n/**\n * Given a value in megabytes converts it back down into bytes.\n */\nfunction mbToBytes(megabytes: number): number {\n    return Math.floor(megabytes * _CONVERSION_UNIT * _CONVERSION_UNIT);\n}\n\n/**\n * Given an amount of bytes, converts them into a human readable string format\n * using \"1024\" as the divisor.\n */\nfunction bytesToString(bytes: number, decimals = 2): string {\n    const k = _CONVERSION_UNIT;\n\n    if (bytes < 1) return '0 Bytes';\n\n    decimals = Math.floor(Math.max(0, decimals));\n    const i = Math.floor(Math.log(bytes) / Math.log(k));\n    const value = Number((bytes / Math.pow(k, i)).toFixed(decimals));\n\n    return `${value} ${['Bytes', 'KiB', 'MiB', 'GiB', 'TiB'][i]}`;\n}\n\n/**\n * Formats an IPv4 or IPv6 address.\n */\nfunction ip(value: string): string {\n    // noinspection RegExpSimplifiable\n    return /([a-f0-9:]+:+)+[a-f0-9]+/.test(value) ? `[${value}]` : value;\n}\n\nexport { ip, mbToBytes, bytesToString };\n"
  },
  {
    "path": "resources/scripts/lib/helpers.spec.ts",
    "content": "import { hexToRgba } from '@/lib/helpers';\n\ndescribe('@/lib/helpers.ts', function () {\n    describe('hexToRgba()', function () {\n        it('should return the expected rgba', function () {\n            expect(hexToRgba('#ffffff')).toBe('rgba(255, 255, 255, 1)');\n            expect(hexToRgba('#00aabb')).toBe('rgba(0, 170, 187, 1)');\n            expect(hexToRgba('#efefef')).toBe('rgba(239, 239, 239, 1)');\n        });\n\n        it('should ignore case', function () {\n            expect(hexToRgba('#FF00A3')).toBe('rgba(255, 0, 163, 1)');\n        });\n\n        it('should allow alpha channel changes', function () {\n            expect(hexToRgba('#ece5a8', 0.5)).toBe('rgba(236, 229, 168, 0.5)');\n            expect(hexToRgba('#ece5a8', 0.1)).toBe('rgba(236, 229, 168, 0.1)');\n            expect(hexToRgba('#000000', 0)).toBe('rgba(0, 0, 0, 0)');\n        });\n\n        it('should handle invalid strings', function () {\n            expect(hexToRgba('')).toBe('');\n            expect(hexToRgba('foobar')).toBe('foobar');\n            expect(hexToRgba('#fff')).toBe('#fff');\n            expect(hexToRgba('#')).toBe('#');\n            expect(hexToRgba('#fffffy')).toBe('#fffffy');\n        });\n    });\n});\n"
  },
  {
    "path": "resources/scripts/lib/helpers.ts",
    "content": "/**\n * Given a valid six character HEX color code, converts it into its associated\n * RGBA value with a user controllable alpha channel.\n */\nfunction hexToRgba(hex: string, alpha = 1): string {\n    // noinspection RegExpSimplifiable\n    if (!/#?([a-fA-F0-9]{2}){3}/.test(hex)) {\n        return hex;\n    }\n\n    // noinspection RegExpSimplifiable\n    const [r, g, b] = hex.match(/[a-fA-F0-9]{2}/g)!.map((v) => parseInt(v, 16));\n\n    return `rgba(${r}, ${g}, ${b}, ${alpha})`;\n}\n\nexport { hexToRgba };\n"
  },
  {
    "path": "resources/scripts/lib/objects.spec.ts",
    "content": "import { isObject } from '@/lib/objects';\n\ndescribe('@/lib/objects.ts', function () {\n    describe('isObject()', function () {\n        it('should return true for objects', function () {\n            expect(isObject({})).toBe(true);\n            expect(isObject({ foo: 123 })).toBe(true);\n            expect(isObject(Object.freeze({}))).toBe(true);\n        });\n\n        it('should return false for null', function () {\n            expect(isObject(null)).toBe(false);\n        });\n\n        it.each([undefined, 123, 'foobar', () => ({}), Function, String(123), isObject, () => null, [], [1, 2, 3]])(\n            'should return false for %p',\n            function (value) {\n                expect(isObject(value)).toBe(false);\n            }\n        );\n    });\n});\n"
  },
  {
    "path": "resources/scripts/lib/objects.ts",
    "content": "/**\n * Determines if the value provided to the function is an object type that\n * is not null.\n */\nfunction isObject(val: unknown): val is Record<string, unknown> {\n    return typeof val === 'object' && val !== null && !Array.isArray(val);\n}\n\n/**\n * Determines if an object is truly empty by looking at the keys present\n * and the prototype value.\n */\n// eslint-disable-next-line @typescript-eslint/ban-types\nfunction isEmptyObject(val: {}): boolean {\n    return Object.keys(val).length === 0 && Object.getPrototypeOf(val) === Object.prototype;\n}\n\n/**\n * A helper function for use in TypeScript that returns all of the keys\n * for an object, but in a typed manner to make working with them a little\n * easier.\n */\n// eslint-disable-next-line @typescript-eslint/ban-types\nfunction getObjectKeys<T extends {}>(o: T): (keyof T)[] {\n    return Object.keys(o) as (keyof typeof o)[];\n}\n\nexport { isObject, isEmptyObject, getObjectKeys };\n"
  },
  {
    "path": "resources/scripts/lib/strings.spec.ts",
    "content": "import { capitalize } from '@/lib/strings';\n\ndescribe('@/lib/strings.ts', function () {\n    describe('capitalize()', function () {\n        it('should capitalize a string', function () {\n            expect(capitalize('foo bar')).toBe('Foo bar');\n            expect(capitalize('FOOBAR')).toBe('Foobar');\n        });\n\n        it('should handle empty strings', function () {\n            expect(capitalize('')).toBe('');\n        });\n    });\n});\n"
  },
  {
    "path": "resources/scripts/lib/strings.ts",
    "content": "function capitalize(value: string): string {\n    return value.charAt(0).toUpperCase() + value.slice(1).toLowerCase();\n}\n\nexport { capitalize };\n"
  },
  {
    "path": "resources/scripts/macros.d.ts",
    "content": "import { ComponentType, ReactElement } from 'react';\n// eslint-disable-next-line no-restricted-imports\nimport styledImport, { css as cssImport, CSSProp, StyledComponentProps } from 'styled-components';\n\ndeclare module 'react' {\n    interface Attributes {\n        css?: CSSProp;\n    }\n}\n\ndeclare module 'styled-components' {\n    interface StyledComponentBase<\n        C extends string | ComponentType<any>,\n        // eslint-disable-next-line @typescript-eslint/ban-types\n        T extends object,\n        // eslint-disable-next-line @typescript-eslint/ban-types\n        O extends object = {},\n        A extends keyof any = never\n    > extends ForwardRefExoticBase<StyledComponentProps<C, T, O, A>> {\n        (\n            props: StyledComponentProps<C, T, O, A> & { as?: Element | string; forwardedAs?: never | undefined }\n        ): ReactElement<StyledComponentProps<C, T, O, A>>;\n    }\n}\n\ndeclare module 'twin.macro' {\n    const css: typeof cssImport;\n    const styled: typeof styledImport;\n}\n"
  },
  {
    "path": "resources/scripts/modes.ts",
    "content": "export interface Mode {\n    name: string;\n    mime: string;\n    mimes?: string[];\n    mode: string;\n    ext?: string[];\n    alias?: string[];\n    file?: RegExp;\n}\n\nconst modes: Mode[] = [\n    { name: 'C', mime: 'text/x-csrc', mode: 'clike', ext: ['c', 'h', 'ino'] },\n    {\n        name: 'C++',\n        mime: 'text/x-c++src',\n        mode: 'clike',\n        ext: ['cpp', 'c++', 'cc', 'cxx', 'hpp', 'h++', 'hh', 'hxx'],\n        alias: ['cpp'],\n    },\n    { name: 'C#', mime: 'text/x-csharp', mode: 'clike', ext: ['cs'], alias: ['csharp', 'cs'] },\n    { name: 'CSS', mime: 'text/css', mode: 'css', ext: ['css'] },\n    { name: 'CQL', mime: 'text/x-cassandra', mode: 'sql', ext: ['cql'] },\n    { name: 'Diff', mime: 'text/x-diff', mode: 'diff', ext: ['diff', 'patch'] },\n    { name: 'Dockerfile', mime: 'text/x-dockerfile', mode: 'dockerfile', file: /^Dockerfile$/ },\n    { name: 'Git Markdown', mime: 'text/x-gfm', mode: 'gfm', file: /^(readme|contributing|history|license).md$/i },\n    { name: 'Golang', mime: 'text/x-go', mode: 'go', ext: ['go'] },\n    { name: 'HTML', mime: 'text/html', mode: 'htmlmixed', ext: ['html', 'htm', 'handlebars', 'hbs'], alias: ['xhtml'] },\n    { name: 'HTTP', mime: 'message/http', mode: 'http' },\n    {\n        name: 'JavaScript',\n        mime: 'text/javascript',\n        mimes: [\n            'text/javascript',\n            'text/ecmascript',\n            'application/javascript',\n            'application/x-javascript',\n            'application/ecmascript',\n        ],\n        mode: 'javascript',\n        ext: ['js'],\n        alias: ['ecmascript', 'js', 'node'],\n    },\n    {\n        name: 'JSON',\n        mime: 'application/json',\n        mimes: ['application/json', 'application/x-json'],\n        mode: 'javascript',\n        ext: ['json', 'map'],\n        alias: ['json5'],\n    },\n    { name: 'Lua', mime: 'text/x-lua', mode: 'lua', ext: ['lua'] },\n    { name: 'Markdown', mime: 'text/x-markdown', mode: 'markdown', ext: ['markdown', 'md', 'mkd'] },\n    { name: 'MariaDB', mime: 'text/x-mariadb', mode: 'sql' },\n    { name: 'MS SQL', mime: 'text/x-mssql', mode: 'sql' },\n    { name: 'MySQL', mime: 'text/x-mysql', mode: 'sql' },\n    { name: 'Nginx', mime: 'text/x-nginx-conf', mode: 'nginx', file: /nginx.*\\.conf$/i },\n    {\n        name: 'PHP',\n        mime: 'text/x-php',\n        mimes: ['text/x-php', 'application/x-httpd-php', 'application/x-httpd-php-open'],\n        mode: 'php',\n        ext: ['php', 'php3', 'php4', 'php5', 'php7', 'phtml'],\n    },\n    { name: 'Plain Text', mime: 'text/plain', mode: 'null', ext: ['txt', 'text', 'conf', 'def', 'list', 'log'] },\n    { name: 'PostgreSQL', mime: 'text/x-pgsql', mode: 'sql' },\n    {\n        name: 'Properties',\n        mime: 'text/x-properties',\n        mode: 'properties',\n        ext: ['properties', 'ini', 'in'],\n        alias: ['ini', 'properties'],\n    },\n    { name: 'Pug', mime: 'text/x-pug', mimes: ['text/x-pug', 'text/x-jade'], mode: 'null', ext: ['pug'] },\n    {\n        name: 'Python',\n        mime: 'text/x-python',\n        mode: 'python',\n        ext: ['BUILD', 'bzl', 'py', 'pyw'],\n        file: /^(BUCK|BUILD)$/,\n    },\n    { name: 'Ruby', mime: 'text/x-ruby', mode: 'ruby', ext: ['rb'], alias: ['jruby', 'macruby', 'rake', 'rb', 'rbx'] },\n    { name: 'Rust', mime: 'text/x-rustsrc', mode: 'rust', ext: ['rs'] },\n    { name: 'Sass', mime: 'text/x-sass', mode: 'sass', ext: ['sass'] },\n    { name: 'SCSS', mime: 'text/x-scss', mode: 'css', ext: ['scss'] },\n    {\n        name: 'Shell',\n        mime: 'text/x-sh',\n        mimes: ['text/x-sh', 'application/x-sh'],\n        mode: 'shell',\n        ext: ['sh', 'ksh', 'bash'],\n        alias: ['bash', 'sh', 'zsh'],\n        file: /^PKGBUILD$/,\n    },\n    { name: 'SQL', mime: 'text/x-sql', mode: 'sql', ext: ['sql'] },\n    { name: 'SQLite', mime: 'text/x-sqlite', mode: 'sql' },\n    { name: 'TOML', mime: 'text/x-toml', mode: 'toml', ext: ['toml'] },\n    { name: 'TypeScript', mime: 'application/typescript', mode: 'javascript', ext: ['ts'], alias: ['ts'] },\n    { name: 'Vue', mime: 'script/x-vue', mimes: ['script/x-vue', 'text/x-vue'], mode: 'vue', ext: ['vue'] },\n    {\n        name: 'XML',\n        mime: 'application/xml',\n        mimes: ['application/xml', 'text/xml'],\n        mode: 'xml',\n        ext: ['xml', 'xsl', 'xsd', 'svg'],\n        alias: ['rss', 'wsdl', 'xsd'],\n    },\n    {\n        name: 'YAML',\n        mime: 'text/x-yaml',\n        mimes: ['text/x-yaml', 'text/yaml'],\n        mode: 'yaml',\n        ext: ['yaml', 'yml'],\n        alias: ['yml'],\n    },\n];\n\nexport default modes;\n"
  },
  {
    "path": "resources/scripts/plugins/Websocket.ts",
    "content": "import Sockette from 'sockette';\nimport { EventEmitter } from 'events';\n\nexport class Websocket extends EventEmitter {\n    // The socket instance being tracked.\n    private socket: Sockette | null = null;\n\n    // The URL being connected to for the socket.\n    private url: string | null = null;\n\n    // The authentication token passed along with every request to the Daemon.\n    // By default this token expires every 15 minutes and must therefore be\n    // refreshed at a pretty continuous interval. The socket server will respond\n    // with \"token expiring\" and \"token expired\" events when approaching 3 minutes\n    // and 0 minutes to expiry.\n    private token = '';\n\n    // Connects to the websocket instance and sets the token for the initial request.\n    connect(url: string): this {\n        this.url = url;\n\n        this.socket = new Sockette(`${this.url}`, {\n            timeout: 1000,\n            maxAttempts: 20,\n            onmessage: (e) => {\n                try {\n                    const { event, args } = JSON.parse(e.data);\n                    args ? this.emit(event, ...args) : this.emit(event);\n                } catch (ex) {\n                    console.warn('无法解析传入的 websocket 消息。', ex);\n                }\n            },\n            onopen: () => {\n                this.emit('SOCKET_OPEN');\n                this.authenticate();\n            },\n            onreconnect: (evt) => {\n                // We return code 4409 from Wings when a server is suspended. We've\n                // gone ahead and reserved 4400 as well here for future expansion without\n                // having to loop back around.\n                //\n                // If either of those codes is returned go ahead and abort here. Unfortunately\n                // the underlying sockette logic always calls reconnect for any code that isn't\n                // 1000/1001/1003, which is painful but we can just stop the flow here.\n                // @ts-expect-error code is actually present here.\n                if (evt.code === 4409 || evt.code === 4400) {\n                    this.close(1000);\n                } else {\n                    this.emit('SOCKET_RECONNECT');\n                }\n            },\n            onclose: () => this.emit('SOCKET_CLOSE'),\n            onerror: (error) => this.emit('SOCKET_ERROR', error),\n            onmaximum: () => this.emit('SOCKET_CONNECT_ERROR'),\n        });\n\n        return this;\n    }\n\n    // Sets the authentication token to use when sending commands back and forth\n    // between the websocket instance.\n    setToken(token: string, isUpdate = false): this {\n        this.token = token;\n\n        if (isUpdate) {\n            this.authenticate();\n        }\n\n        return this;\n    }\n\n    authenticate() {\n        if (this.url && this.token) {\n            this.send('auth', this.token);\n        }\n    }\n\n    close(code?: number, reason?: string) {\n        this.url = null;\n        this.token = '';\n        this.socket?.close(code, reason);\n    }\n\n    open() {\n        this.socket?.open();\n    }\n\n    reconnect() {\n        this.socket?.reconnect();\n    }\n\n    send(event: string, payload?: string | string[]) {\n        this.socket?.json({ event, args: Array.isArray(payload) ? payload : [payload] });\n    }\n}\n"
  },
  {
    "path": "resources/scripts/plugins/XtermScrollDownHelperAddon.ts",
    "content": "import { Terminal, ITerminalAddon } from 'xterm';\n\nexport class ScrollDownHelperAddon implements ITerminalAddon {\n    private terminal: Terminal = new Terminal();\n    private element?: HTMLDivElement;\n\n    activate(terminal: Terminal): void {\n        this.terminal = terminal;\n\n        this.terminal.onScroll(() => {\n            if (this.isScrolledDown()) {\n                this.hide();\n            }\n        });\n\n        this.terminal.onLineFeed(() => {\n            if (!this.isScrolledDown()) {\n                this.show();\n            }\n        });\n\n        this.show();\n    }\n\n    dispose(): void {\n        // ignore\n    }\n\n    show(): void {\n        if (!this.terminal || !this.terminal.element) {\n            return;\n        }\n        if (this.element) {\n            this.element.style.visibility = 'visible';\n            return;\n        }\n\n        this.terminal.element.style.position = 'relative';\n\n        this.element = document.createElement('div');\n        this.element.innerHTML =\n            '<svg aria-hidden=\"true\" focusable=\"false\" data-prefix=\"fas\" data-icon=\"arrow-down\" class=\"svg-inline--fa fa-bell fa-w-14\" role=\"img\" xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 384 512\"><path fill=\"currentColor\" d=\"M374.6 310.6l-160 160C208.4 476.9 200.2 480 192 480s-16.38-3.125-22.62-9.375l-160-160c-12.5-12.5-12.5-32.75 0-45.25s32.75-12.5 45.25 0L160 370.8V64c0-17.69 14.33-31.1 31.1-31.1S224 46.31 224 64v306.8l105.4-105.4c12.5-12.5 32.75-12.5 45.25 0S387.1 298.1 374.6 310.6z\"/></svg>';\n        this.element.style.position = 'absolute';\n        this.element.style.right = '1.5rem';\n        this.element.style.bottom = '.5rem';\n        this.element.style.padding = '.5rem';\n        this.element.style.fontSize = '1.25em';\n        this.element.style.boxShadow = '0 2px 8px #000';\n        this.element.style.backgroundColor = '#252526';\n        this.element.style.zIndex = '999';\n        this.element.style.cursor = 'pointer';\n\n        this.element.addEventListener('click', () => {\n            this.terminal.scrollToBottom();\n        });\n\n        this.terminal.element.appendChild(this.element);\n    }\n\n    hide(): void {\n        if (this.element) {\n            this.element.style.visibility = 'hidden';\n        }\n    }\n\n    isScrolledDown(): boolean {\n        return this.terminal.buffer.active.viewportY === this.terminal.buffer.active.baseY;\n    }\n}\n"
  },
  {
    "path": "resources/scripts/plugins/useDeepCompareEffect.ts",
    "content": "import { DependencyList, EffectCallback, useEffect } from 'react';\nimport { useDeepMemoize } from './useDeepMemoize';\n\nexport const useDeepCompareEffect = (callback: EffectCallback, dependencies: DependencyList) =>\n    useEffect(callback, useDeepMemoize(dependencies));\n"
  },
  {
    "path": "resources/scripts/plugins/useDeepCompareMemo.ts",
    "content": "import { DependencyList, useMemo } from 'react';\nimport { useDeepMemoize } from '@/plugins/useDeepMemoize';\n\nexport const useDeepCompareMemo = <T>(callback: () => T, dependencies: DependencyList) =>\n    useMemo(callback, useDeepMemoize(dependencies));\n"
  },
  {
    "path": "resources/scripts/plugins/useDeepMemoize.ts",
    "content": "import { DependencyList, MutableRefObject, useRef } from 'react';\nimport isEqual from 'react-fast-compare';\n\nexport const useDeepMemoize = <T = DependencyList>(value: T): T => {\n    const ref: MutableRefObject<T | undefined> = useRef();\n\n    if (!isEqual(value, ref.current)) {\n        ref.current = value;\n    }\n\n    return ref.current as T;\n};\n"
  },
  {
    "path": "resources/scripts/plugins/useEventListener.ts",
    "content": "import { useEffect, useRef } from 'react';\n\nexport default (\n    eventName: string,\n    handler: (e: Event | CustomEvent | UIEvent | any) => void,\n    options?: boolean | EventListenerOptions\n) => {\n    const savedHandler = useRef<any>(null);\n\n    useEffect(() => {\n        savedHandler.current = handler;\n    }, [handler]);\n\n    useEffect(() => {\n        const isSupported = window && window.addEventListener;\n        if (!isSupported) return;\n\n        const eventListener = (event: any) => savedHandler.current(event);\n        window.addEventListener(eventName, eventListener, options);\n        return () => {\n            window.removeEventListener(eventName, eventListener);\n        };\n    }, [eventName, window]);\n};\n"
  },
  {
    "path": "resources/scripts/plugins/useFileManagerSwr.ts",
    "content": "import useSWR from 'swr';\nimport loadDirectory, { FileObject } from '@/api/server/files/loadDirectory';\nimport { cleanDirectoryPath } from '@/helpers';\nimport { ServerContext } from '@/state/server';\n\nexport const getDirectorySwrKey = (uuid: string, directory: string): string => `${uuid}:files:${directory}`;\n\nexport default () => {\n    const uuid = ServerContext.useStoreState((state) => state.server.data!.uuid);\n    const directory = ServerContext.useStoreState((state) => state.files.directory);\n\n    return useSWR<FileObject[]>(\n        getDirectorySwrKey(uuid, directory),\n        () => loadDirectory(uuid, cleanDirectoryPath(directory)),\n        {\n            focusThrottleInterval: 30000,\n            revalidateOnMount: false,\n            refreshInterval: 0,\n            errorRetryCount: 2,\n        }\n    );\n};\n"
  },
  {
    "path": "resources/scripts/plugins/useFilteredObject.ts",
    "content": "/**\n * Similar to \"withQueryBuilderParams\" except this function filters out any null,\n * undefined, or empty string key values. This allows the parameters to be used for\n * caching without having to account for all of the different data combinations.\n */\nimport { isEmptyObject, isObject } from '@/lib/objects';\n\n// eslint-disable-next-line @typescript-eslint/ban-types\nexport default <T extends {}>(data: T): T => {\n    const empty = [undefined, null, ''] as unknown[];\n\n    const removeEmptyValues = (input: T): T =>\n        Object.entries(input)\n            .filter(([_, value]) => !empty.includes(value))\n            .reduce((obj, [k, v]) => {\n                const parsed = isObject(v) ? removeEmptyValues(v as any) : v;\n\n                return isObject(parsed) && isEmptyObject(parsed) ? obj : { ...obj, [k]: parsed };\n            }, {} as T);\n\n    return removeEmptyValues(data);\n};\n"
  },
  {
    "path": "resources/scripts/plugins/useFlash.ts",
    "content": "import { Actions, useStoreActions } from 'easy-peasy';\nimport { FlashStore } from '@/state/flashes';\nimport { ApplicationStore } from '@/state';\n\ninterface KeyedFlashStore {\n    addError: (message: string, title?: string) => void;\n    clearFlashes: () => void;\n    clearAndAddHttpError: (error?: Error | string | null) => void;\n}\n\nconst useFlash = (): Actions<FlashStore> => {\n    return useStoreActions((actions: Actions<ApplicationStore>) => actions.flashes);\n};\n\nconst useFlashKey = (key: string): KeyedFlashStore => {\n    const { addFlash, clearFlashes, clearAndAddHttpError } = useFlash();\n\n    return {\n        addError: (message, title) => addFlash({ key, message, title, type: 'error' }),\n        clearFlashes: () => clearFlashes(key),\n        clearAndAddHttpError: (error) => clearAndAddHttpError({ key, error }),\n    };\n};\n\nexport { useFlashKey };\nexport default useFlash;\n"
  },
  {
    "path": "resources/scripts/plugins/useLocationHash.ts",
    "content": "import { useLocation } from 'react-router';\nimport { useMemo } from 'react';\n\nexport default () => {\n    const location = useLocation();\n\n    const getHashObject = (value: string): Record<string, string> =>\n        value\n            .substring(1)\n            .split('&')\n            .reduce((obj, str) => {\n                const [key, value = ''] = str.split('=');\n\n                return !str.trim() ? obj : { ...obj, [key]: value };\n            }, {});\n\n    const pathTo = (params: Record<string, string>): string => {\n        const current = getHashObject(location.hash);\n\n        for (const key in params) {\n            current[key] = params[key];\n        }\n\n        return Object.keys(current)\n            .map((key) => `${key}=${current[key]}`)\n            .join('&');\n    };\n\n    const hash = useMemo((): Record<string, string> => getHashObject(location.hash), [location.hash]);\n\n    return { hash, pathTo };\n};\n"
  },
  {
    "path": "resources/scripts/plugins/usePermissions.ts",
    "content": "import { ServerContext } from '@/state/server';\nimport { useDeepCompareMemo } from '@/plugins/useDeepCompareMemo';\n\nexport const usePermissions = (action: string | string[]): boolean[] => {\n    const userPermissions = ServerContext.useStoreState((state) => state.server.permissions);\n\n    return useDeepCompareMemo(() => {\n        if (userPermissions[0] === '*') {\n            return Array(Array.isArray(action) ? action.length : 1).fill(true);\n        }\n\n        return (Array.isArray(action) ? action : [action]).map(\n            (permission) =>\n                // Allows checking for any permission matching a name, for example files.*\n                // will return if the user has any permission under the file.XYZ namespace.\n                (permission.endsWith('.*') &&\n                    userPermissions.filter((p) => p.startsWith(permission.split('.')[0])).length > 0) ||\n                // Otherwise just check if the entire permission exists in the array or not.\n                userPermissions.indexOf(permission) >= 0\n        );\n    }, [action, userPermissions]);\n};\n"
  },
  {
    "path": "resources/scripts/plugins/usePersistedState.ts",
    "content": "import { Dispatch, SetStateAction, useEffect, useState } from 'react';\n\nexport function usePersistedState<S = undefined>(\n    key: string,\n    defaultValue: S\n): [S | undefined, Dispatch<SetStateAction<S | undefined>>] {\n    const [state, setState] = useState(() => {\n        try {\n            const item = localStorage.getItem(key);\n\n            return JSON.parse(item || String(defaultValue));\n        } catch (e) {\n            console.warn('Failed to retrieve persisted value from store.', e);\n\n            return defaultValue;\n        }\n    });\n\n    useEffect(() => {\n        localStorage.setItem(key, JSON.stringify(state));\n    }, [key, state]);\n\n    return [state, setState];\n}\n"
  },
  {
    "path": "resources/scripts/plugins/useSWRKey.ts",
    "content": "import { useDeepCompareMemo } from '@/plugins/useDeepCompareMemo';\nimport { ServerContext } from '@/state/server';\nimport { useStoreState } from '@/state/hooks';\n\n// eslint-disable-next-line @typescript-eslint/ban-types\ntype Context = string | string[] | (string | number | null | {})[];\n\nfunction useSWRKey(context: Context, prefix: string | null = null): string {\n    const key = useDeepCompareMemo((): string => {\n        return (Array.isArray(context) ? context : [context]).map((value) => JSON.stringify(value)).join(':');\n    }, [context]);\n\n    if (!key.trim().length) {\n        throw new Error('Must provide a valid context key to \"useSWRKey\".');\n    }\n\n    return `swr::${prefix ? `${prefix}:` : ''}${key.trim()}`;\n}\n\nfunction useServerSWRKey(context: Context): string {\n    const uuid = ServerContext.useStoreState((state) => state.server.data?.uuid);\n\n    return useSWRKey(context, `server:${uuid}`);\n}\n\nfunction useUserSWRKey(context: Context): string {\n    const uuid = useStoreState((state) => state.user.data?.uuid);\n\n    return useSWRKey(context, `user:${uuid}`);\n}\n\nexport default useSWRKey;\nexport { useServerSWRKey, useUserSWRKey };\n"
  },
  {
    "path": "resources/scripts/plugins/useWebsocketEvent.ts",
    "content": "import { ServerContext } from '@/state/server';\nimport { useEffect, useRef } from 'react';\nimport { SocketEvent } from '@/components/server/events';\n\nconst useWebsocketEvent = (event: SocketEvent, callback: (data: string) => void) => {\n    const { connected, instance } = ServerContext.useStoreState((state) => state.socket);\n    const savedCallback = useRef<any>(null);\n\n    useEffect(() => {\n        savedCallback.current = callback;\n    }, [callback]);\n\n    return useEffect(() => {\n        const eventListener = (event: SocketEvent) => savedCallback.current(event);\n        if (connected && instance) {\n            instance.addListener(event, eventListener);\n        }\n\n        return () => {\n            instance && instance.removeListener(event, eventListener);\n        };\n    }, [event, connected, instance]);\n};\n\nexport default useWebsocketEvent;\n"
  },
  {
    "path": "resources/scripts/routers/AuthenticationRouter.tsx",
    "content": "import React from 'react';\nimport { Route, Switch, useRouteMatch } from 'react-router-dom';\nimport LoginContainer from '@/components/auth/LoginContainer';\nimport ForgotPasswordContainer from '@/components/auth/ForgotPasswordContainer';\nimport ResetPasswordContainer from '@/components/auth/ResetPasswordContainer';\nimport LoginCheckpointContainer from '@/components/auth/LoginCheckpointContainer';\nimport { NotFound } from '@/components/elements/ScreenBlock';\nimport { useHistory, useLocation } from 'react-router';\n\nexport default () => {\n    const history = useHistory();\n    const location = useLocation();\n    const { path } = useRouteMatch();\n\n    return (\n        <div className={'pt-8 xl:pt-32'}>\n            <Switch location={location}>\n                <Route path={`${path}/login`} component={LoginContainer} exact />\n                <Route path={`${path}/login/checkpoint`} component={LoginCheckpointContainer} />\n                <Route path={`${path}/password`} component={ForgotPasswordContainer} exact />\n                <Route path={`${path}/password/reset/:token`} component={ResetPasswordContainer} />\n                <Route path={`${path}/checkpoint`} />\n                <Route path={'*'}>\n                    <NotFound onBack={() => history.push('/auth/login')} />\n                </Route>\n            </Switch>\n        </div>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/routers/DashboardRouter.tsx",
    "content": "import React from 'react';\nimport { NavLink, Route, Switch } from 'react-router-dom';\nimport NavigationBar from '@/components/NavigationBar';\nimport DashboardContainer from '@/components/dashboard/DashboardContainer';\nimport { NotFound } from '@/components/elements/ScreenBlock';\nimport TransitionRouter from '@/TransitionRouter';\nimport SubNavigation from '@/components/elements/SubNavigation';\nimport { useLocation } from 'react-router';\nimport Spinner from '@/components/elements/Spinner';\nimport routes from '@/routers/routes';\n\nexport default () => {\n    const location = useLocation();\n\n    return (\n        <>\n            <NavigationBar />\n            {location.pathname.startsWith('/account') && (\n                <SubNavigation>\n                    <div>\n                        {routes.account\n                            .filter((route) => !!route.name)\n                            .map(({ path, name, exact = false }) => (\n                                <NavLink key={path} to={`/account/${path}`.replace('//', '/')} exact={exact}>\n                                    {name}\n                                </NavLink>\n                            ))}\n                    </div>\n                </SubNavigation>\n            )}\n            <TransitionRouter>\n                <React.Suspense fallback={<Spinner centered />}>\n                    <Switch location={location}>\n                        <Route path={'/'} exact>\n                            <DashboardContainer />\n                        </Route>\n                        {routes.account.map(({ path, component: Component }) => (\n                            <Route key={path} path={`/account/${path}`.replace('//', '/')} exact>\n                                <Component />\n                            </Route>\n                        ))}\n                        <Route path={'*'}>\n                            <NotFound />\n                        </Route>\n                    </Switch>\n                </React.Suspense>\n            </TransitionRouter>\n        </>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/routers/ServerRouter.tsx",
    "content": "import TransferListener from '@/components/server/TransferListener';\nimport React, { useEffect, useState } from 'react';\nimport { NavLink, Route, Switch, useRouteMatch } from 'react-router-dom';\nimport NavigationBar from '@/components/NavigationBar';\nimport TransitionRouter from '@/TransitionRouter';\nimport WebsocketHandler from '@/components/server/WebsocketHandler';\nimport { ServerContext } from '@/state/server';\nimport { CSSTransition } from 'react-transition-group';\nimport Can from '@/components/elements/Can';\nimport Spinner from '@/components/elements/Spinner';\nimport { NotFound, ServerError } from '@/components/elements/ScreenBlock';\nimport { httpErrorToHuman } from '@/api/http';\nimport { useStoreState } from 'easy-peasy';\nimport SubNavigation from '@/components/elements/SubNavigation';\nimport InstallListener from '@/components/server/InstallListener';\nimport ErrorBoundary from '@/components/elements/ErrorBoundary';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport { faExternalLinkAlt } from '@fortawesome/free-solid-svg-icons';\nimport { useLocation } from 'react-router';\nimport ConflictStateRenderer from '@/components/server/ConflictStateRenderer';\nimport PermissionRoute from '@/components/elements/PermissionRoute';\nimport routes from '@/routers/routes';\n\nexport default () => {\n    const match = useRouteMatch<{ id: string }>();\n    const location = useLocation();\n\n    const rootAdmin = useStoreState((state) => state.user.data!.rootAdmin);\n    const [error, setError] = useState('');\n\n    const id = ServerContext.useStoreState((state) => state.server.data?.id);\n    const uuid = ServerContext.useStoreState((state) => state.server.data?.uuid);\n    const inConflictState = ServerContext.useStoreState((state) => state.server.inConflictState);\n    const serverId = ServerContext.useStoreState((state) => state.server.data?.internalId);\n    const getServer = ServerContext.useStoreActions((actions) => actions.server.getServer);\n    const clearServerState = ServerContext.useStoreActions((actions) => actions.clearServerState);\n\n    const to = (value: string, url = false) => {\n        if (value === '/') {\n            return url ? match.url : match.path;\n        }\n        return `${(url ? match.url : match.path).replace(/\\/*$/, '')}/${value.replace(/^\\/+/, '')}`;\n    };\n\n    useEffect(\n        () => () => {\n            clearServerState();\n        },\n        []\n    );\n\n    useEffect(() => {\n        setError('');\n\n        getServer(match.params.id).catch((error) => {\n            console.error(error);\n            setError(httpErrorToHuman(error));\n        });\n\n        return () => {\n            clearServerState();\n        };\n    }, [match.params.id]);\n\n    return (\n        <React.Fragment key={'server-router'}>\n            <NavigationBar />\n            {!uuid || !id ? (\n                error ? (\n                    <ServerError message={error} />\n                ) : (\n                    <Spinner size={'large'} centered />\n                )\n            ) : (\n                <>\n                    <CSSTransition timeout={150} classNames={'fade'} appear in>\n                        <SubNavigation>\n                            <div>\n                                {routes.server\n                                    .filter((route) => !!route.name)\n                                    .map((route) =>\n                                        route.permission ? (\n                                            <Can key={route.path} action={route.permission} matchAny>\n                                                <NavLink to={to(route.path, true)} exact={route.exact}>\n                                                    {route.name}\n                                                </NavLink>\n                                            </Can>\n                                        ) : (\n                                            <NavLink key={route.path} to={to(route.path, true)} exact={route.exact}>\n                                                {route.name}\n                                            </NavLink>\n                                        )\n                                    )}\n                                {rootAdmin && (\n                                    // eslint-disable-next-line react/jsx-no-target-blank\n                                    <a href={`/admin/servers/view/${serverId}`} target={'_blank'}>\n                                        <FontAwesomeIcon icon={faExternalLinkAlt} />\n                                    </a>\n                                )}\n                            </div>\n                        </SubNavigation>\n                    </CSSTransition>\n                    <InstallListener />\n                    <TransferListener />\n                    <WebsocketHandler />\n                    {inConflictState && (!rootAdmin || (rootAdmin && !location.pathname.endsWith(`/server/${id}`))) ? (\n                        <ConflictStateRenderer />\n                    ) : (\n                        <ErrorBoundary>\n                            <TransitionRouter>\n                                <Switch location={location}>\n                                    {routes.server.map(({ path, permission, component: Component }) => (\n                                        <PermissionRoute key={path} permission={permission} path={to(path)} exact>\n                                            <Spinner.Suspense>\n                                                <Component />\n                                            </Spinner.Suspense>\n                                        </PermissionRoute>\n                                    ))}\n                                    <Route path={'*'} component={NotFound} />\n                                </Switch>\n                            </TransitionRouter>\n                        </ErrorBoundary>\n                    )}\n                </>\n            )}\n        </React.Fragment>\n    );\n};\n"
  },
  {
    "path": "resources/scripts/routers/routes.ts",
    "content": "import React, { lazy } from 'react';\nimport ServerConsole from '@/components/server/console/ServerConsoleContainer';\nimport DatabasesContainer from '@/components/server/databases/DatabasesContainer';\nimport ScheduleContainer from '@/components/server/schedules/ScheduleContainer';\nimport UsersContainer from '@/components/server/users/UsersContainer';\nimport BackupContainer from '@/components/server/backups/BackupContainer';\nimport NetworkContainer from '@/components/server/network/NetworkContainer';\nimport StartupContainer from '@/components/server/startup/StartupContainer';\nimport FileManagerContainer from '@/components/server/files/FileManagerContainer';\nimport SettingsContainer from '@/components/server/settings/SettingsContainer';\nimport AccountOverviewContainer from '@/components/dashboard/AccountOverviewContainer';\nimport AccountApiContainer from '@/components/dashboard/AccountApiContainer';\nimport AccountSSHContainer from '@/components/dashboard/ssh/AccountSSHContainer';\nimport ActivityLogContainer from '@/components/dashboard/activity/ActivityLogContainer';\nimport ServerActivityLogContainer from '@/components/server/ServerActivityLogContainer';\n\n// Each of the router files is already code split out appropriately — so\n// all of the items above will only be loaded in when that router is loaded.\n//\n// These specific lazy loaded routes are to avoid loading in heavy screens\n// for the server dashboard when they're only needed for specific instances.\nconst FileEditContainer = lazy(() => import('@/components/server/files/FileEditContainer'));\nconst ScheduleEditContainer = lazy(() => import('@/components/server/schedules/ScheduleEditContainer'));\n\ninterface RouteDefinition {\n    path: string;\n    // If undefined is passed this route is still rendered into the router itself\n    // but no navigation link is displayed in the sub-navigation menu.\n    name: string | undefined;\n    component: React.ComponentType;\n    exact?: boolean;\n}\n\ninterface ServerRouteDefinition extends RouteDefinition {\n    permission: string | string[] | null;\n}\n\ninterface Routes {\n    // All of the routes available under \"/account\"\n    account: RouteDefinition[];\n    // All of the routes available under \"/server/:id\"\n    server: ServerRouteDefinition[];\n}\n\nexport default {\n    account: [\n        {\n            path: '/',\n            name: '帐户',\n            component: AccountOverviewContainer,\n            exact: true,\n        },\n        {\n            path: '/api',\n            name: 'API 凭证',\n            component: AccountApiContainer,\n        },\n        {\n            path: '/ssh',\n            name: 'SSH 密钥',\n            component: AccountSSHContainer,\n        },\n        {\n            path: '/activity',\n            name: '活动日志',\n            component: ActivityLogContainer,\n        },\n    ],\n    server: [\n        {\n            path: '/',\n            permission: null,\n            name: '控制台',\n            component: ServerConsole,\n            exact: true,\n        },\n        {\n            path: '/files',\n            permission: 'file.*',\n            name: '文件',\n            component: FileManagerContainer,\n        },\n        {\n            path: '/files/:action(edit|new)',\n            permission: 'file.*',\n            name: undefined,\n            component: FileEditContainer,\n        },\n        {\n            path: '/databases',\n            permission: 'database.*',\n            name: '数据库',\n            component: DatabasesContainer,\n        },\n        {\n            path: '/schedules',\n            permission: 'schedule.*',\n            name: '计划',\n            component: ScheduleContainer,\n        },\n        {\n            path: '/schedules/:id',\n            permission: 'schedule.*',\n            name: undefined,\n            component: ScheduleEditContainer,\n        },\n        {\n            path: '/users',\n            permission: 'user.*',\n            name: '子用户',\n            component: UsersContainer,\n        },\n        {\n            path: '/backups',\n            permission: 'backup.*',\n            name: '备份',\n            component: BackupContainer,\n        },\n        {\n            path: '/network',\n            permission: 'allocation.*',\n            name: '网络',\n            component: NetworkContainer,\n        },\n        {\n            path: '/startup',\n            permission: 'startup.*',\n            name: '启动',\n            component: StartupContainer,\n        },\n        {\n            path: '/settings',\n            permission: ['settings.*', 'file.sftp'],\n            name: '设置',\n            component: SettingsContainer,\n        },\n        {\n            path: '/activity',\n            permission: 'activity.*',\n            name: '活动日志',\n            component: ServerActivityLogContainer,\n        },\n    ],\n} as Routes;\n"
  },
  {
    "path": "resources/scripts/setup-tests.ts",
    "content": "import '@testing-library/jest-dom';\n"
  },
  {
    "path": "resources/scripts/state/flashes.ts",
    "content": "import { Action, action } from 'easy-peasy';\nimport { FlashMessageType } from '@/components/MessageBox';\nimport { httpErrorToHuman } from '@/api/http';\n\nexport interface FlashStore {\n    items: FlashMessage[];\n    addFlash: Action<FlashStore, FlashMessage>;\n    addError: Action<FlashStore, { message: string; key?: string }>;\n    clearAndAddHttpError: Action<FlashStore, { error?: Error | any | null; key?: string }>;\n    clearFlashes: Action<FlashStore, string | void>;\n}\n\nexport interface FlashMessage {\n    id?: string;\n    key?: string;\n    type: FlashMessageType;\n    title?: string;\n    message: string;\n}\n\nconst flashes: FlashStore = {\n    items: [],\n\n    addFlash: action((state, payload) => {\n        state.items.push(payload);\n    }),\n\n    addError: action((state, payload) => {\n        state.items.push({ type: 'error', title: '错误', ...payload });\n    }),\n\n    clearAndAddHttpError: action((state, payload) => {\n        if (!payload.error) {\n            state.items = [];\n        } else {\n            console.error(payload.error);\n\n            state.items = [\n                {\n                    type: 'error',\n                    title: '错误',\n                    key: payload.key,\n                    message: httpErrorToHuman(payload.error),\n                },\n            ];\n        }\n    }),\n\n    clearFlashes: action((state, payload) => {\n        state.items = payload ? state.items.filter((flashes) => flashes.key !== payload) : [];\n    }),\n};\n\nexport default flashes;\n"
  },
  {
    "path": "resources/scripts/state/hooks.ts",
    "content": "import { createTypedHooks } from 'easy-peasy';\nimport { ApplicationStore } from '@/state/index';\n\nconst hooks = createTypedHooks<ApplicationStore>();\n\nexport const useStore = hooks.useStore;\nexport const useStoreState = hooks.useStoreState;\nexport const useStoreActions = hooks.useStoreActions;\nexport const useStoreDispatch = hooks.useStoreDispatch;\n"
  },
  {
    "path": "resources/scripts/state/index.ts",
    "content": "import { createStore } from 'easy-peasy';\nimport flashes, { FlashStore } from '@/state/flashes';\nimport user, { UserStore } from '@/state/user';\nimport permissions, { GloablPermissionsStore } from '@/state/permissions';\nimport settings, { SettingsStore } from '@/state/settings';\nimport progress, { ProgressStore } from '@/state/progress';\n\nexport interface ApplicationStore {\n    permissions: GloablPermissionsStore;\n    flashes: FlashStore;\n    user: UserStore;\n    settings: SettingsStore;\n    progress: ProgressStore;\n}\n\nconst state: ApplicationStore = {\n    permissions,\n    flashes,\n    user,\n    settings,\n    progress,\n};\n\nexport const store = createStore(state);\n"
  },
  {
    "path": "resources/scripts/state/permissions.ts",
    "content": "import { action, Action, thunk, Thunk } from 'easy-peasy';\nimport getSystemPermissions from '@/api/getSystemPermissions';\n\nexport interface PanelPermissions {\n    [key: string]: {\n        description: string;\n        keys: { [k: string]: string };\n    };\n}\n\nexport interface GloablPermissionsStore {\n    data: PanelPermissions;\n    setPermissions: Action<GloablPermissionsStore, PanelPermissions>;\n    getPermissions: Thunk<GloablPermissionsStore, void, Record<string, unknown>, any, Promise<void>>;\n}\n\nconst permissions: GloablPermissionsStore = {\n    data: {},\n\n    setPermissions: action((state, payload) => {\n        state.data = payload;\n    }),\n\n    getPermissions: thunk(async (actions) => {\n        const permissions = await getSystemPermissions();\n\n        actions.setPermissions(permissions);\n    }),\n};\n\nexport default permissions;\n"
  },
  {
    "path": "resources/scripts/state/progress.ts",
    "content": "import { action, Action } from 'easy-peasy';\n\nexport interface ProgressStore {\n    continuous: boolean;\n    progress?: number;\n\n    startContinuous: Action<ProgressStore>;\n    setProgress: Action<ProgressStore, number | undefined>;\n    setComplete: Action<ProgressStore>;\n}\n\nconst progress: ProgressStore = {\n    continuous: false,\n    progress: undefined,\n\n    startContinuous: action((state) => {\n        state.continuous = true;\n    }),\n\n    setProgress: action((state, payload) => {\n        state.progress = payload;\n    }),\n\n    setComplete: action((state) => {\n        if (state.progress) {\n            state.progress = 100;\n        }\n\n        state.continuous = false;\n    }),\n};\n\nexport default progress;\n"
  },
  {
    "path": "resources/scripts/state/server/databases.ts",
    "content": "import { action, Action } from 'easy-peasy';\nimport { ServerDatabase } from '@/api/server/databases/getServerDatabases';\n\nexport interface ServerDatabaseStore {\n    data: ServerDatabase[];\n    setDatabases: Action<ServerDatabaseStore, ServerDatabase[]>;\n    appendDatabase: Action<ServerDatabaseStore, ServerDatabase>;\n    removeDatabase: Action<ServerDatabaseStore, string>;\n}\n\nconst databases: ServerDatabaseStore = {\n    data: [],\n\n    setDatabases: action((state, payload) => {\n        state.data = payload;\n    }),\n\n    appendDatabase: action((state, payload) => {\n        if (state.data.find((database) => database.id === payload.id)) {\n            state.data = state.data.map((database) => (database.id === payload.id ? payload : database));\n        } else {\n            state.data = [...state.data, payload];\n        }\n    }),\n\n    removeDatabase: action((state, payload) => {\n        state.data = [...state.data.filter((database) => database.id !== payload)];\n    }),\n};\n\nexport default databases;\n"
  },
  {
    "path": "resources/scripts/state/server/files.ts",
    "content": "import { action, Action } from 'easy-peasy';\nimport { cleanDirectoryPath } from '@/helpers';\n\nexport interface FileUploadData {\n    loaded: number;\n    readonly abort: AbortController;\n    readonly total: number;\n}\n\nexport interface ServerFileStore {\n    directory: string;\n    selectedFiles: string[];\n    uploads: Record<string, FileUploadData>;\n\n    setDirectory: Action<ServerFileStore, string>;\n    setSelectedFiles: Action<ServerFileStore, string[]>;\n    appendSelectedFile: Action<ServerFileStore, string>;\n    removeSelectedFile: Action<ServerFileStore, string>;\n\n    pushFileUpload: Action<ServerFileStore, { name: string; data: FileUploadData }>;\n    setUploadProgress: Action<ServerFileStore, { name: string; loaded: number }>;\n    clearFileUploads: Action<ServerFileStore>;\n    removeFileUpload: Action<ServerFileStore, string>;\n    cancelFileUpload: Action<ServerFileStore, string>;\n}\n\nconst files: ServerFileStore = {\n    directory: '/',\n    selectedFiles: [],\n    uploads: {},\n\n    setDirectory: action((state, payload) => {\n        state.directory = cleanDirectoryPath(payload);\n    }),\n\n    setSelectedFiles: action((state, payload) => {\n        state.selectedFiles = payload;\n    }),\n\n    appendSelectedFile: action((state, payload) => {\n        state.selectedFiles = state.selectedFiles.filter((f) => f !== payload).concat(payload);\n    }),\n\n    removeSelectedFile: action((state, payload) => {\n        state.selectedFiles = state.selectedFiles.filter((f) => f !== payload);\n    }),\n\n    clearFileUploads: action((state) => {\n        Object.values(state.uploads).forEach((upload) => upload.abort.abort());\n\n        state.uploads = {};\n    }),\n\n    pushFileUpload: action((state, payload) => {\n        state.uploads[payload.name] = payload.data;\n    }),\n\n    setUploadProgress: action((state, { name, loaded }) => {\n        if (state.uploads[name]) {\n            state.uploads[name].loaded = loaded;\n        }\n    }),\n\n    removeFileUpload: action((state, payload) => {\n        if (state.uploads[payload]) {\n            delete state.uploads[payload];\n        }\n    }),\n\n    cancelFileUpload: action((state, payload) => {\n        if (state.uploads[payload]) {\n            // Abort the request if it is still in flight. If it already completed this is\n            // a no-op.\n            state.uploads[payload].abort.abort();\n\n            delete state.uploads[payload];\n        }\n    }),\n};\n\nexport default files;\n"
  },
  {
    "path": "resources/scripts/state/server/index.ts",
    "content": "import getServer, { Server } from '@/api/server/getServer';\nimport { action, Action, computed, Computed, createContextStore, thunk, Thunk } from 'easy-peasy';\nimport socket, { SocketStore } from './socket';\nimport files, { ServerFileStore } from '@/state/server/files';\nimport subusers, { ServerSubuserStore } from '@/state/server/subusers';\nimport { composeWithDevTools } from 'redux-devtools-extension';\nimport schedules, { ServerScheduleStore } from '@/state/server/schedules';\nimport databases, { ServerDatabaseStore } from '@/state/server/databases';\nimport isEqual from 'react-fast-compare';\n\nexport type ServerStatus = 'offline' | 'starting' | 'stopping' | 'running' | null;\n\ninterface ServerDataStore {\n    data?: Server;\n    inConflictState: Computed<ServerDataStore, boolean>;\n    isInstalling: Computed<ServerDataStore, boolean>;\n    permissions: string[];\n\n    getServer: Thunk<ServerDataStore, string, Record<string, unknown>, ServerStore, Promise<void>>;\n    setServer: Action<ServerDataStore, Server>;\n    setServerFromState: Action<ServerDataStore, (s: Server) => Server>;\n    setPermissions: Action<ServerDataStore, string[]>;\n}\n\nconst server: ServerDataStore = {\n    permissions: [],\n\n    inConflictState: computed((state) => {\n        if (!state.data) {\n            return false;\n        }\n\n        return state.data.status !== null || state.data.isTransferring || state.data.isNodeUnderMaintenance;\n    }),\n\n    isInstalling: computed((state) => {\n        return state.data?.status === 'installing' || state.data?.status === 'install_failed';\n    }),\n\n    getServer: thunk(async (actions, payload) => {\n        const [server, permissions] = await getServer(payload);\n\n        actions.setServer(server);\n        actions.setPermissions(permissions);\n    }),\n\n    setServer: action((state, payload) => {\n        if (!isEqual(payload, state.data)) {\n            state.data = payload;\n        }\n    }),\n\n    setServerFromState: action((state, payload) => {\n        const output = payload(state.data!);\n        if (!isEqual(output, state.data)) {\n            state.data = output;\n        }\n    }),\n\n    setPermissions: action((state, payload) => {\n        if (!isEqual(payload, state.permissions)) {\n            state.permissions = payload;\n        }\n    }),\n};\n\ninterface ServerStatusStore {\n    value: ServerStatus;\n    setServerStatus: Action<ServerStatusStore, ServerStatus>;\n}\n\nconst status: ServerStatusStore = {\n    value: null,\n    setServerStatus: action((state, payload) => {\n        state.value = payload;\n    }),\n};\n\nexport interface ServerStore {\n    server: ServerDataStore;\n    subusers: ServerSubuserStore;\n    databases: ServerDatabaseStore;\n    files: ServerFileStore;\n    schedules: ServerScheduleStore;\n    socket: SocketStore;\n    status: ServerStatusStore;\n    clearServerState: Action<ServerStore>;\n}\n\nexport const ServerContext = createContextStore<ServerStore>(\n    {\n        server,\n        socket,\n        status,\n        databases,\n        files,\n        subusers,\n        schedules,\n        clearServerState: action((state) => {\n            state.server.data = undefined;\n            state.server.permissions = [];\n            state.databases.data = [];\n            state.subusers.data = [];\n            state.files.directory = '/';\n            state.files.selectedFiles = [];\n            state.schedules.data = [];\n\n            if (state.socket.instance) {\n                state.socket.instance.removeAllListeners();\n                state.socket.instance.close();\n            }\n\n            state.socket.instance = null;\n            state.socket.connected = false;\n        }),\n    },\n    {\n        compose: composeWithDevTools({\n            name: 'ServerStore',\n            trace: true,\n        }),\n    }\n);\n"
  },
  {
    "path": "resources/scripts/state/server/schedules.ts",
    "content": "import { action, Action } from 'easy-peasy';\nimport { Schedule } from '@/api/server/schedules/getServerSchedules';\n\nexport interface ServerScheduleStore {\n    data: Schedule[];\n    setSchedules: Action<ServerScheduleStore, Schedule[]>;\n    appendSchedule: Action<ServerScheduleStore, Schedule>;\n    removeSchedule: Action<ServerScheduleStore, number>;\n}\n\nconst schedules: ServerScheduleStore = {\n    data: [],\n\n    setSchedules: action((state, payload) => {\n        state.data = payload;\n    }),\n\n    appendSchedule: action((state, payload) => {\n        if (state.data.find((schedule) => schedule.id === payload.id)) {\n            state.data = state.data.map((schedule) => (schedule.id === payload.id ? payload : schedule));\n        } else {\n            state.data = [...state.data, payload];\n        }\n    }),\n\n    removeSchedule: action((state, payload) => {\n        state.data = [...state.data.filter((schedule) => schedule.id !== payload)];\n    }),\n};\n\nexport default schedules;\n"
  },
  {
    "path": "resources/scripts/state/server/socket.ts",
    "content": "import { Action, action } from 'easy-peasy';\nimport { Websocket } from '@/plugins/Websocket';\n\nexport interface SocketStore {\n    instance: Websocket | null;\n    connected: boolean;\n    setInstance: Action<SocketStore, Websocket | null>;\n    setConnectionState: Action<SocketStore, boolean>;\n}\n\nconst socket: SocketStore = {\n    instance: null,\n    connected: false,\n    setInstance: action((state, payload) => {\n        state.instance = payload;\n    }),\n    setConnectionState: action((state, payload) => {\n        state.connected = payload;\n    }),\n};\n\nexport default socket;\n"
  },
  {
    "path": "resources/scripts/state/server/subusers.ts",
    "content": "import { action, Action } from 'easy-peasy';\n\nexport type SubuserPermission =\n    | 'websocket.connect'\n    | 'control.console'\n    | 'control.start'\n    | 'control.stop'\n    | 'control.restart'\n    | 'user.create'\n    | 'user.read'\n    | 'user.update'\n    | 'user.delete'\n    | 'file.create'\n    | 'file.read'\n    | 'file.update'\n    | 'file.delete'\n    | 'file.archive'\n    | 'file.sftp'\n    | 'allocation.read'\n    | 'allocation.update'\n    | 'startup.read'\n    | 'startup.update'\n    | 'database.create'\n    | 'database.read'\n    | 'database.update'\n    | 'database.delete'\n    | 'database.view_password'\n    | 'schedule.create'\n    | 'schedule.read'\n    | 'schedule.update'\n    | 'schedule.delete';\n\nexport interface Subuser {\n    uuid: string;\n    username: string;\n    email: string;\n    image: string;\n    twoFactorEnabled: boolean;\n    createdAt: Date;\n    permissions: SubuserPermission[];\n\n    can(permission: SubuserPermission): boolean;\n}\n\nexport interface ServerSubuserStore {\n    data: Subuser[];\n    setSubusers: Action<ServerSubuserStore, Subuser[]>;\n    appendSubuser: Action<ServerSubuserStore, Subuser>;\n    removeSubuser: Action<ServerSubuserStore, string>;\n}\n\nconst subusers: ServerSubuserStore = {\n    data: [],\n\n    setSubusers: action((state, payload) => {\n        state.data = payload;\n    }),\n\n    appendSubuser: action((state, payload) => {\n        let matched = false;\n        state.data = [\n            ...state.data\n                .map((user) => {\n                    if (user.uuid === payload.uuid) {\n                        matched = true;\n\n                        return payload;\n                    }\n\n                    return user;\n                })\n                .concat(matched ? [] : [payload]),\n        ];\n    }),\n\n    removeSubuser: action((state, payload) => {\n        state.data = [...state.data.filter((user) => user.uuid !== payload)];\n    }),\n};\n\nexport default subusers;\n"
  },
  {
    "path": "resources/scripts/state/settings.ts",
    "content": "import { action, Action } from 'easy-peasy';\n\nexport interface SiteSettings {\n    name: string;\n    locale: string;\n    recaptcha: {\n        enabled: boolean;\n        siteKey: string;\n    };\n    logo: {\n        title: string;\n        favicon: string;\n        auth: string;\n    };\n    icp: {\n        enabled: boolean;\n        record: string;\n        security_record: string;\n    };\n    allocations: {\n        consecutiveEnabled: boolean;\n        consecutiveLimit: number;\n    };\n}\n\nexport interface SettingsStore {\n    data?: SiteSettings;\n    setSettings: Action<SettingsStore, SiteSettings>;\n}\n\nconst settings: SettingsStore = {\n    data: undefined,\n\n    setSettings: action((state, payload) => {\n        state.data = payload;\n    }),\n};\n\nexport default settings;\n"
  },
  {
    "path": "resources/scripts/state/user.ts",
    "content": "import { Action, action, Thunk, thunk } from 'easy-peasy';\nimport updateAccountEmail from '@/api/account/updateAccountEmail';\n\nexport interface UserData {\n    uuid: string;\n    username: string;\n    email: string;\n    language: string;\n    rootAdmin: boolean;\n    useTotp: boolean;\n    createdAt: Date;\n    updatedAt: Date;\n}\n\nexport interface UserStore {\n    data?: UserData;\n    setUserData: Action<UserStore, UserData>;\n    updateUserData: Action<UserStore, Partial<UserData>>;\n    updateUserEmail: Thunk<UserStore, { email: string; password: string }, any, UserStore, Promise<void>>;\n}\n\nconst user: UserStore = {\n    data: undefined,\n    setUserData: action((state, payload) => {\n        state.data = payload;\n    }),\n\n    updateUserData: action((state, payload) => {\n        // @ts-expect-error limitation of Typescript, can't do much about that currently unfortunately.\n        state.data = { ...state.data, ...payload };\n    }),\n\n    updateUserEmail: thunk(async (actions, payload) => {\n        await updateAccountEmail(payload.email, payload.password);\n\n        actions.updateUserData({ email: payload.email });\n    }),\n};\n\nexport default user;\n"
  },
  {
    "path": "resources/scripts/theme.ts",
    "content": "import { BreakpointFunction, createBreakpoint } from 'styled-components-breakpoint';\n\ntype Breakpoints = 'xs' | 'sm' | 'md' | 'lg' | 'xl';\nexport const breakpoint: BreakpointFunction<Breakpoints> = createBreakpoint<Breakpoints>({\n    xs: 0,\n    sm: 640,\n    md: 768,\n    lg: 1024,\n    xl: 1280,\n});\n"
  },
  {
    "path": "resources/views/admin/api/index.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    应用 API\n@endsection\n\n@section('content-header')\n    <h1>应用 API<small>通过 API 控制管理此面板的访问凭证.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">应用 API</li>\n    </ol>\n@endsection\n\n@section('content')\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">凭证列表</h3>\n                    <div class=\"box-tools\">\n                        <a href=\"{{ route('admin.api.new') }}\" class=\"btn btn-sm btn-primary\">新建</a>\n                    </div>\n                </div>\n                <div class=\"box-body table-responsive no-padding\">\n                    <table class=\"table table-hover\">\n                        <tr>\n                            <th>密钥 Key</th>\n                            <th>备注</th>\n                            <th>上次使用于</th>\n                            <th>创建于</th>\n                            <th>创建自</th>\n                            <th></th>\n                        </tr>\n                        @foreach($keys as $key)\n                            <tr>\n                                <td><code>\n                                    @if (Auth::user()->is($key->user))\n                                        {{ $key->identifier . decrypt($key->token) }}\n                                    @else\n                                        {{ $key->identifier . '****' }}\n                                    @endif\n                                </code></td>\n                                <td>{{ $key->memo }}</td>\n                                <td>\n                                    @if(!is_null($key->last_used_at))\n                                        @datetimeHuman($key->last_used_at)\n                                    @else\n                                        &mdash;\n                                    @endif\n                                </td>\n                                <td>@datetimeHuman($key->created_at)</td>\n                                <td>\n                                    <a href=\"{{ route('admin.users.view', $key->user->id) }}\">{{ $key->user->username }}</a>\n                                </td>\n                                <td>\n                                    <a href=\"#\" data-action=\"revoke-key\" data-attr=\"{{ $key->identifier }}\">\n                                        <i class=\"fa fa-trash-o text-danger\"></i>\n                                    </a>\n                                </td>\n                            </tr>\n                        @endforeach\n                    </table>\n                </div>\n            </div>\n        </div>\n    </div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n        $(document).ready(function() {\n            $('[data-action=\"revoke-key\"]').click(function (event) {\n                var self = $(this);\n                event.preventDefault();\n                swal({\n                    type: 'error',\n                    title: '删除 API 密钥',\n                    text: '一旦此 API 密钥被删除，当前使用它的任何应用程序都将停止工作。',\n                    showCancelButton: true,\n                    allowOutsideClick: true,\n                    closeOnConfirm: false,\n                    confirmButtonText: '删除',\n                    confirmButtonColor: '#d9534f',\n                    showLoaderOnConfirm: true\n                }, function () {\n                    $.ajax({\n                        method: 'DELETE',\n                        url: '/admin/api/revoke/' + self.data('attr'),\n                        headers: {\n                            'X-CSRF-TOKEN': '{{ csrf_token() }}'\n                        }\n                    }).done(function () {\n                        swal({\n                            type: 'success',\n                            title: '',\n                            text: '此 API 密钥已被删除.'\n                        });\n                        self.parent().parent().slideUp();\n                    }).fail(function (jqXHR) {\n                        console.error(jqXHR);\n                        swal({\n                            type: 'error',\n                            title: '离了个大谱!',\n                            text: '删除此 API 密钥时发生错误，此操作无法继续进行.'\n                        });\n                    });\n                });\n            });\n        });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/api/new.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    应用 API\n@endsection\n\n@section('content-header')\n    <h1>应用 API<small>创建新的应用程序 API 密钥.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.api.index') }}\">应用 API</a></li>\n        <li class=\"active\">新凭证</li>\n    </ol>\n@endsection\n\n@section('content')\n    <div class=\"row\">\n        <form method=\"POST\" action=\"{{ route('admin.api.new') }}\">\n            <div class=\"col-sm-8 col-xs-12\">\n                <div class=\"box box-primary\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">选择权限</h3>\n                    </div>\n                    <div class=\"box-body table-responsive no-padding\">\n                        <table class=\"table table-hover\">\n                            @foreach($resources as $resource)\n                                <tr>\n                                    <td class=\"col-sm-3 strong\">{{ str_replace('_', ' ', title_case($resource)) }}</td>\n                                    <td class=\"col-sm-3 radio radio-primary text-center\">\n                                        <input type=\"radio\" id=\"r_{{ $resource }}\" name=\"r_{{ $resource }}\" value=\"{{ $permissions['r'] }}\">\n                                        <label for=\"r_{{ $resource }}\">只读</label>\n                                    </td>\n                                    <td class=\"col-sm-3 radio radio-primary text-center\">\n                                        <input type=\"radio\" id=\"rw_{{ $resource }}\" name=\"r_{{ $resource }}\" value=\"{{ $permissions['rw'] }}\">\n                                        <label for=\"rw_{{ $resource }}\">可读 &amp; 可写</label>\n                                    </td>\n                                    <td class=\"col-sm-3 radio text-center\">\n                                        <input type=\"radio\" id=\"n_{{ $resource }}\" name=\"r_{{ $resource }}\" value=\"{{ $permissions['n'] }}\" checked>\n                                        <label for=\"n_{{ $resource }}\">无权限</label>\n                                    </td>\n                                </tr>\n                            @endforeach\n                        </table>\n                    </div>\n                </div>\n            </div>\n            <div class=\"col-sm-4 col-xs-12\">\n                <div class=\"box box-primary\">\n                    <div class=\"box-body\">\n                        <div class=\"form-group\">\n                            <label class=\"control-label\" for=\"memoField\">描述 <span class=\"field-required\"></span></label>\n                            <input id=\"memoField\" type=\"text\" name=\"memo\" class=\"form-control\">\n                        </div>\n                        <p class=\"text-muted\">一旦您分配了权限并创建了这组凭证，您将无法返回并对其进行编辑。如果您需要在以后进行更改，则需要创建一组新的凭证.</p>\n                    </div>\n                    <div class=\"box-footer\">\n                        {{ csrf_field() }}\n                        <button type=\"submit\" class=\"btn btn-success btn-sm pull-right\">创建凭证</button>\n                    </div>\n                </div>\n            </div>\n        </form>\n    </div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/databases/index.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    数据库主机\n@endsection\n\n@section('content-header')\n    <h1>数据库主机<small>服务器可以在其上创建数据库的数据库主机。</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">数据库主机</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">主机列表</h3>\n                <div class=\"box-tools\">\n                    <button class=\"btn btn-sm btn-primary\" data-toggle=\"modal\" data-target=\"#newHostModal\">新建</button>\n                </div>\n            </div>\n            <div class=\"box-body table-responsive no-padding\">\n                <table class=\"table table-hover\">\n                    <tbody>\n                        <tr>\n                            <th>ID</th>\n                            <th>名称</th>\n                            <th>地址</th>\n                            <th>端口</th>\n                            <th>用户名</th>\n                            <th class=\"text-center\">数据库</th>\n                            <th class=\"text-center\">节点</th>\n                        </tr>\n                        @foreach ($hosts as $host)\n                            <tr>\n                                <td><code>{{ $host->id }}</code></td>\n                                <td><a href=\"{{ route('admin.databases.view', $host->id) }}\">{{ $host->name }}</a></td>\n                                <td><code>{{ $host->host }}</code></td>\n                                <td><code>{{ $host->port }}</code></td>\n                                <td>{{ $host->username }}</td>\n                                <td class=\"text-center\">{{ $host->databases_count }}</td>\n                                <td class=\"text-center\">\n                                    @if(! is_null($host->node))\n                                        <a href=\"{{ route('admin.nodes.view', $host->node->id) }}\">{{ $host->node->name }}</a>\n                                    @else\n                                        <span class=\"label label-default\">无</span>\n                                    @endif\n                                </td>\n                            </tr>\n                        @endforeach\n                    </tbody>\n                </table>\n            </div>\n        </div>\n    </div>\n</div>\n<div class=\"modal fade\" id=\"newHostModal\" tabindex=\"-1\" role=\"dialog\">\n    <div class=\"modal-dialog\" role=\"document\">\n        <div class=\"modal-content\">\n            <form action=\"{{ route('admin.databases') }}\" method=\"POST\">\n                <div class=\"modal-header\">\n                    <button type=\"button\" class=\"close\" data-dismiss=\"modal\" aria-label=\"Close\"><span aria-hidden=\"true\">&times;</span></button>\n                    <h4 class=\"modal-title\">新建数据库主机</h4>\n                </div>\n                <div class=\"modal-body\">\n                    <div class=\"form-group\">\n                        <label for=\"pName\" class=\"form-label\">名称</label>\n                        <input type=\"text\" name=\"name\" id=\"pName\" class=\"form-control\" />\n                        <p class=\"text-muted small\">用于将此主机与其他主机区分开来的简短标识符。必须介于 1 到 60 个字符之间，例如, <code>us.nyc.lvl3</code>.</p>\n                    </div>\n                    <div class=\"row\">\n                        <div class=\"col-md-6\">\n                            <label for=\"pHost\" class=\"form-label\">地址</label>\n                            <input type=\"text\" name=\"host\" id=\"pHost\" class=\"form-control\" />\n                            <p class=\"text-muted small\">尝试连接到此 MySQL 主机时应使用的 IP 地址或域名.</p>\n                        </div>\n                        <div class=\"col-md-6\">\n                            <label for=\"pPort\" class=\"form-label\">端口</label>\n                            <input type=\"text\" name=\"port\" id=\"pPort\" class=\"form-control\" value=\"3306\"/>\n                            <p class=\"text-muted small\">MYSQL 主机运行开放的端口.</p>\n                        </div>\n                    </div>\n                    <div class=\"row\">\n                        <div class=\"col-md-6\">\n                            <label for=\"pUsername\" class=\"form-label\">用户名</label>\n                            <input type=\"text\" name=\"username\" id=\"pUsername\" class=\"form-control\" />\n                            <p class=\"text-muted small\">具有足够权限在系统上创建新用户和数据库的帐户的用户名.</p>\n                        </div>\n                        <div class=\"col-md-6\">\n                            <label for=\"pPassword\" class=\"form-label\">密码</label>\n                            <input type=\"password\" name=\"password\" id=\"pPassword\" class=\"form-control\" />\n                            <p class=\"text-muted small\">上方阁下填写的账户的密码.</p>\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pNodeId\" class=\"form-label\">关联的节点</label>\n                        <select name=\"node_id\" id=\"pNodeId\" class=\"form-control\">\n                            <option value=\"\">无</option>\n                            @foreach($locations as $location)\n                                <optgroup label=\"{{ $location->short }}\">\n                                    @foreach($location->nodes as $node)\n                                        <option value=\"{{ $node->id }}\">{{ $node->name }}</option>\n                                    @endforeach\n                                </optgroup>\n                            @endforeach\n                        </select>\n                        <p class=\"text-muted small\">此设置除了将数据库默认添加到所选节点上的服务器以外没有任何作用.</p>\n                    </div>\n                </div>\n                <div class=\"modal-footer\">\n                    <p class=\"text-danger small text-left\">连接此数据库主机所使用的账户 <strong>必须</strong> 具有 <code>WITH GRANT OPTION</code> 权限. 如果账户没有此权限将 <em>无法</em> 成功建立数据库. <strong>不要为 MySQL 使用您为此面板使用的相同帐户详细信息.</strong></p>\n                    {!! csrf_field() !!}\n                    <button type=\"button\" class=\"btn btn-default btn-sm pull-left\" data-dismiss=\"modal\">取消</button>\n                    <button type=\"submit\" class=\"btn btn-success btn-sm\">创建</button>\n                </div>\n            </form>\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n        $('#pNodeId').select2();\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/databases/view.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    数据库主机 &rarr; 详细信息 &rarr; {{ $host->name }}\n@endsection\n\n@section('content-header')\n    <h1>{{ $host->name }}<small>查看此数据库主机的关联数据库和详细信息.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.databases') }}\">数据库主机</a></li>\n        <li class=\"active\">{{ $host->name }}</li>\n    </ol>\n@endsection\n\n@section('content')\n<form action=\"{{ route('admin.databases.view', $host->id) }}\" method=\"POST\">\n    <div class=\"row\">\n        <div class=\"col-sm-6\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">主机详情</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"pName\" class=\"form-label\">名称</label>\n                        <input type=\"text\" id=\"pName\" name=\"name\" class=\"form-control\" value=\"{{ old('name', $host->name) }}\" />\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pHost\" class=\"form-label\">地址</label>\n                        <input type=\"text\" id=\"pHost\" name=\"host\" class=\"form-control\" value=\"{{ old('host', $host->host) }}\" />\n                        <p class=\"text-muted small\">尝试连接到此 MySQL 主机时应使用的 IP 地址或域名.</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pPort\" class=\"form-label\">端口</label>\n                        <input type=\"text\" id=\"pPort\" name=\"port\" class=\"form-control\" value=\"{{ old('port', $host->port) }}\" />\n                        <p class=\"text-muted small\">MYSQL 主机运行开放的端口.</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pNodeId\" class=\"form-label\">关联的节点</label>\n                        <select name=\"node_id\" id=\"pNodeId\" class=\"form-control\">\n                            <option value=\"\">无</option>\n                            @foreach($locations as $location)\n                                <optgroup label=\"{{ $location->short }}\">\n                                    @foreach($location->nodes as $node)\n                                        <option value=\"{{ $node->id }}\" {{ $host->node_id !== $node->id ?: 'selected' }}>{{ $node->name }}</option>\n                                    @endforeach\n                                </optgroup>\n                            @endforeach\n                        </select>\n                        <p class=\"text-muted small\">此设置除了将数据库默认添加到所选节点上的服务器以外没有任何作用.</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-sm-6\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">用户详情</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"pUsername\" class=\"form-label\">用户名</label>\n                        <input type=\"text\" name=\"username\" id=\"pUsername\" class=\"form-control\" value=\"{{ old('username', $host->username) }}\" />\n                        <p class=\"text-muted small\">具有足够权限在系统上创建新用户和数据库的帐户的用户名.</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pPassword\" class=\"form-label\">密码</label>\n                        <input type=\"password\" name=\"password\" id=\"pPassword\" class=\"form-control\" />\n                        <p class=\"text-muted small\">已定义帐户的密码。留空以继续使用分配的密码.</p>\n                    </div>\n                    <hr />\n                    <p class=\"text-danger small text-left\">连接此数据库主机所使用的账户 <strong>必须</strong> 具有 <code>WITH GRANT OPTION</code> 权限. 如果账户没有此权限将 <em>无法</em> 成功建立数据库. <strong>不要为 MySQL 使用您为此面板使用的相同帐户详细信息.</strong></p>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <button name=\"_method\" value=\"PATCH\" class=\"btn btn-sm btn-primary pull-right\">保存</button>\n                    <button name=\"_method\" value=\"DELETE\" class=\"btn btn-sm btn-danger pull-left muted muted-hover\"><i class=\"fa fa-trash-o\"></i></button>\n                </div>\n            </div>\n        </div>\n    </div>\n</form>\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">数据库</h3>\n            </div>\n            <div class=\"box-body table-responsive no-padding\">\n                <table class=\"table table-hover\">\n                    <tr>\n                        <th>服务器</th>\n                        <th>数据库名</th>\n                        <th>用户名</th>\n                        <th>连接白名单</th>\n                        <th>最大连接数</th>\n                        <th></th>\n                    </tr>\n                    @foreach($databases as $database)\n                        <tr>\n                            <td class=\"middle\"><a href=\"{{ route('admin.servers.view', $database->getRelation('server')->id) }}\">{{ $database->getRelation('server')->name }}</a></td>\n                            <td class=\"middle\">{{ $database->database }}</td>\n                            <td class=\"middle\">{{ $database->username }}</td>\n                            <td class=\"middle\">{{ $database->remote }}</td>\n                            @if($database->max_connections != null)\n                                <td class=\"middle\">{{ $database->max_connections }}</td>\n                            @else\n                                <td class=\"middle\">无限制</td>\n                            @endif\n                            <td class=\"text-center\">\n                                <a href=\"{{ route('admin.servers.view.database', $database->getRelation('server')->id) }}\">\n                                    <button class=\"btn btn-xs btn-primary\">管理</button>\n                                </a>\n                            </td>\n                        </tr>\n                    @endforeach\n                </table>\n            </div>\n            @if($databases->hasPages())\n                <div class=\"box-footer with-border\">\n                    <div class=\"col-md-12 text-center\">{!! $databases->render() !!}</div>\n                </div>\n            @endif\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n        $('#pNodeId').select2();\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/eggs/new.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    预设配置\n@endsection\n\n@section('content-header')\n    <h1>新预设<small>为服务器创建新预设.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nests') }}\">预设组</a></li>\n        <li class=\"active\">新预设</li>\n    </ol>\n@endsection\n\n@section('content')\n<form action=\"{{ route('admin.nests.egg.new') }}\" method=\"POST\">\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">配置</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"row\">\n                        <div class=\"col-sm-6\">\n                            <div class=\"form-group\">\n                                <label for=\"pNestId\" class=\"form-label\">所属预设组</label>\n                                <div>\n                                    <select name=\"nest_id\" id=\"pNestId\">\n                                        @foreach($nests as $nest)\n                                        <option value=\"{{ $nest->id }}\" {{ old('nest_id') != $nest->id ?: 'selected' }}>{{ $nest->name }} &lt;{{ $nest->author }}&gt;</option>\n                                        @endforeach\n                                    </select>\n                                    <p class=\"text-muted small\">官方将此功能定义为 Nest 和 Egg，为了中文语境下更方便理解，将其翻译为预设组和预设。</p>\n                                </div>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pName\" class=\"form-label\">预设名</label>\n                                <input type=\"text\" id=\"pName\" name=\"name\" value=\"{{ old('name') }}\" class=\"form-control\" />\n                                <p class=\"text-muted small\">一个简单的、易读的，用作此预设的标识符。这是用户将看到的游戏服务器类型.</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pDescription\" class=\"form-label\">描述</label>\n                                <textarea id=\"pDescription\" name=\"description\" class=\"form-control\" rows=\"8\">{{ old('description') }}</textarea>\n                                <p class=\"text-muted small\">预设的描述.</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <div class=\"checkbox checkbox-primary no-margin-bottom\">\n                                    <input id=\"pForceOutgoingIp\" name=\"force_outgoing_ip\" type=\"checkbox\" value=\"1\" {{ \\Pterodactyl\\Helpers\\Utilities::checked('force_outgoing_ip', 0) }} />\n                                    <label for=\"pForceOutgoingIp\" class=\"strong\">强制传出 IP</label>\n                                    <p class=\"text-muted small\">\n                                        强制所有传出的网络流量将其源 IP地址转换(NAT) 到服务器首选IP 的 IP地址。\n                                        当节点具有多个公共IP地址时，某些游戏需要它才能正常运行。\n                                        <br>\n                                        <strong>\n                                            启用此选项将禁用任何使用此预设的服务器内网，这将导致它们无法从内部访问同一节点上的其他服务器。\n                                        </strong>\n                                    </p>\n                                </div>\n                            </div>\n                        </div>\n                        <div class=\"col-sm-6\">\n                            <div class=\"form-group\">\n                                <label for=\"pDockerImage\" class=\"control-label\">Docker 镜像</label>\n                                <textarea id=\"pDockerImages\" name=\"docker_images\" rows=\"4\" placeholder=\"ghcr.io/pterodactyl/yolks\" class=\"form-control\">{{ old('docker_images') }}</textarea>\n                                <p class=\"text-muted small\">使用这个预设的服务器可用的 Docker 镜像。每行输入一个。如果提供了多个值，用户将能够从此图像列表中自行选择。</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pStartup\" class=\"control-label\">启动命令</label>\n                                <textarea id=\"pStartup\" name=\"startup\" class=\"form-control\" rows=\"10\">{{ old('startup') }}</textarea>\n                                <p class=\"text-muted small\">用于此预设创建的新服务器的默认启动命令。您可以根据需要更改每个服务器。</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pConfigFeatures\" class=\"control-label\">功能</label>\n                                <div>\n                                    <select class=\"form-control\" name=\"features[]\" id=\"pConfigFeatures\" multiple>\n                                    </select>\n                                    <p class=\"text-muted small\">属于该预设的附加功能，用于配置面板的额外修改。</p>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">进程管理识别</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"row\">\n                        <div class=\"col-xs-12\">\n                            <div class=\"alert alert-warning\">\n                                <p>除非您从“复制设置自”下拉菜单中选择单独的选项，否则下方所有框框都是必填的，在使用复制设置情况下，框框可以留空以使用原预设中的值。</p>\n                            </div>\n                        </div>\n                        <div class=\"col-sm-6\">\n                            <div class=\"form-group\">\n                                <label for=\"pConfigFrom\" class=\"form-label\">复制设置自</label>\n                                <select name=\"config_from\" id=\"pConfigFrom\" class=\"form-control\">\n                                    <option value=\"\">无</option>\n                                </select>\n                                <p class=\"text-muted small\">如果您想默认使用另一个预设的设置，请从上面的下拉列表中选择它。</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pConfigStop\" class=\"form-label\">关机命令</label>\n                                <input type=\"text\" id=\"pConfigStop\" name=\"config_stop\" class=\"form-control\" value=\"{{ old('config_stop') }}\" />\n                                <p class=\"text-muted small\">应该发送到服务器进程以正常停止它们的命令。如果你需要输出 <code>SIGINT</code> 你应该填入 <code>^C</code> 于此。</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pConfigLogs\" class=\"form-label\">日志设置</label>\n                                <textarea data-action=\"handle-tabs\" id=\"pConfigLogs\" name=\"config_logs\" class=\"form-control\" rows=\"6\">{{ old('config_logs') }}</textarea>\n                                <p class=\"text-muted small\">这里应该用 JSON 格式语法来让系统判断是否进行日志记录并指定日志存储的位置。</p>\n                            </div>\n                        </div>\n                        <div class=\"col-sm-6\">\n                            <div class=\"form-group\">\n                                <label for=\"pConfigFiles\" class=\"form-label\">配置文件</label>\n                                <textarea data-action=\"handle-tabs\" id=\"pConfigFiles\" name=\"config_files\" class=\"form-control\" rows=\"6\">{{ old('config_files') }}</textarea>\n                                <p class=\"text-muted small\">这里应该使用 JSON 格式语法来让系统判断更改那些配置文件以及更改何处。</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pConfigStartup\" class=\"form-label\">启动识别</label>\n                                <textarea data-action=\"handle-tabs\" id=\"pConfigStartup\" name=\"config_startup\" class=\"form-control\" rows=\"6\">{{ old('config_startup') }}</textarea>\n                                <p class=\"text-muted small\">这里应该使用 JSON 格式语法来让系统判断服务端程序是否已正常启动完成。</p>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <button type=\"submit\" class=\"btn btn-success btn-sm pull-right\">创建</button>\n                </div>\n            </div>\n        </div>\n    </div>\n</form>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    {!! Theme::js('vendor/lodash/lodash.js') !!}\n    <script>\n    $(document).ready(function() {\n        $('#pNestId').select2().change();\n        $('#pConfigFrom').select2();\n    });\n    $('#pNestId').on('change', function (event) {\n        $('#pConfigFrom').html('<option value=\"\">None</option>').select2({\n            data: $.map(_.get(Pterodactyl.nests, $(this).val() + '.eggs', []), function (item) {\n                return {\n                    id: item.id,\n                    text: item.name + ' <' + item.author + '>',\n                };\n            }),\n        });\n    });\n    $('textarea[data-action=\"handle-tabs\"]').on('keydown', function(event) {\n        if (event.keyCode === 9) {\n            event.preventDefault();\n\n            var curPos = $(this)[0].selectionStart;\n            var prepend = $(this).val().substr(0, curPos);\n            var append = $(this).val().substr(curPos);\n\n            $(this).val(prepend + '    ' + append);\n        }\n    });\n    $('#pConfigFeatures').select2({\n        tags: true,\n        selectOnClose: false,\n        tokenSeparators: [',', ' '],\n    });\n</script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/eggs/scripts.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    预设配置: {{ $egg->name }} &rarr; 安装脚本\n@endsection\n\n@section('content-header')\n    <h1>{{ $egg->name }}<small>管理预设使用的安装脚本.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nests') }}\">预设组</a></li>\n        <li><a href=\"{{ route('admin.nests.view', $egg->nest->id) }}\">{{ $egg->nest->name }}</a></li>\n        <li><a href=\"{{ route('admin.nests.egg.view', $egg->id) }}\">{{ $egg->name }}</a></li>\n        <li class=\"active\">{{ $egg->name }}</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"nav-tabs-custom nav-tabs-floating\">\n            <ul class=\"nav nav-tabs\">\n                <li><a href=\"{{ route('admin.nests.egg.view', $egg->id) }}\">设置</a></li>\n                <li><a href=\"{{ route('admin.nests.egg.variables', $egg->id) }}\">变量</a></li>\n                <li class=\"active\"><a href=\"{{ route('admin.nests.egg.scripts', $egg->id) }}\">安装脚本</a></li>\n            </ul>\n        </div>\n    </div>\n</div>\n<form action=\"{{ route('admin.nests.egg.scripts', $egg->id) }}\" method=\"POST\">\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">安装脚本</h3>\n                </div>\n                @if(! is_null($egg->copyFrom))\n                    <div class=\"box-body\">\n                        <div class=\"callout callout-warning no-margin\">\n                            这个选项是复制预设配置于另一个配置 <a href=\"{{ route('admin.nests.egg.view', $egg->copyFrom->id) }}\">{{ $egg->copyFrom->name }}</a>. 除非您从下面的下拉框中选择“无”，否则您对此脚本所做的任何更改都不会应用.\n                        </div>\n                    </div>\n                @endif\n                <div class=\"box-body no-padding\">\n                    <div id=\"editor_install\"style=\"height:300px\">{{ $egg->script_install }}</div>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"row\">\n                        <div class=\"form-group col-sm-4\">\n                            <label class=\"control-label\">脚本复制于</label>\n                            <select id=\"pCopyScriptFrom\" name=\"copy_script_from\">\n                                <option value=\"\">无</option>\n                                @foreach($copyFromOptions as $opt)\n                                    <option value=\"{{ $opt->id }}\" {{ $egg->copy_script_from !== $opt->id ?: 'selected' }}>{{ $opt->name }}</option>\n                                @endforeach\n                            </select>\n                            <p class=\"text-muted small\">如果选中，上方的安装脚本将被忽略，所选选项中的安装脚本将被使用.</p>\n                        </div>\n                        <div class=\"form-group col-sm-4\">\n                            <label class=\"control-label\">脚本容器</label>\n                            <input type=\"text\" name=\"script_container\" class=\"form-control\" value=\"{{ $egg->script_container }}\" />\n                            <p class=\"text-muted small\">在为服务器运行此脚本时使用的 Docker 容器，以供脚本能够正常运行。</p>\n                        </div>\n                        <div class=\"form-group col-sm-4\">\n                            <label class=\"control-label\">脚本入口命令</label>\n                            <input type=\"text\" name=\"script_entry\" class=\"form-control\" value=\"{{ $egg->script_entry }}\" />\n                            <p class=\"text-muted small\">用于此脚本的入口命令.</p>\n                        </div>\n                    </div>\n                    <div class=\"row\">\n                        <div class=\"col-xs-12 text-muted\">\n                            以下服务选项依赖于此脚本:\n                            @if(count($relyOnScript) > 0)\n                                @foreach($relyOnScript as $rely)\n                                    <a href=\"{{ route('admin.nests.egg.view', $rely->id) }}\">\n                                        <code>{{ $rely->name }}</code>@if(!$loop->last),&nbsp;@endif\n                                    </a>\n                                @endforeach\n                            @else\n                                <em>无</em>\n                            @endif\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <textarea name=\"script_install\" class=\"hidden\"></textarea>\n                    <button type=\"submit\" name=\"_method\" value=\"PATCH\" class=\"btn btn-primary btn-sm pull-right\">保存</button>\n                </div>\n            </div>\n        </div>\n    </div>\n</form>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    {!! Theme::js('vendor/ace/ace.js') !!}\n    {!! Theme::js('vendor/ace/ext-modelist.js') !!}\n    <script>\n    $(document).ready(function () {\n        $('#pCopyScriptFrom').select2();\n\n        const InstallEditor = ace.edit('editor_install');\n        const Modelist = ace.require('ace/ext/modelist')\n\n        InstallEditor.setTheme('ace/theme/chrome');\n        InstallEditor.getSession().setMode('ace/mode/sh');\n        InstallEditor.getSession().setUseWrapMode(true);\n        InstallEditor.setShowPrintMargin(false);\n\n        $('form').on('submit', function (e) {\n            $('textarea[name=\"script_install\"]').val(InstallEditor.getValue());\n        });\n    });\n    </script>\n\n@endsection\n"
  },
  {
    "path": "resources/views/admin/eggs/variables.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    预设 &rarr; {{ $egg->name }} &rarr; 变量\n@endsection\n\n@section('content-header')\n    <h1>{{ $egg->name }}<small>管理预设所使用的变量.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nests') }}\">预设组</a></li>\n        <li><a href=\"{{ route('admin.nests.view', $egg->nest->id) }}\">{{ $egg->nest->name }}</a></li>\n        <li><a href=\"{{ route('admin.nests.egg.view', $egg->id) }}\">{{ $egg->name }}</a></li>\n        <li class=\"active\">变量</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"nav-tabs-custom nav-tabs-floating\">\n            <ul class=\"nav nav-tabs\">\n                <li><a href=\"{{ route('admin.nests.egg.view', $egg->id) }}\">设置</a></li>\n                <li class=\"active\"><a href=\"{{ route('admin.nests.egg.variables', $egg->id) }}\">变量</a></li>\n                <li><a href=\"{{ route('admin.nests.egg.scripts', $egg->id) }}\">安装脚本</a></li>\n            </ul>\n        </div>\n    </div>\n</div>\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box no-border\">\n            <div class=\"box-body\">\n                <a href=\"#\" class=\"btn btn-sm btn-success pull-right\" data-toggle=\"modal\" data-target=\"#newVariableModal\">新建变量</a>\n            </div>\n        </div>\n    </div>\n</div>\n<div class=\"row\">\n    @foreach($egg->variables as $variable)\n        <div class=\"col-sm-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">{{ $variable->name }}</h3>\n                </div>\n                <form action=\"{{ route('admin.nests.egg.variables.edit', ['egg' => $egg->id, 'variable' => $variable->id]) }}\" method=\"POST\">\n                    <div class=\"box-body\">\n                        <div class=\"form-group\">\n                            <label class=\"form-label\">名称</label>\n                            <input type=\"text\" name=\"name\" value=\"{{ $variable->name }}\" class=\"form-control\" />\n                        </div>\n                        <div class=\"form-group\">\n                            <label class=\"form-label\">描述</label>\n                            <textarea name=\"description\" class=\"form-control\" rows=\"3\">{{ $variable->description }}</textarea>\n                        </div>\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-6\">\n                                <label class=\"form-label\">环境变量</label>\n                                <input type=\"text\" name=\"env_variable\" value=\"{{ $variable->env_variable }}\" class=\"form-control\" />\n                            </div>\n                            <div class=\"form-group col-md-6\">\n                                <label class=\"form-label\">默认值</label>\n                                <input type=\"text\" name=\"default_value\" value=\"{{ $variable->default_value }}\" class=\"form-control\" />\n                            </div>\n                            <div class=\"col-xs-12\">\n                                <p class=\"text-muted small\">这个变量可以在启动命令中以 <code>{{ $variable->env_variable }}</code> 来使用.</p>\n                            </div>\n                        </div>\n                        <div class=\"form-group\">\n                            <label class=\"form-label\">权限</label>\n                            <select name=\"options[]\" class=\"pOptions form-control\" multiple>\n                                <option value=\"user_viewable\" {{ (! $variable->user_viewable) ?: 'selected' }}>用户只读</option>\n                                <option value=\"user_editable\" {{ (! $variable->user_editable) ?: 'selected' }}>用户可写</option>\n                            </select>\n                        </div>\n                        <div class=\"form-group\">\n                            <label class=\"form-label\">输入规则</label>\n                            <input type=\"text\" name=\"rules\" class=\"form-control\" value=\"{{ $variable->rules }}\" />\n                            <p class=\"text-muted small\">这些规则是使用 <a href=\"https://laravel.com/docs/10.x/validation#available-validation-rules\" target=\"_blank\">Laravel 框架验证规则</a> 标准定义的.</p>\n                        </div>\n                    </div>\n                    <div class=\"box-footer\">\n                        {!! csrf_field() !!}\n                        <button class=\"btn btn-sm btn-primary pull-right\" name=\"_method\" value=\"PATCH\" type=\"submit\">保存</button>\n                        <button class=\"btn btn-sm btn-danger pull-left muted muted-hover\" data-action=\"delete\" name=\"_method\" value=\"DELETE\" type=\"submit\"><i class=\"fa fa-trash-o\"></i></button>\n                    </div>\n                </form>\n            </div>\n        </div>\n    @endforeach\n</div>\n<div class=\"modal fade\" id=\"newVariableModal\" tabindex=\"-1\" role=\"dialog\">\n    <div class=\"modal-dialog\" role=\"document\">\n        <div class=\"modal-content\">\n            <div class=\"modal-header\">\n                <button type=\"button\" class=\"close\" data-dismiss=\"modal\" aria-label=\"Close\"><span aria-hidden=\"true\">&times;</span></button>\n                <h4 class=\"modal-title\">创建新预设变量</h4>\n            </div>\n            <form action=\"{{ route('admin.nests.egg.variables', $egg->id) }}\" method=\"POST\">\n                <div class=\"modal-body\">\n                    <div class=\"form-group\">\n                        <label class=\"control-label\">名称 <span class=\"field-required\"></span></label>\n                        <input type=\"text\" name=\"name\" class=\"form-control\" value=\"{{ old('name') }}\"/>\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"control-label\">描述</label>\n                        <textarea name=\"description\" class=\"form-control\" rows=\"3\">{{ old('description') }}</textarea>\n                    </div>\n                    <div class=\"row\">\n                        <div class=\"form-group col-md-6\">\n                            <label class=\"control-label\">环境变量 <span class=\"field-required\"></span></label>\n                            <input type=\"text\" name=\"env_variable\" class=\"form-control\" value=\"{{ old('env_variable') }}\" />\n                        </div>\n                        <div class=\"form-group col-md-6\">\n                            <label class=\"control-label\">默认值</label>\n                            <input type=\"text\" name=\"default_value\" class=\"form-control\" value=\"{{ old('default_value') }}\" />\n                        </div>\n                        <div class=\"col-xs-12\">\n                            <p class=\"text-muted small\">这个变量可以在启动命令中以 <code>@{{environment variable value}}</code> 来使用.</p>\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"control-label\">权限</label>\n                        <select name=\"options[]\" class=\"pOptions form-control\" multiple>\n                            <option value=\"user_viewable\">用户只读</option>\n                            <option value=\"user_editable\">用户可写</option>\n                        </select>\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"control-label\">输入规则 <span class=\"field-required\"></span></label>\n                        <input type=\"text\" name=\"rules\" class=\"form-control\" value=\"{{ old('rules', 'required|string|max:20') }}\" placeholder=\"required|string|max:20\" />\n                        <p class=\"text-muted small\">这些规则是使用 <a href=\"https://laravel.com/docs/10.x/validation#available-validation-rules\" target=\"_blank\">Laravel 框架验证规则</a> 标准定义的.</p>\n                    </div>\n                </div>\n                <div class=\"modal-footer\">\n                    {!! csrf_field() !!}\n                    <button type=\"button\" class=\"btn btn-default pull-left\" data-dismiss=\"modal\">关闭</button>\n                    <button type=\"submit\" class=\"btn btn-primary\">创建变量</button>\n                </div>\n            </form>\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n        $('.pOptions').select2();\n        $('[data-action=\"delete\"]').on('mouseenter', function (event) {\n            $(this).find('i').html(' 删除变量');\n        }).on('mouseleave', function (event) {\n            $(this).find('i').html('');\n        });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/eggs/view.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    预设配置: {{ $egg->name }}\n@endsection\n\n@section('content-header')\n    <h1>{{ $egg->name }}<small>{{ str_limit($egg->description, 50) }}</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nests') }}\">预设</a></li>\n        <li><a href=\"{{ route('admin.nests.view', $egg->nest->id) }}\">{{ $egg->nest->name }}</a></li>\n        <li class=\"active\">{{ $egg->name }}</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"nav-tabs-custom nav-tabs-floating\">\n            <ul class=\"nav nav-tabs\">\n                <li class=\"active\"><a href=\"{{ route('admin.nests.egg.view', $egg->id) }}\">设置</a></li>\n                <li><a href=\"{{ route('admin.nests.egg.variables', $egg->id) }}\">变量</a></li>\n                <li><a href=\"{{ route('admin.nests.egg.scripts', $egg->id) }}\">安装脚本</a></li>\n            </ul>\n        </div>\n    </div>\n</div>\n<form action=\"{{ route('admin.nests.egg.view', $egg->id) }}\" enctype=\"multipart/form-data\" method=\"POST\">\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box box-danger\">\n                <div class=\"box-body\">\n                    <div class=\"row\">\n                        <div class=\"col-xs-8\">\n                            <div class=\"form-group no-margin-bottom\">\n                                <label for=\"pName\" class=\"control-label\">预设文件</label>\n                                <div>\n                                    <input type=\"file\" name=\"import_file\" class=\"form-control\" style=\"border: 0;margin-left:-10px;\" />\n                                    <p class=\"text-muted small no-margin-bottom\">如果您想通过上传新的 JSON 文件来替换此预设的设置，只需在此处选择它并按“更新预设”。这不会更改现有服务器使用的任何启动命令或 Docker 映像。</p>\n                                </div>\n                            </div>\n                        </div>\n                        <div class=\"col-xs-4\">\n                            {!! csrf_field() !!}\n                            <button type=\"submit\" name=\"_method\" value=\"PUT\" class=\"btn btn-sm btn-danger pull-right\">更新预设</button>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n</form>\n<form action=\"{{ route('admin.nests.egg.view', $egg->id) }}\" method=\"POST\">\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">设置</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"row\">\n                        <div class=\"col-sm-6\">\n                            <div class=\"form-group\">\n                                <label for=\"pName\" class=\"control-label\">名称 <span class=\"field-required\"></span></label>\n                                <input type=\"text\" id=\"pName\" name=\"name\" value=\"{{ $egg->name }}\" class=\"form-control\" />\n                                <p class=\"text-muted small\">一个简单的、易读的名称，用作此预设的标识符。</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pUuid\" class=\"control-label\">UUID</label>\n                                <input type=\"text\" id=\"pUuid\" readonly value=\"{{ $egg->uuid }}\" class=\"form-control\" />\n                                <p class=\"text-muted small\">这是这个预设的全局唯一标识符，守护进程将其用作预设分辨依据.</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pAuthor\" class=\"control-label\">作者</label>\n                                <input type=\"text\" id=\"pAuthor\" readonly value=\"{{ $egg->author }}\" class=\"form-control\" />\n                                <p class=\"text-muted small\">该预设作者默认不可修改，仅在新建预设时才可填写。</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pDockerImage\" class=\"control-label\">Docker 镜像 <span class=\"field-required\"></span></label>\n                                <textarea id=\"pDockerImages\" name=\"docker_images\" class=\"form-control\" rows=\"4\">{{ implode(PHP_EOL, $images) }}</textarea>\n                                <p class=\"text-muted small\">\n                                    使用这个预设的服务器可用的 docker 镜像。每行输入一个。\n                                    如果提供了多个值，用户则可以从此列表中自行选择。\n                                    也可以通过在镜像地址前面加上名称来提供显示名称\n                                    后跟一个竖线字符，然后是镜像 URL. 例如: <code>镜像显示名称|ghcr.io/my/egg</code>\n                                </p>\n                            </div>\n                            <div class=\"form-group\">\n                                <div class=\"checkbox checkbox-primary no-margin-bottom\">\n                                    <input id=\"pForceOutgoingIp\" name=\"force_outgoing_ip\" type=\"checkbox\" value=\"1\" @if($egg->force_outgoing_ip) checked @endif />\n                                    <label for=\"pForceOutgoingIp\" class=\"strong\">强制传出 IP</label>\n                                    <p class=\"text-muted small\">\n                                        强制所有传出的网络流量将其源 IP地址转换（NAT）到服务器首选IP 的 IP地址。\n                                        当节点具有多个公共IP地址时，某些游戏需要它才能正常运行。\n                                        <br>\n                                        <strong>\n                                            启用此选项将禁用任何使用此预设的服务器内网，这将导致它们无法从内部访问同一节点上的其他服务器。\n                                        </strong>\n                                    </p>\n                                </div>\n                            </div>\n\n                        </div>\n                        <div class=\"col-sm-6\">\n                            <div class=\"form-group\">\n                                <label for=\"pDescription\" class=\"control-label\">描述</label>\n                                <textarea id=\"pDescription\" name=\"description\" class=\"form-control\" rows=\"8\">{{ $egg->description }}</textarea>\n                                <p class=\"text-muted small\">将根据需要在整个面板中显示的此预设的描述.</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pStartup\" class=\"control-label\">启动命令 <span class=\"field-required\"></span></label>\n                                <textarea id=\"pStartup\" name=\"startup\" class=\"form-control\" rows=\"8\">{{ $egg->startup }}</textarea>\n                                <p class=\"text-muted small\">使用此预设的新服务器的默认启动命令.</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pConfigFeatures\" class=\"control-label\">功能</label>\n                                <div>\n                                    <select class=\"form-control\" name=\"features[]\" id=\"pConfigFeatures\" multiple>\n                                        @foreach(($egg->features ?? []) as $feature)\n                                            <option value=\"{{ $feature }}\" selected>{{ $feature }}</option>\n                                        @endforeach\n                                    </select>\n                                    <p class=\"text-muted small\">属于该预设的附加功能，用于配置面板的额外修改。</p>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">进程管理识别</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"row\">\n                        <div class=\"col-xs-12\">\n                            <div class=\"alert alert-warning\">\n                                <p>除非您了解此系统的工作原理，否则不应编辑以下配置选项。如果修改错误，守护程序主机可能会宕机。</p>\n                                <p>除非您从“复制设置自”下拉列表中选择单独的选项，否则所有字段都是必需的，在这种情况下，字段可能会留空以使用该预设中的值.</p>\n                            </div>\n                        </div>\n                        <div class=\"col-sm-6\">\n                            <div class=\"form-group\">\n                                <label for=\"pConfigFrom\" class=\"form-label\">复制设置自</label>\n                                <select name=\"config_from\" id=\"pConfigFrom\" class=\"form-control\">\n                                    <option value=\"\">无</option>\n                                    @foreach($egg->nest->eggs as $o)\n                                        <option value=\"{{ $o->id }}\" {{ ($egg->config_from !== $o->id) ?: 'selected' }}>{{ $o->name }} &lt;{{ $o->author }}&gt;</option>\n                                    @endforeach\n                                </select>\n                                <p class=\"text-muted small\">如果您想默认使用另一个预设的设置，请从上面的菜单中选择它.</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pConfigStop\" class=\"form-label\">关机指令</label>\n                                <input type=\"text\" id=\"pConfigStop\" name=\"config_stop\" class=\"form-control\" value=\"{{ $egg->config_stop }}\" />\n                                <p class=\"text-muted small\">应该发送到服务器进程以正常停止它们的命令。如果你需要输出 <code>SIGINT</code> 你应该填入 <code>^C</code> 于此。</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pConfigLogs\" class=\"form-label\">日志设置</label>\n                                <textarea data-action=\"handle-tabs\" id=\"pConfigLogs\" name=\"config_logs\" class=\"form-control\" rows=\"6\">{{ ! is_null($egg->config_logs) ? json_encode(json_decode($egg->config_logs), JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES) : '' }}</textarea>\n                                <p class=\"text-muted small\">这里应该用 JSON 格式语法来让系统判断是否进行日志记录并指定日志存储的位置。</p>\n                            </div>\n                        </div>\n                        <div class=\"col-sm-6\">\n                            <div class=\"form-group\">\n                                <label for=\"pConfigFiles\" class=\"form-label\">配置文件</label>\n                                <textarea data-action=\"handle-tabs\" id=\"pConfigFiles\" name=\"config_files\" class=\"form-control\" rows=\"6\">{{ ! is_null($egg->config_files) ? json_encode(json_decode($egg->config_files), JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES) : '' }}</textarea>\n                                <p class=\"text-muted small\">这里应该用 JSON 格式语法来让系统判断是否进行指定配置文件中部分内容修改。</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pConfigStartup\" class=\"form-label\">启动识别</label>\n                                <textarea data-action=\"handle-tabs\" id=\"pConfigStartup\" name=\"config_startup\" class=\"form-control\" rows=\"6\">{{ ! is_null($egg->config_startup) ? json_encode(json_decode($egg->config_startup), JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES) : '' }}</textarea>\n                                <p class=\"text-muted small\">这里应该使用 JSON 格式语法来让系统判断服务端程序是否已正常启动完成。</p>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <button type=\"submit\" name=\"_method\" value=\"PATCH\" class=\"btn btn-primary btn-sm pull-right\">保存</button>\n                    <a href=\"{{ route('admin.nests.egg.export', $egg->id) }}\" class=\"btn btn-sm btn-info pull-right\" style=\"margin-right:10px;\">导出</a>\n                    <button id=\"deleteButton\" type=\"submit\" name=\"_method\" value=\"DELETE\" class=\"btn btn-danger btn-sm muted muted-hover\">\n                        <i class=\"fa fa-trash-o\"></i>\n                    </button>\n                </div>\n            </div>\n        </div>\n    </div>\n</form>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    $('#pConfigFrom').select2();\n    $('#deleteButton').on('mouseenter', function (event) {\n        $(this).find('i').html(' 删除预设');\n    }).on('mouseleave', function (event) {\n        $(this).find('i').html('');\n    });\n    $('textarea[data-action=\"handle-tabs\"]').on('keydown', function(event) {\n        if (event.keyCode === 9) {\n            event.preventDefault();\n\n            var curPos = $(this)[0].selectionStart;\n            var prepend = $(this).val().substr(0, curPos);\n            var append = $(this).val().substr(curPos);\n\n            $(this).val(prepend + '    ' + append);\n        }\n    });\n    $('#pConfigFeatures').select2({\n        tags: true,\n        selectOnClose: false,\n        tokenSeparators: [',', ' '],\n    });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/index.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    管理\n@endsection\n\n@section('content-header')\n    <h1>管理概况<small>快速浏览您的系统.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">首页</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box\n            @if($version->isLatestPanel())\n                box-success\n            @else\n                box-danger\n            @endif\n        \">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">系统信息</h3>\n            </div>\n            <div class=\"box-body\">\n                @if ($version->isLatestPanel())\n                    您正运行的 Pterodactyl-CHINA 面板版本为 <code>{{ config('app.version') }}</code>。您的面板目前是最新的！\n                @else\n                    您目前使用的面板 <strong>并非最新!</strong> 目前最新版本为 <a href=\"https://github.com/pterodactyl-china/panel/releases/v{{ $version->getPanel() }}\" target=\"_blank\"><code>{{ $version->getPanel() }}</code></a> 您正运行的版本为 <code>{{ config('app.version') }}</code>.\n                @endif\n            </div>\n        </div>\n    </div>\n</div>\n<div class=\"row\">\n    <div class=\"col-xs-6 col-sm-3 text-center\">\n        <a href=\"{{ $version->getDiscord() }}\"><button class=\"btn btn-warning\" style=\"width:100%;\"><i class=\"fa fa-fw fa-support\"></i> 获取帮助 <small>(翼龙中国社区)</small></button></a>\n    </div>\n    <div class=\"col-xs-6 col-sm-3 text-center\">\n        <a href=\"https://pterodactyl.top\"><button class=\"btn btn-primary\" style=\"width:100%;\"><i class=\"fa fa-fw fa-link\"></i> 翼龙中国文档</button></a>\n    </div>\n    <div class=\"clearfix visible-xs-block\">&nbsp;</div>\n    <div class=\"col-xs-6 col-sm-3 text-center\">\n        <a href=\"https://github.com/pterodactyl-china/panel\"><button class=\"btn btn-primary\" style=\"width:100%;\"><i class=\"fa fa-fw fa-support\"></i> GitHub</button></a>\n    </div>\n    <div class=\"col-xs-6 col-sm-3 text-center\">\n        <a href=\"{{ $version->getDonations() }}\"><button class=\"btn btn-success\" style=\"width:100%;\"><i class=\"fa fa-fw fa-money\"></i> 支持此项目</button></a>\n    </div>\n</div>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/locations/index.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    地域\n@endsection\n\n@section('content-header')\n    <h1>地域<small>可以将节点分配到所有地域以便于分类。</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">地域</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">地域列表</h3>\n                <div class=\"box-tools\">\n                    <button class=\"btn btn-sm btn-primary\" data-toggle=\"modal\" data-target=\"#newLocationModal\">新建</button>\n                </div>\n            </div>\n            <div class=\"box-body table-responsive no-padding\">\n                <table class=\"table table-hover\">\n                    <tbody>\n                        <tr>\n                            <th>ID</th>\n                            <th>标识码</th>\n                            <th>描述</th>\n                            <th class=\"text-center\">节点</th>\n                            <th class=\"text-center\">服务器</th>\n                        </tr>\n                        @foreach ($locations as $location)\n                            <tr>\n                                <td><code>{{ $location->id }}</code></td>\n                                <td><a href=\"{{ route('admin.locations.view', $location->id) }}\">{{ $location->short }}</a></td>\n                                <td>{{ $location->long }}</td>\n                                <td class=\"text-center\">{{ $location->nodes_count }}</td>\n                                <td class=\"text-center\">{{ $location->servers_count }}</td>\n                            </tr>\n                        @endforeach\n                    </tbody>\n                </table>\n            </div>\n        </div>\n    </div>\n</div>\n<div class=\"modal fade\" id=\"newLocationModal\" tabindex=\"-1\" role=\"dialog\">\n    <div class=\"modal-dialog\" role=\"document\">\n        <div class=\"modal-content\">\n            <form action=\"{{ route('admin.locations') }}\" method=\"POST\">\n                <div class=\"modal-header\">\n                    <button type=\"button\" class=\"close\" data-dismiss=\"modal\" aria-label=\"Close\"><span aria-hidden=\"true\">&times;</span></button>\n                    <h4 class=\"modal-title\">创建地域</h4>\n                </div>\n                <div class=\"modal-body\">\n                    <div class=\"row\">\n                        <div class=\"col-md-12\">\n                            <label for=\"pShortModal\" class=\"form-label\">标识码</label>\n                            <input type=\"text\" name=\"short\" id=\"pShortModal\" class=\"form-control\" />\n                            <p class=\"text-muted small\">用于将此地域与其他地域区分开来的简短标识符。必须介于 1 到 60 个字符之间, 例如, <code>us.nyc.lvl3</code>.</p>\n                        </div>\n                        <div class=\"col-md-12\">\n                            <label for=\"pLongModal\" class=\"form-label\">描述</label>\n                            <textarea name=\"long\" id=\"pLongModal\" class=\"form-control\" rows=\"4\"></textarea>\n                            <p class=\"text-muted small\">此地域的详细说明，最多不应超过 191 个字符.</p>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"modal-footer\">\n                    {!! csrf_field() !!}\n                    <button type=\"button\" class=\"btn btn-default btn-sm pull-left\" data-dismiss=\"modal\">取消</button>\n                    <button type=\"submit\" class=\"btn btn-success btn-sm\">创建</button>\n                </div>\n            </form>\n        </div>\n    </div>\n</div>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/locations/view.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    地域 &rarr; 概览 &rarr; {{ $location->short }}\n@endsection\n\n@section('content-header')\n    <h1>{{ $location->short }}<small>{{ str_limit($location->long, 75) }}</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.locations') }}\">地域</a></li>\n        <li class=\"active\">{{ $location->short }}</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-sm-6\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">服务器组详情</h3>\n            </div>\n            <form action=\"{{ route('admin.locations.view', $location->id) }}\" method=\"POST\">\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"pShort\" class=\"form-label\">识别码</label>\n                        <input type=\"text\" id=\"pShort\" name=\"short\" class=\"form-control\" value=\"{{ $location->short }}\" />\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pLong\" class=\"form-label\">描述</label>\n                        <textarea id=\"pLong\" name=\"long\" class=\"form-control\" rows=\"4\">{{ $location->long }}</textarea>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    {!! method_field('PATCH') !!}\n                    <button name=\"action\" value=\"edit\" class=\"btn btn-sm btn-primary pull-right\">保存</button>\n                    <button name=\"action\" value=\"delete\" class=\"btn btn-sm btn-danger pull-left muted muted-hover\"><i class=\"fa fa-trash-o\"></i></button>\n                </div>\n            </form>\n        </div>\n    </div>\n    <div class=\"col-sm-6\">\n        <div class=\"box\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">节点</h3>\n            </div>\n            <div class=\"box-body table-responsive no-padding\">\n                <table class=\"table table-hover\">\n                    <tr>\n                        <th>ID</th>\n                        <th>名称</th>\n                        <th>域名</th>\n                        <th>服务器</th>\n                    </tr>\n                    @foreach($location->nodes as $node)\n                        <tr>\n                            <td><code>{{ $node->id }}</code></td>\n                            <td><a href=\"{{ route('admin.nodes.view', $node->id) }}\">{{ $node->name }}</a></td>\n                            <td><code>{{ $node->fqdn }}</code></td>\n                            <td>{{ $node->servers->count() }}</td>\n                        </tr>\n                    @endforeach\n                </table>\n            </div>\n        </div>\n    </div>\n</div>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/mounts/index.blade.php",
    "content": "\n@extends('layouts.admin')\n\n@section('title')\n    挂载\n@endsection\n\n@section('content-header')\n    <h1>挂载<small>配置和管理服务器的附加挂载点。</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">挂载</li>\n    </ol>\n@endsection\n\n@section('content')\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">挂载点列表</h3>\n\n                    <div class=\"box-tools\">\n                        <button class=\"btn btn-sm btn-primary\" data-toggle=\"modal\" data-target=\"#newMountModal\">新建</button>\n                    </div>\n                </div>\n\n                <div class=\"box-body table-responsive no-padding\">\n                    <table class=\"table table-hover\">\n                        <tbody>\n                            <tr>\n                                <th>ID</th>\n                                <th>名称</th>\n                                <th>来源路径</th>\n                                <th>挂载路径</th>\n                                <th class=\"text-center\">预设</th>\n                                <th class=\"text-center\">节点</th>\n                                <th class=\"text-center\">服务器</th>\n                            </tr>\n\n                            @foreach ($mounts as $mount)\n                                <tr>\n                                    <td><code>{{ $mount->id }}</code></td>\n                                    <td><a href=\"{{ route('admin.mounts.view', $mount->id) }}\">{{ $mount->name }}</a></td>\n                                    <td><code>{{ $mount->source }}</code></td>\n                                    <td><code>{{ $mount->target }}</code></td>\n                                    <td class=\"text-center\">{{ $mount->eggs_count }}</td>\n                                    <td class=\"text-center\">{{ $mount->nodes_count }}</td>\n                                    <td class=\"text-center\">{{ $mount->servers_count }}</td>\n                                </tr>\n                            @endforeach\n                        </tbody>\n                    </table>\n                </div>\n            </div>\n        </div>\n    </div>\n\n    <div class=\"modal fade\" id=\"newMountModal\" tabindex=\"-1\" role=\"dialog\">\n        <div class=\"modal-dialog\" role=\"document\">\n            <div class=\"modal-content\">\n                <form action=\"{{ route('admin.mounts') }}\" method=\"POST\">\n                    <div class=\"modal-header\">\n                        <button type=\"button\" class=\"close\" data-dismiss=\"modal\" aria-label=\"Close\">\n                            <span aria-hidden=\"true\" style=\"color: #FFFFFF\">&times;</span>\n                        </button>\n\n                        <h4 class=\"modal-title\">创建挂载</h4>\n                    </div>\n\n                    <div class=\"modal-body\">\n                        <div class=\"row\">\n                            <div class=\"col-md-12\">\n                                <label for=\"pName\" class=\"form-label\">名称</label>\n                                <input type=\"text\" id=\"pName\" name=\"name\" class=\"form-control\" />\n                                <p class=\"text-muted small\">用于将此挂载与另一个挂载分开的唯一名称.</p>\n                            </div>\n\n                            <div class=\"col-md-12\">\n                                <label for=\"pDescription\" class=\"form-label\">描述</label>\n                                <textarea id=\"pDescription\" name=\"description\" class=\"form-control\" rows=\"4\"></textarea>\n                                <p class=\"text-muted small\">此挂载的详细描述，不应多于 191 个字符.</p>\n                            </div>\n\n                            <div class=\"col-md-6\">\n                                <label for=\"pSource\" class=\"form-label\">来源路径</label>\n                                <input type=\"text\" id=\"pSource\" name=\"source\" class=\"form-control\" />\n                                <p class=\"text-muted small\">主机系统上要挂载到容器的文件路径.</p>\n                            </div>\n\n                            <div class=\"col-md-6\">\n                                <label for=\"pTarget\" class=\"form-label\">挂载路径</label>\n                                <input type=\"text\" id=\"pTarget\" name=\"target\" class=\"form-control\" />\n                                <p class=\"text-muted small\">将于容器内挂载的可读写文件路径.</p>\n                            </div>\n\n                            <div class=\"col-md-6\">\n                                <label class=\"form-label\">只读</label>\n\n                                <div>\n                                    <div class=\"radio radio-success radio-inline\">\n                                        <input type=\"radio\" id=\"pReadOnlyFalse\" name=\"read_only\" value=\"0\" checked>\n                                        <label for=\"pReadOnlyFalse\">否</label>\n                                    </div>\n\n                                    <div class=\"radio radio-warning radio-inline\">\n                                        <input type=\"radio\" id=\"pReadOnly\" name=\"read_only\" value=\"1\">\n                                        <label for=\"pReadOnly\">是</label>\n                                    </div>\n                                </div>\n\n                                <p class=\"text-muted small\">在容器文件系统内此挂载只读?</p>\n                            </div>\n\n                            <div class=\"col-md-6\">\n                                <label class=\"form-label\">用户可挂载</label>\n\n                                <div>\n                                    <div class=\"radio radio-success radio-inline\">\n                                        <input type=\"radio\" id=\"pUserMountableFalse\" name=\"user_mountable\" value=\"0\" checked>\n                                        <label for=\"pUserMountableFalse\">否</label>\n                                    </div>\n\n                                    <div class=\"radio radio-warning radio-inline\">\n                                        <input type=\"radio\" id=\"pUserMountable\" name=\"user_mountable\" value=\"1\">\n                                        <label for=\"pUserMountable\">是</label>\n                                    </div>\n                                </div>\n\n                                <p class=\"text-muted small\">用户是否可以自行进行挂载操作?</p>\n                            </div>\n                        </div>\n                    </div>\n\n                    <div class=\"modal-footer\">\n                        {!! csrf_field() !!}\n                        <button type=\"button\" class=\"btn btn-default btn-sm pull-left\" data-dismiss=\"modal\">取消</button>\n                        <button type=\"submit\" class=\"btn btn-success btn-sm\">创建</button>\n                    </div>\n                </form>\n            </div>\n        </div>\n    </div>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/mounts/view.blade.php",
    "content": "{{-- Pterodactyl CHINA - Panel --}}\n{{-- Copyright (c) 2015 - 2017 Dane Everitt <dane@daneeveritt.com> --}}\n{{-- Simplified Chinese Translation Copyright (c) 2018 - 2022 ValiantShishu <vlssu@vlssu.com> --}}\n\n{{-- This software is licensed under the terms of the MIT license. --}}\n{{-- https://opensource.org/licenses/MIT --}}\n\n@extends('layouts.admin')\n\n@section('title')\n    挂载 &rarr; 概览 &rarr; {{ $mount->id }}\n@endsection\n\n@section('content-header')\n    <h1>{{ $mount->name }}<small>{{ str_limit($mount->description, 75) }}</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.mounts') }}\">挂载</a></li>\n        <li class=\"active\">{{ $mount->name }}</li>\n    </ol>\n@endsection\n\n@section('content')\n    <div class=\"row\">\n        <div class=\"col-sm-6\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">挂载点详情</h3>\n                </div>\n\n                <form action=\"{{ route('admin.mounts.view', $mount->id) }}\" method=\"POST\">\n                    <div class=\"box-body\">\n                        <div class=\"form-group\">\n                            <label for=\"PUniqueID\" class=\"form-label\">ID</label>\n                            <input type=\"text\" id=\"PUniqueID\" class=\"form-control\" value=\"{{ $mount->uuid }}\" disabled />\n                        </div>\n\n                        <div class=\"form-group\">\n                            <label for=\"pName\" class=\"form-label\">名称</label>\n                            <input type=\"text\" id=\"pName\" name=\"name\" class=\"form-control\" value=\"{{ $mount->name }}\" />\n                        </div>\n\n                        <div class=\"form-group\">\n                            <label for=\"pDescription\" class=\"form-label\">描述</label>\n                            <textarea id=\"pDescription\" name=\"description\" class=\"form-control\" rows=\"4\">{{ $mount->description }}</textarea>\n                        </div>\n\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-6\">\n                                <label for=\"pSource\" class=\"form-label\">来源路径</label>\n                                <input type=\"text\" id=\"pSource\" name=\"source\" class=\"form-control\" value=\"{{ $mount->source }}\" />\n                            </div>\n\n                            <div class=\"form-group col-md-6\">\n                                <label for=\"pTarget\" class=\"form-label\">挂载路径</label>\n                                <input type=\"text\" id=\"pTarget\" name=\"target\" class=\"form-control\" value=\"{{ $mount->target }}\" />\n                            </div>\n                        </div>\n\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-6\">\n                                <label class=\"form-label\">只读</label>\n\n                                <div>\n                                    <div class=\"radio radio-success radio-inline\">\n                                        <input type=\"radio\" id=\"pReadOnlyFalse\" name=\"read_only\" value=\"0\" @if(!$mount->read_only) checked @endif>\n                                        <label for=\"pReadOnlyFalse\">否</label>\n                                    </div>\n\n                                    <div class=\"radio radio-warning radio-inline\">\n                                        <input type=\"radio\" id=\"pReadOnly\" name=\"read_only\" value=\"1\" @if($mount->read_only) checked @endif>\n                                        <label for=\"pReadOnly\">是</label>\n                                    </div>\n                                </div>\n                            </div>\n\n                            <div class=\"form-group col-md-6\">\n                                <label class=\"form-label\">用户可挂载</label>\n\n                                <div>\n                                    <div class=\"radio radio-success radio-inline\">\n                                        <input type=\"radio\" id=\"pUserMountableFalse\" name=\"user_mountable\" value=\"0\" @if(!$mount->user_mountable) checked @endif>\n                                        <label for=\"pUserMountableFalse\">否</label>\n                                    </div>\n\n                                    <div class=\"radio radio-warning radio-inline\">\n                                        <input type=\"radio\" id=\"pUserMountable\" name=\"user_mountable\" value=\"1\" @if($mount->user_mountable) checked @endif>\n                                        <label for=\"pUserMountable\">是</label>\n                                    </div>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n\n                    <div class=\"box-footer\">\n                        {!! csrf_field() !!}\n                        {!! method_field('PATCH') !!}\n\n                        <button name=\"action\" value=\"edit\" class=\"btn btn-sm btn-primary pull-right\">保存</button>\n                        <button name=\"action\" value=\"delete\" class=\"btn btn-sm btn-danger pull-left muted muted-hover\"><i class=\"fa fa-trash-o\"></i></button>\n                    </div>\n                </form>\n            </div>\n        </div>\n\n        <div class=\"col-sm-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">预设</h3>\n\n                    <div class=\"box-tools\">\n                        <button class=\"btn btn-sm btn-primary\" data-toggle=\"modal\" data-target=\"#addEggsModal\">添加预设</button>\n                    </div>\n                </div>\n\n                <div class=\"box-body table-responsive no-padding\">\n                    <table class=\"table table-hover\">\n                        <tr>\n                            <th>ID</th>\n                            <th>名称</th>\n                            <th></th>\n                        </tr>\n\n                        @foreach ($mount->eggs as $egg)\n                            <tr>\n                                <td class=\"col-sm-2 middle\"><code>{{ $egg->id }}</code></td>\n                                <td class=\"middle\"><a href=\"{{ route('admin.nests.egg.view', $egg->id) }}\">{{ $egg->name }}</a></td>\n                                <td class=\"col-sm-1 middle\">\n                                    <button data-action=\"detach-egg\" data-id=\"{{ $egg->id }}\" class=\"btn btn-sm btn-danger\"><i class=\"fa fa-trash-o\"></i></button>\n                                </td>\n                            </tr>\n                        @endforeach\n                    </table>\n                </div>\n            </div>\n\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">节点</h3>\n\n                    <div class=\"box-tools\">\n                        <button class=\"btn btn-sm btn-primary\" data-toggle=\"modal\" data-target=\"#addNodesModal\">添加节点</button>\n                    </div>\n                </div>\n\n                <div class=\"box-body table-responsive no-padding\">\n                    <table class=\"table table-hover\">\n                        <tr>\n                            <th>ID</th>\n                            <th>名称</th>\n                            <th>域名</th>\n                            <th></th>\n                        </tr>\n\n                        @foreach ($mount->nodes as $node)\n                            <tr>\n                                <td class=\"col-sm-2 middle\"><code>{{ $node->id }}</code></td>\n                                <td class=\"middle\"><a href=\"{{ route('admin.nodes.view', $node->id) }}\">{{ $node->name }}</a></td>\n                                <td class=\"middle\"><code>{{ $node->fqdn }}</code></td>\n                                <td class=\"col-sm-1 middle\">\n                                    <button data-action=\"detach-node\" data-id=\"{{ $node->id }}\" class=\"btn btn-sm btn-danger\"><i class=\"fa fa-trash-o\"></i></button>\n                                </td>\n                            </tr>\n                        @endforeach\n                    </table>\n                </div>\n            </div>\n        </div>\n    </div>\n\n    <div class=\"modal fade\" id=\"addEggsModal\" tabindex=\"-1\" role=\"dialog\">\n        <div class=\"modal-dialog\" role=\"document\">\n            <div class=\"modal-content\">\n                <form action=\"{{ route('admin.mounts.eggs', $mount->id) }}\" method=\"POST\">\n                    <div class=\"modal-header\">\n                        <button type=\"button\" class=\"close\" data-dismiss=\"modal\" aria-label=\"Close\">\n                            <span aria-hidden=\"true\" style=\"color: #FFFFFF\">&times;</span>\n                        </button>\n\n                        <h4 class=\"modal-title\">添加预设</h4>\n                    </div>\n\n                    <div class=\"modal-body\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-12\">\n                                <label for=\"pEggs\">预设</label>\n                                <select id=\"pEggs\" name=\"eggs[]\" class=\"form-control\" multiple>\n                                    @foreach ($nests as $nest)\n                                        <optgroup label=\"{{ $nest->name }}\">\n                                            @foreach ($nest->eggs as $egg)\n\n                                                @if (! in_array($egg->id, $mount->eggs->pluck('id')->toArray()))\n                                                    <option value=\"{{ $egg->id }}\">{{ $egg->name }}</option>\n                                                @endif\n\n                                            @endforeach\n                                        </optgroup>\n                                    @endforeach\n                                </select>\n                            </div>\n                        </div>\n                    </div>\n\n                    <div class=\"modal-footer\">\n                        {!! csrf_field() !!}\n\n                        <button type=\"button\" class=\"btn btn-default btn-sm pull-left\" data-dismiss=\"modal\">取消</button>\n                        <button type=\"submit\" class=\"btn btn-primary btn-sm\">添加</button>\n                    </div>\n                </form>\n            </div>\n        </div>\n    </div>\n\n    <div class=\"modal fade\" id=\"addNodesModal\" tabindex=\"-1\" role=\"dialog\">\n        <div class=\"modal-dialog\" role=\"document\">\n            <div class=\"modal-content\">\n                <form action=\"{{ route('admin.mounts.nodes', $mount->id) }}\" method=\"POST\">\n                    <div class=\"modal-header\">\n                        <button type=\"button\" class=\"close\" data-dismiss=\"modal\" aria-label=\"Close\">\n                            <span aria-hidden=\"true\" style=\"color: #FFFFFF\">&times;</span>\n                        </button>\n\n                        <h4 class=\"modal-title\">添加节点</h4>\n                    </div>\n\n                    <div class=\"modal-body\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-12\">\n                                <label for=\"pNodes\">节点</label>\n                                <select id=\"pNodes\" name=\"nodes[]\" class=\"form-control\" multiple>\n                                    @foreach ($locations as $location)\n                                        <optgroup label=\"{{ $location->long }} ({{ $location->short }})\">\n                                            @foreach ($location->nodes as $node)\n\n                                                @if (! in_array($node->id, $mount->nodes->pluck('id')->toArray()))\n                                                    <option value=\"{{ $node->id }}\">{{ $node->name }}</option>\n                                                @endif\n\n                                            @endforeach\n                                        </optgroup>\n                                    @endforeach\n                                </select>\n                            </div>\n                        </div>\n                    </div>\n\n                    <div class=\"modal-footer\">\n                        {!! csrf_field() !!}\n\n                        <button type=\"button\" class=\"btn btn-default btn-sm pull-left\" data-dismiss=\"modal\">取消</button>\n                        <button type=\"submit\" class=\"btn btn-primary btn-sm\">添加</button>\n                    </div>\n                </form>\n            </div>\n        </div>\n    </div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n\n    <script>\n        $(document).ready(function() {\n            $('#pEggs').select2({\n                placeholder: '选择预设..',\n            });\n\n            $('#pNodes').select2({\n                placeholder: '选择节点..',\n            });\n\n            $('button[data-action=\"detach-egg\"]').click(function (event) {\n                event.preventDefault();\n\n                const element = $(this);\n                const eggId = $(this).data('id');\n\n                $.ajax({\n                    method: 'DELETE',\n                    url: '/admin/mounts/' + {{ $mount->id }} + '/eggs/' + eggId,\n                    headers: { 'X-CSRF-TOKEN': $('meta[name=\"_token\"]').attr('content') },\n                }).done(function () {\n                    element.parent().parent().addClass('warning').delay(100).fadeOut();\n                    swal({ type: 'success', title: '预设已解除关联.' });\n                }).fail(function (jqXHR) {\n                    console.error(jqXHR);\n                    swal({\n                        title: '盖了帽了!',\n                        text: jqXHR.responseJSON.error,\n                        type: 'error'\n                    });\n                });\n            });\n\n            $('button[data-action=\"detach-node\"]').click(function (event) {\n                event.preventDefault();\n\n                const element = $(this);\n                const nodeId = $(this).data('id');\n\n                $.ajax({\n                    method: 'DELETE',\n                    url: '/admin/mounts/' + {{ $mount->id }} + '/nodes/' + nodeId,\n                    headers: { 'X-CSRF-TOKEN': $('meta[name=\"_token\"]').attr('content') },\n                }).done(function () {\n                    element.parent().parent().addClass('warning').delay(100).fadeOut();\n                    swal({ type: 'success', title: '节点已解除关联.' });\n                }).fail(function (jqXHR) {\n                    console.error(jqXHR);\n                    swal({\n                        title: '盖了帽了!',\n                        text: jqXHR.responseJSON.error,\n                        type: 'error'\n                    });\n                });\n            });\n        });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/nests/index.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    预设组\n@endsection\n\n@section('content-header')\n    <h1>预设组<small>于此系统上的所有预设组.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">预设组</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"alert alert-danger\">\n            预设是翼龙面板的一个强大功能，可实现极大的灵活性和配置。请注意，虽然功能强大，但错误地修改预设很容易使您的服务器宕机并导致更多问题。请避免编辑我们的默认预设 — 由 <code>support@pterodactyl.io</code> 提供 — 除非阁下十分明白该如何修改预设.\n        </div>\n    </div>\n</div>\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">已配置的预设组</h3>\n                <div class=\"box-tools\">\n                    <a href=\"#\" class=\"btn btn-sm btn-success\" data-toggle=\"modal\" data-target=\"#importServiceOptionModal\" role=\"button\"><i class=\"fa fa-upload\"></i> 导入预设</a>\n                    <a href=\"{{ route('admin.nests.new') }}\" class=\"btn btn-primary btn-sm\">新建</a>\n                </div>\n            </div>\n            <div class=\"box-body table-responsive no-padding\">\n                <table class=\"table table-hover\">\n                    <tr>\n                        <th>ID</th>\n                        <th>名称</th>\n                        <th>描述</th>\n                        <th class=\"text-center\">预设</th>\n                        <th class=\"text-center\">服务器</th>\n                    </tr>\n                    @foreach($nests as $nest)\n                        <tr>\n                            <td class=\"middle\"><code>{{ $nest->id }}</code></td>\n                            <td class=\"middle\"><a href=\"{{ route('admin.nests.view', $nest->id) }}\" data-toggle=\"tooltip\" data-placement=\"right\" title=\"{{ $nest->author }}\">{{ $nest->name }}</a></td>\n                            <td class=\"col-xs-6 middle\">{{ $nest->description }}</td>\n                            <td class=\"text-center middle\">{{ $nest->eggs_count }}</td>\n                            <td class=\"text-center middle\">{{ $nest->servers_count }}</td>\n                        </tr>\n                    @endforeach\n                </table>\n            </div>\n        </div>\n    </div>\n</div>\n<div class=\"modal fade\" tabindex=\"-1\" role=\"dialog\" id=\"importServiceOptionModal\">\n    <div class=\"modal-dialog\" role=\"document\">\n        <div class=\"modal-content\">\n            <div class=\"modal-header\">\n                <button type=\"button\" class=\"close\" data-dismiss=\"modal\" aria-label=\"Close\"><span aria-hidden=\"true\">&times;</span></button>\n                <h4 class=\"modal-title\">导入预设</h4>\n            </div>\n            <form action=\"{{ route('admin.nests.egg.import') }}\" enctype=\"multipart/form-data\" method=\"POST\">\n                <div class=\"modal-body\">\n                    <div class=\"form-group\">\n                        <label class=\"control-label\" for=\"pImportFile\">预设文件 <span class=\"field-required\"></span></label>\n                        <div>\n                            <input id=\"pImportFile\" type=\"file\" name=\"import_file\" class=\"form-control\" accept=\"application/json\" />\n                            <p class=\"small text-muted\">选择 <code>.json</code> 文件以导入你想要的预设.</p>\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"control-label\" for=\"pImportToNest\">关联的预设组 <span class=\"field-required\"></span></label>\n                        <div>\n                            <select id=\"pImportToNest\" name=\"import_to_nest\">\n                                @foreach($nests as $nest)\n                                   <option value=\"{{ $nest->id }}\">{{ $nest->name }} &lt;{{ $nest->author }}&gt;</option>\n                                @endforeach\n                            </select>\n                            <p class=\"small text-muted\">从下拉列表中选择与此预设关联的预设组。如果您希望将其与新预设组相关联，则需要在继续之前创建该预设组.</p>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"modal-footer\">\n                    {{ csrf_field() }}\n                    <button type=\"button\" class=\"btn btn-default\" data-dismiss=\"modal\">取消</button>\n                    <button type=\"submit\" class=\"btn btn-primary\">导入</button>\n                </div>\n            </form>\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n        $(document).ready(function() {\n            $('#pImportToNest').select2();\n        });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/nests/new.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    新预设组\n@endsection\n\n@section('content-header')\n    <h1>新预设组<small>配置一个新的预设部署到所有节点.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nests') }}\">预设组</a></li>\n        <li class=\"active\">新建</li>\n    </ol>\n@endsection\n\n@section('content')\n<form action=\"{{ route('admin.nests.new') }}\" method=\"POST\">\n    <div class=\"row\">\n        <div class=\"col-md-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">新建预设组</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label class=\"control-label\">名称</label>\n                        <div>\n                            <input type=\"text\" name=\"name\" class=\"form-control\" value=\"{{ old('name') }}\" />\n                            <p class=\"text-muted\"><small>预设组的名称.</small></p>\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"control-label\">描述</label>\n                        <div>\n                            <textarea name=\"description\" class=\"form-control\" rows=\"6\">{{ old('description') }}</textarea>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <button type=\"submit\" class=\"btn btn-primary pull-right\">保存</button>\n                </div>\n            </div>\n        </div>\n    </div>\n</form>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/nests/view.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    预设组 &rarr; {{ $nest->name }}\n@endsection\n\n@section('content-header')\n    <h1>{{ $nest->name }}<small>{{ str_limit($nest->description, 50) }}</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nests') }}\">预设组</a></li>\n        <li class=\"active\">{{ $nest->name }}</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <form action=\"{{ route('admin.nests.view', $nest->id) }}\" method=\"POST\">\n        <div class=\"col-md-6\">\n            <div class=\"box\">\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label class=\"control-label\">名称 <span class=\"field-required\"></span></label>\n                        <div>\n                            <input type=\"text\" name=\"name\" class=\"form-control\" value=\"{{ $nest->name }}\" />\n                            <p class=\"text-muted\"><small>预设组的名称.</small></p>\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"control-label\">描述</label>\n                        <div>\n                            <textarea name=\"description\" class=\"form-control\" rows=\"7\">{{ $nest->description }}</textarea>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <button type=\"submit\" name=\"_method\" value=\"PATCH\" class=\"btn btn-primary btn-sm pull-right\">保存</button>\n                    <button id=\"deleteButton\" type=\"submit\" name=\"_method\" value=\"DELETE\" class=\"btn btn-sm btn-danger muted muted-hover\"><i class=\"fa fa-trash-o\"></i></button>\n                </div>\n            </div>\n        </div>\n    </form>\n    <div class=\"col-md-6\">\n        <div class=\"box\">\n            <div class=\"box-body\">\n                <div class=\"form-group\">\n                    <label class=\"control-label\">预设组 ID</label>\n                    <div>\n                        <input type=\"text\" readonly class=\"form-control\" value=\"{{ $nest->id }}\" />\n                        <p class=\"text-muted small\">用于在内部和通过 API 识别此预设的唯一 ID.</p>\n                    </div>\n                </div>\n                <div class=\"form-group\">\n                    <label class=\"control-label\">作者</label>\n                    <div>\n                        <input type=\"text\" readonly class=\"form-control\" value=\"{{ $nest->author }}\" />\n                        <p class=\"text-muted small\">此预设配置的作者。有问题联系他的邮箱，除非这是由 <code>support@pterodactyl.io</code>提供的预设。</p>\n                    </div>\n                </div>\n                <div class=\"form-group\">\n                    <label class=\"control-label\">UUID</label>\n                    <div>\n                        <input type=\"text\" readonly class=\"form-control\" value=\"{{ $nest->uuid }}\" />\n                        <p class=\"text-muted small\">为所有使用此预设的服务器分配的 UUID 用于识别目的.</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n</div>\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">新预设</h3>\n            </div>\n            <div class=\"box-body table-responsive no-padding\">\n                <table class=\"table table-hover\">\n                    <tr>\n                        <th>ID</th>\n                        <th>名称</th>\n                        <th>描述</th>\n                        <th class=\"text-center\">服务器</th>\n                        <th class=\"text-center\"></th>\n                    </tr>\n                    @foreach($nest->eggs as $egg)\n                        <tr>\n                            <td class=\"align-middle\"><code>{{ $egg->id }}</code></td>\n                            <td class=\"align-middle\"><a href=\"{{ route('admin.nests.egg.view', $egg->id) }}\" data-toggle=\"tooltip\" data-placement=\"right\" title=\"{{ $egg->author }}\">{{ $egg->name }}</a></td>\n                            <td class=\"col-xs-8 align-middle\">{{ $egg->description }}</td>\n                            <td class=\"text-center align-middle\"><code>{{ $egg->servers->count() }}</code></td>\n                            <td class=\"align-middle\">\n                                <a href=\"{{ route('admin.nests.egg.export', ['egg' => $egg->id]) }}\"><i class=\"fa fa-download\"></i></a>\n                            </td>\n                        </tr>\n                    @endforeach\n                </table>\n            </div>\n            <div class=\"box-footer\">\n                <a href=\"{{ route('admin.nests.egg.new') }}\"><button class=\"btn btn-success btn-sm pull-right\">新预设</button></a>\n            </div>\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n        $('#deleteButton').on('mouseenter', function (event) {\n            $(this).find('i').html(' 删除预设组');\n        }).on('mouseleave', function (event) {\n            $(this).find('i').html('');\n        });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/nodes/index.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    节点列表\n@endsection\n\n@section('scripts')\n    @parent\n    {!! Theme::css('vendor/fontawesome/animation.min.css') !!}\n@endsection\n\n@section('content-header')\n    <h1>节点<small>连接到面板服务器的所有节点.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">节点</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">节点列表</h3>\n                <div class=\"box-tools search01\">\n                    <form action=\"{{ route('admin.nodes') }}\" method=\"GET\">\n                        <div class=\"input-group input-group-sm\">\n                            <input type=\"text\" name=\"filter[name]\" class=\"form-control pull-right\" value=\"{{ request()->input('filter.name') }}\" placeholder=\"搜索节点\">\n                            <div class=\"input-group-btn\">\n                                <button type=\"submit\" class=\"btn btn-default\"><i class=\"fa fa-search\"></i></button>\n                                <a href=\"{{ route('admin.nodes.new') }}\"><button type=\"button\" class=\"btn btn-sm btn-primary\" style=\"border-radius: 0 3px 3px 0;margin-left:-1px;\">新建</button></a>\n                            </div>\n                        </div>\n                    </form>\n                </div>\n            </div>\n            <div class=\"box-body table-responsive no-padding\">\n                <table class=\"table table-hover\">\n                    <tbody>\n                        <tr>\n                            <th></th>\n                            <th>名称</th>\n                            <th>地域</th>\n                            <th>内存容量</th>\n                            <th>存储容量</th>\n                            <th class=\"text-center\">服务器</th>\n                            <th class=\"text-center\">SSL</th>\n                            <th class=\"text-center\">公开</th>\n                        </tr>\n                        @foreach ($nodes as $node)\n                            <tr>\n                                <td class=\"text-center text-muted left-icon\" data-action=\"ping\" data-secret=\"{{ $node->getDecryptedKey() }}\" data-location=\"{{ $node->scheme }}://{{ $node->fqdn }}:{{ $node->daemonListen }}/api/system\"><i class=\"fa fa-fw fa-refresh fa-spin\"></i></td>\n                                <td>{!! $node->maintenance_mode ? '<span class=\"label label-warning\"><i class=\"fa fa-wrench\"></i></span> ' : '' !!}<a href=\"{{ route('admin.nodes.view', $node->id) }}\">{{ $node->name }}</a></td>\n                                <td>{{ $node->location->short }}</td>\n                                <td>{{ $node->memory }} MiB</td>\n                                <td>{{ $node->disk }} MiB</td>\n                                <td class=\"text-center\">{{ $node->servers_count }}</td>\n                                <td class=\"text-center\" style=\"color:{{ ($node->scheme === 'https') ? '#50af51' : '#d9534f' }}\"><i class=\"fa fa-{{ ($node->scheme === 'https') ? 'lock' : 'unlock' }}\"></i></td>\n                                <td class=\"text-center\"><i class=\"fa fa-{{ ($node->public) ? 'eye' : 'eye-slash' }}\"></i></td>\n                            </tr>\n                        @endforeach\n                    </tbody>\n                </table>\n            </div>\n            @if($nodes->hasPages())\n                <div class=\"box-footer with-border\">\n                    <div class=\"col-md-12 text-center\">{!! $nodes->appends(['query' => Request::input('query')])->render() !!}</div>\n                </div>\n            @endif\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    (function pingNodes() {\n        $('td[data-action=\"ping\"]').each(function(i, element) {\n            $.ajax({\n                type: 'GET',\n                url: $(element).data('location'),\n                headers: {\n                    'Authorization': 'Bearer ' + $(element).data('secret'),\n                },\n                timeout: 5000\n            }).done(function (data) {\n                $(element).find('i').tooltip({\n                    title: 'v' + data.version,\n                });\n                $(element).removeClass('text-muted').find('i').removeClass().addClass('fa fa-fw fa-heartbeat faa-pulse animated').css('color', '#50af51');\n            }).fail(function (error) {\n                var errorText = '无法连接至节点! 查看浏览器开发控制台以了解更多.';\n                try {\n                    errorText = error.responseJSON.errors[0].detail || errorText;\n                } catch (ex) {}\n\n                $(element).removeClass('text-muted').find('i').removeClass().addClass('fa fa-fw fa-heart-o').css('color', '#d9534f');\n                $(element).find('i').tooltip({ title: errorText });\n            });\n        }).promise().done(function () {\n            setTimeout(pingNodes, 10000);\n        });\n    })();\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/nodes/new.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    节点 &rarr; 新建\n@endsection\n\n@section('content-header')\n    <h1>新节点<small>在本地或远程主机创建面板使用的新节点.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nodes') }}\">节点</a></li>\n        <li class=\"active\">新建</li>\n    </ol>\n@endsection\n\n@section('content')\n<form action=\"{{ route('admin.nodes.new') }}\" method=\"POST\">\n    <div class=\"row\">\n        <div class=\"col-sm-6\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">基础信息</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"pName\" class=\"form-label\">名称</label>\n                        <input type=\"text\" name=\"name\" id=\"pName\" class=\"form-control\" value=\"{{ old('name') }}\"/>\n                        <p class=\"text-muted small\">字符限制: <code>a-zA-Z0-9_.-</code> 与 <code>[空格]</code> (最少 1, 最多 100 字符).</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pDescription\" class=\"form-label\">描述</label>\n                        <textarea name=\"description\" id=\"pDescription\" rows=\"4\" class=\"form-control\">{{ old('description') }}</textarea>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pLocationId\" class=\"form-label\">地域</label>\n                        <select name=\"location_id\" id=\"pLocationId\">\n                            @foreach($locations as $location)\n                                <option value=\"{{ $location->id }}\" {{ $location->id != old('location_id') ?: 'selected' }}>{{ $location->short }}</option>\n                            @endforeach\n                        </select>\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"form-label\">节点可见性</label>\n                        <div>\n                            <div class=\"radio radio-success radio-inline\">\n\n                                <input type=\"radio\" id=\"pPublicTrue\" value=\"1\" name=\"public\" checked>\n                                <label for=\"pPublicTrue\"> 公开 </label>\n                            </div>\n                            <div class=\"radio radio-danger radio-inline\">\n                                <input type=\"radio\" id=\"pPublicFalse\" value=\"0\" name=\"public\">\n                                <label for=\"pPublicFalse\"> 私人 </label>\n                            </div>\n                        </div>\n                        <p class=\"text-muted small\">将节点设为 <code>私人</code> 将无法使用节点自动部署的功能.\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pFQDN\" class=\"form-label\">域名</label>\n                        <input type=\"text\" name=\"fqdn\" id=\"pFQDN\" class=\"form-control\" value=\"{{ old('fqdn') }}\"/>\n                        <p class=\"text-muted small\">请输入用于连接守护程序的域名 (例如 <code>node.example.com</code>)。<em>仅在</em> 您没有为此节点使用 SSL 连接的情况下才可以使用 IP 地址。</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"form-label\">与面板前端以 SSL 通信</label>\n                        <div>\n                            <div class=\"radio radio-success radio-inline\">\n                                <input type=\"radio\" id=\"pSSLTrue\" value=\"https\" name=\"scheme\" checked>\n                                <label for=\"pSSLTrue\"> 使用 SSL 通信</label>\n                            </div>\n                            <div class=\"radio radio-danger radio-inline\">\n                                <input type=\"radio\" id=\"pSSLFalse\" value=\"http\" name=\"scheme\" @if(request()->isSecure()) disabled @endif>\n                                <label for=\"pSSLFalse\"> 使用 HTTP 通信 (无 SSL)</label>\n                            </div>\n                        </div>\n                        @if(request()->isSecure())\n                            <p class=\"text-danger small\">您的面板当前配置为使用 SSL 安全连接。为了让浏览器连接到您的节点，其 <strong>必须</strong> 使用 SSL 连接.</p>\n                        @else\n                            <p class=\"text-muted small\">在大多数情况下，您应该选择使用 SSL 连接。如果使用 IP 地址或者您根本不想使用 SSL，请选择 HTTP 连接。( 不安全 )</p>\n                        @endif\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"form-label\">通过代理</label>\n                        <div>\n                            <div class=\"radio radio-success radio-inline\">\n                                <input type=\"radio\" id=\"pProxyFalse\" value=\"0\" name=\"behind_proxy\" checked>\n                                <label for=\"pProxyFalse\"> 不通过代理 </label>\n                            </div>\n                            <div class=\"radio radio-info radio-inline\">\n                                <input type=\"radio\" id=\"pProxyTrue\" value=\"1\" name=\"behind_proxy\">\n                                <label for=\"pProxyTrue\"> 通过代理 </label>\n                            </div>\n                        </div>\n                        <p class=\"text-muted small\">如果您在 Cloudflare 等代理CDN运行守护程序，请选择此选项以使守护程序在启动时跳过查找证书。</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-sm-6\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">设置</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"row\">\n                        <div class=\"form-group col-md-6\">\n                            <label for=\"pDaemonBase\" class=\"form-label\">守护程序服务器文件目录</label>\n                            <input type=\"text\" name=\"daemonBase\" id=\"pDaemonBase\" class=\"form-control\" value=\"/var/lib/pterodactyl/volumes\" />\n                            <p class=\"text-muted small\">输入存储服务器使用的文件目录. <strong>如果您使用 OVH，您应该检查您的分区方案。你可能需要让 <code>/home/daemon-data</code> 有足够的空间.</strong></p>\n                        </div>\n                        <div class=\"form-group col-md-6\">\n                            <label for=\"pMemory\" class=\"form-label\">总内存容量</label>\n                            <div class=\"input-group\">\n                                <input type=\"text\" name=\"memory\" data-multiplicator=\"true\" class=\"form-control\" id=\"pMemory\" value=\"{{ old('memory') }}\"/>\n                                <span class=\"input-group-addon\">MiB</span>\n                            </div>\n                        </div>\n                        <div class=\"form-group col-md-6\">\n                            <label for=\"pMemoryOverallocate\" class=\"form-label\">内存过额分配</label>\n                            <div class=\"input-group\">\n                                <input type=\"text\" name=\"memory_overallocate\" class=\"form-control\" id=\"pMemoryOverallocate\" value=\"{{ old('memory_overallocate') }}\"/>\n                                <span class=\"input-group-addon\">%</span>\n                            </div>\n                        </div>\n                        <div class=\"col-md-12\">\n                            <p class=\"text-muted small\">输入可用于新服务器的内存总量。如果您希望允许过度分配内存，请输入您希望允许的百分比。要禁用检查过度分配，请输入 <code>-1</code> 于此处. 如果输入 <code>0</code> 这将在可能超出节点的最大内存总量时阻止创建新服务器.</p>\n                        </div>\n                    </div>\n                    <div class=\"row\">\n                        <div class=\"form-group col-md-6\">\n                            <label for=\"pDisk\" class=\"form-label\">总存储容量</label>\n                            <div class=\"input-group\">\n                                <input type=\"text\" name=\"disk\" data-multiplicator=\"true\" class=\"form-control\" id=\"pDisk\" value=\"{{ old('disk') }}\"/>\n                                <span class=\"input-group-addon\">MiB</span>\n                            </div>\n                        </div>\n                        <div class=\"form-group col-md-6\">\n                            <label for=\"pDiskOverallocate\" class=\"form-label\">存储空间过额分配</label>\n                            <div class=\"input-group\">\n                                <input type=\"text\" name=\"disk_overallocate\" class=\"form-control\" id=\"pDiskOverallocate\" value=\"{{ old('disk_overallocate') }}\"/>\n                                <span class=\"input-group-addon\">%</span>\n                            </div>\n                        </div>\n                        <div class=\"col-md-12\">\n                            <p class=\"text-muted small\">输入可用于新服务器的存储空间总量。如果您希望允许过度分配存储空间，请输入您希望允许的百分比。要禁用检查过度分配，请输入 <code>-1</code> 于此处. 如果输入 <code>0</code> 这将在可能超出节点的最大存储空间总量时阻止创建新服务器.(请注意,备份文件并不计入)</p>\n                        </div>\n                    </div>\n                    <div class=\"row\">\n                        <div class=\"form-group col-md-6\">\n                            <label for=\"pDaemonListen\" class=\"form-label\">守护进程端口</label>\n                            <input type=\"text\" name=\"daemonListen\" class=\"form-control\" id=\"pDaemonListen\" value=\"8080\" />\n                        </div>\n                        <div class=\"form-group col-md-6\">\n                            <label for=\"pDaemonSFTP\" class=\"form-label\">守护进程 SFTP 端口</label>\n                            <input type=\"text\" name=\"daemonSFTP\" class=\"form-control\" id=\"pDaemonSFTP\" value=\"2022\" />\n                        </div>\n                        <div class=\"col-md-12\">\n                            <p class=\"text-muted small\">守护进程运行自己的 SFTP 管理容器，并且不使用主物理服务器上的 SSHd 进程。<Strong>不要使用为物理服务器的 SSH 进程分配的相同端口。</strong> 如果您将在 CloudFlare 后面运行守护程序&reg; 您应该将守护程序端口设置为 <code>8443</code> 允许通过 SSL 进行 websocket 代理.</p>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <button type=\"submit\" class=\"btn btn-success pull-right\">创建节点</button>\n                </div>\n            </div>\n        </div>\n    </div>\n</form>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n        $('#pLocationId').select2();\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/nodes/view/allocation.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    {{ $node->name }}: 分配\n@endsection\n\n@section('content-header')\n    <h1>{{ $node->name }}<small>控制此节点上的服务器可用的分配.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nodes') }}\">节点</a></li>\n        <li><a href=\"{{ route('admin.nodes.view', $node->id) }}\">{{ $node->name }}</a></li>\n        <li class=\"active\">分配</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"nav-tabs-custom nav-tabs-floating\">\n            <ul class=\"nav nav-tabs\">\n                <li><a href=\"{{ route('admin.nodes.view', $node->id) }}\">关于</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.settings', $node->id) }}\">设置</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.configuration', $node->id) }}\">配置</a></li>\n                <li class=\"active\"><a href=\"{{ route('admin.nodes.view.allocation', $node->id) }}\">分配</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.servers', $node->id) }}\">服务器</a></li>\n            </ul>\n        </div>\n    </div>\n</div>\n<div class=\"row\">\n    <div class=\"col-sm-8\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">已使用的分配</h3>\n            </div>\n            <div class=\"box-body table-responsive no-padding\" style=\"overflow-x: visible\">\n                <table class=\"table table-hover\" style=\"margin-bottom:0;\">\n                    <tr>\n                        <th>\n                            <input type=\"checkbox\" class=\"select-all-files hidden-xs\" data-action=\"selectAll\">\n                        </th>\n                        <th>IP 地址 <i class=\"fa fa-fw fa-minus-square\" style=\"font-weight:normal;color:#d9534f;cursor:pointer;\" data-toggle=\"modal\" data-target=\"#allocationModal\"></i></th>\n                        <th>域名</th>\n                        <th>端口</th>\n                        <th>分配给</th>\n                        <th>\n                            <div class=\"btn-group hidden-xs\">\n                                <button type=\"button\" id=\"mass_actions\" class=\"btn btn-sm btn-default dropdown-toggle disabled\"\n                                        data-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\">批量操作 <span class=\"caret\"></span>\n                                </button>\n                                <ul class=\"dropdown-menu dropdown-massactions\">\n                                    <li><a href=\"#\" id=\"selective-deletion\" data-action=\"selective-deletion\">删除 <i class=\"fa fa-fw fa-trash-o\"></i></a></li>\n                                </ul>\n                            </div>\n                        </th>\n                    </tr>\n                    @foreach($node->allocations as $allocation)\n                        <tr>\n                            <td class=\"middle min-size\" data-identifier=\"type\">\n                                @if(is_null($allocation->server_id))\n                                <input type=\"checkbox\" class=\"select-file hidden-xs\" data-action=\"addSelection\">\n                                @else\n                                <input disabled=\"disabled\" type=\"checkbox\" class=\"select-file hidden-xs\" data-action=\"addSelection\">\n                                @endif\n                            </td>\n                            <td class=\"col-sm-3 middle\" data-identifier=\"ip\">{{ $allocation->ip }}</td>\n                            <td class=\"col-sm-3 middle\">\n                                <input class=\"form-control input-sm\" type=\"text\" value=\"{{ $allocation->ip_alias }}\" data-action=\"set-alias\" data-id=\"{{ $allocation->id }}\" placeholder=\"无\" />\n                                <span class=\"input-loader\"><i class=\"fa fa-refresh fa-spin fa-fw\"></i></span>\n                            </td>\n                            <td class=\"col-sm-2 middle\" data-identifier=\"port\">{{ $allocation->port }}</td>\n                            <td class=\"col-sm-3 middle\">\n                                @if(! is_null($allocation->server))\n                                    <a href=\"{{ route('admin.servers.view', $allocation->server_id) }}\">{{ $allocation->server->name }}</a>\n                                @endif\n                            </td>\n                            <td class=\"col-sm-1 middle\">\n                                @if(is_null($allocation->server_id))\n                                    <button data-action=\"deallocate\" data-id=\"{{ $allocation->id }}\" class=\"btn btn-sm btn-danger\"><i class=\"fa fa-trash-o\"></i></button>\n                                @endif\n                            </td>\n                        </tr>\n                    @endforeach\n                </table>\n            </div>\n            @if($node->allocations->hasPages())\n                <div class=\"box-footer text-center\">\n                    {{ $node->allocations->render() }}\n                </div>\n            @endif\n        </div>\n    </div>\n    <div class=\"col-sm-4\">\n        <form action=\"{{ route('admin.nodes.view.allocation', $node->id) }}\" method=\"POST\">\n            <div class=\"box box-success\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">创建新分配</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"pAllocationIP\" class=\"control-label\">IP 地址</label>\n                        <div>\n                            <select class=\"form-control\" name=\"allocation_ip\" id=\"pAllocationIP\" multiple>\n                                @foreach($allocations as $allocation)\n                                    <option value=\"{{ $allocation->ip }}\">{{ $allocation->ip }}</option>\n                                @endforeach\n                            </select>\n                            <p class=\"text-muted small\">在此处输入要分配端口的 IP 地址.</p>\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pAllocationIP\" class=\"control-label\">域名</label>\n                        <div>\n                            <input type=\"text\" id=\"pAllocationAlias\" class=\"form-control\" name=\"allocation_alias\" placeholder=\"别名\" />\n                            <p class=\"text-muted small\">如果您想为这些分配分配一个默认域名，请在此处输入.</p>\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pAllocationPorts\" class=\"control-label\">端口</label>\n                        <div>\n                            <select class=\"form-control\" name=\"allocation_ports[]\" id=\"pAllocationPorts\" multiple></select>\n                            <p class=\"text-muted small\">在此处输入单个端口或端口范围，以逗号或空格分隔.</p>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <button type=\"submit\" class=\"btn btn-success btn-sm pull-right\">提交</button>\n                </div>\n            </div>\n        </form>\n    </div>\n</div>\n<div class=\"modal fade\" id=\"allocationModal\" tabindex=\"-1\" role=\"dialog\">\n    <div class=\"modal-dialog\" role=\"document\">\n        <div class=\"modal-content\">\n            <div class=\"modal-header\">\n                <button type=\"button\" class=\"close\" data-dismiss=\"modal\" aria-label=\"Close\"><span aria-hidden=\"true\">&times;</span></button>\n                <h4 class=\"modal-title\">删除 IP 区块分配</h4>\n            </div>\n            <form action=\"{{ route('admin.nodes.view.allocation.removeBlock', $node->id) }}\" method=\"POST\">\n                <div class=\"modal-body\">\n                    <div class=\"row\">\n                        <div class=\"col-md-12\">\n                            <select class=\"form-control\" name=\"ip\">\n                                @foreach($allocations as $allocation)\n                                    <option value=\"{{ $allocation->ip }}\">{{ $allocation->ip }}</option>\n                                @endforeach\n                            </select>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"modal-footer\">\n                    {{{ csrf_field() }}}\n                    <button type=\"button\" class=\"btn btn-default\" data-dismiss=\"modal\">关闭</button>\n                    <button type=\"submit\" class=\"btn btn-danger\">删除分配</button>\n                </div>\n            </form>\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    $('[data-action=\"addSelection\"]').on('click', function () {\n        updateMassActions();\n    });\n\n    $('[data-action=\"selectAll\"]').on('click', function () {\n        $('input.select-file').not(':disabled').prop('checked', function (i, val) {\n            return !val;\n        });\n\n        updateMassActions();\n    });\n\n    $('[data-action=\"selective-deletion\"]').on('mousedown', function () {\n        deleteSelected();\n    });\n\n    $('#pAllocationIP').select2({\n        tags: true,\n        maximumSelectionLength: 1,\n        selectOnClose: true,\n        tokenSeparators: [',', ' '],\n    });\n\n    $('#pAllocationPorts').select2({\n        tags: true,\n        selectOnClose: true,\n        tokenSeparators: [',', ' '],\n    });\n\n    $('button[data-action=\"deallocate\"]').click(function (event) {\n        event.preventDefault();\n        var element = $(this);\n        var allocation = $(this).data('id');\n        swal({\n            title: '',\n            text: '你确定删除此分配?',\n            type: 'warning',\n            showCancelButton: true,\n            allowOutsideClick: true,\n            closeOnConfirm: false,\n            confirmButtonText: '确定',\n            confirmButtonColor: '#d9534f',\n            showLoaderOnConfirm: true\n        }, function () {\n            $.ajax({\n                method: 'DELETE',\n                url: '/admin/nodes/view/' + {{ $node->id }} + '/allocation/remove/' + allocation,\n                headers: { 'X-CSRF-TOKEN': $('meta[name=\"_token\"]').attr('content') },\n            }).done(function (data) {\n                element.parent().parent().addClass('warning').delay(100).fadeOut();\n                swal({ type: 'success', title: '端口已删除!' });\n            }).fail(function (jqXHR) {\n                console.error(jqXHR);\n                swal({\n                    title: '呜呼!',\n                    text: jqXHR.responseJSON.error,\n                    type: 'error'\n                });\n            });\n        });\n    });\n\n    var typingTimer;\n    $('input[data-action=\"set-alias\"]').keyup(function () {\n        clearTimeout(typingTimer);\n        $(this).parent().removeClass('has-error has-success');\n        typingTimer = setTimeout(sendAlias, 250, $(this));\n    });\n\n    var fadeTimers = [];\n    function sendAlias(element) {\n        element.parent().find('.input-loader').show();\n        clearTimeout(fadeTimers[element.data('id')]);\n        $.ajax({\n            method: 'POST',\n            url: '/admin/nodes/view/' + {{ $node->id }} + '/allocation/alias',\n            headers: { 'X-CSRF-TOKEN': $('meta[name=\"_token\"]').attr('content') },\n            data: {\n                alias: element.val(),\n                allocation_id: element.data('id'),\n            }\n        }).done(function () {\n            element.parent().addClass('has-success');\n        }).fail(function (jqXHR) {\n            console.error(jqXHR);\n            element.parent().addClass('has-error');\n        }).always(function () {\n            element.parent().find('.input-loader').hide();\n            fadeTimers[element.data('id')] = setTimeout(clearHighlight, 2500, element);\n        });\n    }\n\n    function clearHighlight(element) {\n        element.parent().removeClass('has-error has-success');\n    }\n\n    function updateMassActions() {\n        if ($('input.select-file:checked').length > 0) {\n            $('#mass_actions').removeClass('disabled');\n        } else {\n            $('#mass_actions').addClass('disabled');\n        }\n    }\n\n    function deleteSelected() {\n        var selectedIds = [];\n        var selectedItems = [];\n        var selectedItemsElements = [];\n\n        $('input.select-file:checked').each(function () {\n            var $parent = $($(this).closest('tr'));\n            var id = $parent.find('[data-action=\"deallocate\"]').data('id');\n            var $ip = $parent.find('td[data-identifier=\"ip\"]');\n            var $port = $parent.find('td[data-identifier=\"port\"]');\n            var block = `${$ip.text()}:${$port.text()}`;\n\n            selectedIds.push({\n                id: id\n            });\n            selectedItems.push(block);\n            selectedItemsElements.push($parent);\n        });\n\n        if (selectedItems.length !== 0) {\n            var formattedItems = \"\";\n            var i = 0;\n            $.each(selectedItems, function (key, value) {\n                formattedItems += (\"<code>\" + value + \"</code>, \");\n                i++;\n                return i < 5;\n            });\n\n            formattedItems = formattedItems.slice(0, -2);\n            if (selectedItems.length > 5) {\n                formattedItems += ', 和另外 ' + (selectedItems.length - 5) + ' 个';\n            }\n\n            swal({\n                type: 'warning',\n                title: '',\n                text: '您确定要删除这些分配吗？' + formattedItems + '.',\n                html: true,\n                showCancelButton: true,\n                showConfirmButton: true,\n                closeOnConfirm: false,\n                showLoaderOnConfirm: true\n            }, function () {\n                $.ajax({\n                    method: 'DELETE',\n                    url: '/admin/nodes/view/' + {{ $node->id }} + '/allocations',\n                    headers: {'X-CSRF-TOKEN': $('meta[name=\"_token\"]').attr('content')},\n                    data: JSON.stringify({\n                        allocations: selectedIds\n                    }),\n                    contentType: 'application/json',\n                    processData: false\n                }).done(function () {\n                    $('#file_listing input:checked').each(function () {\n                        $(this).prop('checked', false);\n                    });\n\n                    $.each(selectedItemsElements, function () {\n                        $(this).addClass('warning').delay(200).fadeOut();\n                    });\n\n                    swal({\n                        type: 'success',\n                        title: '端口已删除'\n                    });\n                }).fail(function (jqXHR) {\n                    console.error(jqXHR);\n                    swal({\n                        type: 'error',\n                        title: '呜呼!',\n                        html: true,\n                        text: '尝试删除这些分配时发生错误，请再试一次。',\n                    });\n                });\n            });\n        } else {\n            swal({\n                type: 'warning',\n                title: '',\n                text: '请选择要删除的分配。',\n            });\n        }\n    }\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/nodes/view/configuration.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    {{ $node->name }}: 配置\n@endsection\n\n@section('content-header')\n    <h1>{{ $node->name }}<small>守护进程配置文件.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nodes') }}\">节点</a></li>\n        <li><a href=\"{{ route('admin.nodes.view', $node->id) }}\">{{ $node->name }}</a></li>\n        <li class=\"active\">配置</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"nav-tabs-custom nav-tabs-floating\">\n            <ul class=\"nav nav-tabs\">\n                <li><a href=\"{{ route('admin.nodes.view', $node->id) }}\">关于</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.settings', $node->id) }}\">设置</a></li>\n                <li class=\"active\"><a href=\"{{ route('admin.nodes.view.configuration', $node->id) }}\">配置</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.allocation', $node->id) }}\">分配</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.servers', $node->id) }}\">服务器</a></li>\n            </ul>\n        </div>\n    </div>\n</div>\n<div class=\"row\">\n    <div class=\"col-sm-8\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">配置文件</h3>\n            </div>\n            <div class=\"box-body\">\n                <pre class=\"no-margin\">{{ $node->getYamlConfiguration() }}</pre>\n            </div>\n            <div class=\"box-footer\">\n                <p class=\"no-margin\">这个文件应该放在你的守护进程的根目录中 (一般是 <code>/etc/pterodactyl</code>) 中的 <code>config.yml</code>.</p>\n            </div>\n        </div>\n    </div>\n    <div class=\"col-sm-4\">\n        <div class=\"box box-success\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">自动部署</h3>\n            </div>\n            <div class=\"box-body\">\n                <p class=\"text-muted small\">\n                    使用下方按钮生成自定义部署命令，可用于自动配置 Wings 守护进程。\n                </p>\n            </div>\n            <div class=\"box-footer\">\n                <button type=\"button\" id=\"configTokenBtn\" class=\"btn btn-sm btn-default\" style=\"width:100%;\">生成自动部署指令</button>\n            </div>\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    $('#configTokenBtn').on('click', function (event) {\n        $.ajax({\n            method: 'POST',\n            url: '{{ route('admin.nodes.view.configuration.token', $node->id) }}',\n            headers: { 'X-CSRF-TOKEN': '{{ csrf_token() }}' },\n        }).done(function (data) {\n            swal({\n                type: 'success',\n                title: '指令已生成.',\n                text: '<p>要自动配置节点，请运行以下命令:<br /><small><pre>cd /etc/pterodactyl && sudo wings configure --panel-url {{ config('app.url') }} --token ' + data.token + ' --node ' + data.node + '{{ config('app.debug') ? ' --allow-insecure' : '' }}</pre></small></p>',\n                html: true\n            })\n        }).fail(function () {\n            swal({\n                title: '错误',\n                text: '生成自动部署指令时发生错误，无法继续此操作.',\n                type: 'error'\n            });\n        });\n    });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/nodes/view/index.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    {{ $node->name }}\n@endsection\n\n@section('content-header')\n    <h1>{{ $node->name }}<small>快速概览您的节点。</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nodes') }}\">节点</a></li>\n        <li class=\"active\">{{ $node->name }}</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"nav-tabs-custom nav-tabs-floating\">\n            <ul class=\"nav nav-tabs\">\n                <li class=\"active\"><a href=\"{{ route('admin.nodes.view', $node->id) }}\">关于</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.settings', $node->id) }}\">设置</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.configuration', $node->id) }}\">配置</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.allocation', $node->id) }}\">分配</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.servers', $node->id) }}\">服务器</a></li>\n            </ul>\n        </div>\n    </div>\n</div>\n<div class=\"row\">\n    <div class=\"col-sm-8\">\n        <div class=\"row\">\n            <div class=\"col-xs-12\">\n                <div class=\"box box-primary\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">信息</h3>\n                    </div>\n                    <div class=\"box-body table-responsive no-padding\">\n                        <table class=\"table table-hover\">\n                            <tr>\n                                <td>守护进程版本</td>\n                                <td><code data-attr=\"info-version\"><i class=\"fa fa-refresh fa-fw fa-spin\"></i></code> (最新版本: <code>{{ $version->getDaemon() }}</code>)</td>\n                            </tr>\n                            <tr>\n                                <td>系统版本</td>\n                                <td data-attr=\"info-system\"><i class=\"fa fa-refresh fa-fw fa-spin\"></i></td>\n                            </tr>\n                            <tr>\n                                <td>总 CPU 线程</td>\n                                <td data-attr=\"info-cpus\"><i class=\"fa fa-refresh fa-fw fa-spin\"></i></td>\n                            </tr>\n                        </table>\n                    </div>\n                </div>\n            </div>\n            @if ($node->description)\n                <div class=\"col-xs-12\">\n                    <div class=\"box box-default\">\n                        <div class=\"box-header with-border\">\n                            描述\n                        </div>\n                        <div class=\"box-body table-responsive\">\n                            <pre>{{ $node->description }}</pre>\n                        </div>\n                    </div>\n                </div>\n            @endif\n            <div class=\"col-xs-12\">\n                <div class=\"box box-danger\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">删除节点</h3>\n                    </div>\n                    <div class=\"box-body\">\n                        <p class=\"no-margin\">删除节点是不可逆的操作，会立即从面板中删除该节点。必须没有与此节点关联的服务器才能进行删除操作。</p>\n                    </div>\n                    <div class=\"box-footer\">\n                        <form action=\"{{ route('admin.nodes.view.delete', $node->id) }}\" method=\"POST\">\n                            {!! csrf_field() !!}\n                            {!! method_field('DELETE') !!}\n                            <button type=\"submit\" class=\"btn btn-danger btn-sm pull-right\" {{ ($node->servers_count < 1) ?: 'disabled' }}>确定，删除此节点。</button>\n                        </form>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n    <div class=\"col-sm-4\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">资源概览</h3>\n            </div>\n            <div class=\"box-body\">\n                <div class=\"row\">\n                    @if($node->maintenance_mode)\n                    <div class=\"col-sm-12\">\n                        <div class=\"info-box bg-orange\">\n                            <span class=\"info-box-icon\"><i class=\"ion ion-wrench\"></i></span>\n                            <div class=\"info-box-content\" style=\"padding: 23px 10px 0;\">\n                                <span class=\"info-box-text\">此节点状态为</span>\n                                <span class=\"info-box-number\">维护中</span>\n                            </div>\n                        </div>\n                    </div>\n                    @endif\n                    <div class=\"col-sm-12\">\n                        <div class=\"info-box bg-{{ $stats['disk']['css'] }}\">\n                            <span class=\"info-box-icon\"><i class=\"ion ion-ios-folder-outline\"></i></span>\n                            <div class=\"info-box-content\" style=\"padding: 15px 10px 0;\">\n                                <span class=\"info-box-text\">存储空间分配</span>\n                                <span class=\"info-box-number\">{{ $stats['disk']['value'] }} / {{ $stats['disk']['max'] }} MiB</span>\n                                <div class=\"progress\">\n                                    <div class=\"progress-bar\" style=\"width: {{ $stats['disk']['percent'] }}%\"></div>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                    <div class=\"col-sm-12\">\n                        <div class=\"info-box bg-{{ $stats['memory']['css'] }}\">\n                            <span class=\"info-box-icon\"><i class=\"ion ion-ios-barcode-outline\"></i></span>\n                            <div class=\"info-box-content\" style=\"padding: 15px 10px 0;\">\n                                <span class=\"info-box-text\">内存分配</span>\n                                <span class=\"info-box-number\">{{ $stats['memory']['value'] }} / {{ $stats['memory']['max'] }} MiB</span>\n                                <div class=\"progress\">\n                                    <div class=\"progress-bar\" style=\"width: {{ $stats['memory']['percent'] }}%\"></div>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                    <div class=\"col-sm-12\">\n                        <div class=\"info-box bg-blue\">\n                            <span class=\"info-box-icon\"><i class=\"ion ion-social-buffer-outline\"></i></span>\n                            <div class=\"info-box-content\" style=\"padding: 23px 10px 0;\">\n                                <span class=\"info-box-text\">服务器</span>\n                                <span class=\"info-box-number\">{{ $node->servers_count }}</span>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    function escapeHtml(str) {\n        var div = document.createElement('div');\n        div.appendChild(document.createTextNode(str));\n        return div.innerHTML;\n    }\n\n    (function getInformation() {\n        $.ajax({\n            method: 'GET',\n            url: '/admin/nodes/view/{{ $node->id }}/system-information',\n            timeout: 5000,\n        }).done(function (data) {\n            $('[data-attr=\"info-version\"]').html(escapeHtml(data.version));\n            $('[data-attr=\"info-system\"]').html(escapeHtml(data.system.type) + ' (' + escapeHtml(data.system.arch) + ') <code>' + escapeHtml(data.system.release) + '</code>');\n            $('[data-attr=\"info-cpus\"]').html(data.system.cpus);\n        }).fail(function (jqXHR) {\n\n        }).always(function() {\n            setTimeout(getInformation, 10000);\n        });\n    })();\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/nodes/view/servers.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    {{ $node->name }}: 服务器\n@endsection\n\n@section('content-header')\n    <h1>{{ $node->name }}<small>当前分配给该节点的所有服务器。</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nodes') }}\">节点</a></li>\n        <li><a href=\"{{ route('admin.nodes.view', $node->id) }}\">{{ $node->name }}</a></li>\n        <li class=\"active\">服务器</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"nav-tabs-custom nav-tabs-floating\">\n            <ul class=\"nav nav-tabs\">\n                <li><a href=\"{{ route('admin.nodes.view', $node->id) }}\">关于</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.settings', $node->id) }}\">设置</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.configuration', $node->id) }}\">配置</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.allocation', $node->id) }}\">分配</a></li>\n                <li class=\"active\"><a href=\"{{ route('admin.nodes.view.servers', $node->id) }}\">服务器</a></li>\n            </ul>\n        </div>\n    </div>\n</div>\n<div class=\"row\">\n    <div class=\"col-sm-12\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">服务器管理</h3>\n            </div>\n            <div class=\"box-body table-responsive no-padding\">\n                <table class=\"table table-hover\">\n                    <tr>\n                        <th>ID</th>\n                        <th>服务器名称</th>\n                        <th>服务器管理员</th>\n                        <th>使用预设</th>\n                    </tr>\n                    @foreach($servers as $server)\n                        <tr data-server=\"{{ $server->uuid }}\">\n                            <td><code>{{ $server->uuidShort }}</code></td>\n                            <td><a href=\"{{ route('admin.servers.view', $server->id) }}\">{{ $server->name }}</a></td>\n                            <td><a href=\"{{ route('admin.users.view', $server->owner_id) }}\">{{ $server->user->username }}</a></td>\n                            <td>{{ $server->nest->name }} ({{ $server->egg->name }})</td>\n                        </tr>\n                    @endforeach\n                </table>\n                @if($servers->hasPages())\n                    <div class=\"box-footer with-border\">\n                        <div class=\"col-md-12 text-center\">{!! $servers->render() !!}</div>\n                    </div>\n                @endif\n            </div>\n        </div>\n    </div>\n</div>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/nodes/view/settings.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    {{ $node->name }}: 设置\n@endsection\n\n@section('content-header')\n    <h1>{{ $node->name }}<small>配置你的节点设置.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.nodes') }}\">节点</a></li>\n        <li><a href=\"{{ route('admin.nodes.view', $node->id) }}\">{{ $node->name }}</a></li>\n        <li class=\"active\">设置</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"nav-tabs-custom nav-tabs-floating\">\n            <ul class=\"nav nav-tabs\">\n                <li><a href=\"{{ route('admin.nodes.view', $node->id) }}\">关于</a></li>\n                <li class=\"active\"><a href=\"{{ route('admin.nodes.view.settings', $node->id) }}\">设置</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.configuration', $node->id) }}\">配置</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.allocation', $node->id) }}\">分配</a></li>\n                <li><a href=\"{{ route('admin.nodes.view.servers', $node->id) }}\">服务器</a></li>\n            </ul>\n        </div>\n    </div>\n</div>\n<form action=\"{{ route('admin.nodes.view.settings', $node->id) }}\" method=\"POST\">\n    <div class=\"row\">\n        <div class=\"col-sm-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">设置</h3>\n                </div>\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"name\" class=\"control-label\">节点名称</label>\n                        <div>\n                            <input type=\"text\" autocomplete=\"off\" name=\"name\" class=\"form-control\" value=\"{{ old('name', $node->name) }}\" />\n                            <p class=\"text-muted\"><small>字符限制: <code>a-zA-Z0-9_.-</code> 和 <code>[空格]</code> (最少 1, 最多 100 字符).</small></p>\n                        </div>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"description\" class=\"control-label\">描述</label>\n                        <div>\n                            <textarea name=\"description\" id=\"description\" rows=\"4\" class=\"form-control\">{{ $node->description }}</textarea>\n                        </div>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"name\" class=\"control-label\">地域</label>\n                        <div>\n                            <select name=\"location_id\" class=\"form-control\">\n                                @foreach($locations as $location)\n                                    <option value=\"{{ $location->id }}\" {{ (((int) old('location_id', $node->location_id)) === $location->id) ? 'selected' : '' }}>{{ $location->long }} ({{ $location->short }})</option>\n                                @endforeach\n                            </select>\n                        </div>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"public\" class=\"control-label\">允许自动超额分配 <sup><a data-toggle=\"tooltip\" data-placement=\"top\" title=\"允许自动分配给该节点？\">?</a></sup></label>\n                        <div>\n                            <input type=\"radio\" name=\"public\" value=\"1\" {{ (old('public', $node->public)) ? 'checked' : '' }} id=\"public_1\" checked> <label for=\"public_1\" style=\"padding-left:5px;\">是</label><br />\n                            <input type=\"radio\" name=\"public\" value=\"0\" {{ (old('public', $node->public)) ? '' : 'checked' }} id=\"public_0\"> <label for=\"public_0\" style=\"padding-left:5px;\">否</label>\n                        </div>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"fqdn\" class=\"control-label\">域名</label>\n                        <div>\n                            <input type=\"text\" autocomplete=\"off\" name=\"fqdn\" class=\"form-control\" value=\"{{ old('fqdn', $node->fqdn) }}\" />\n                        </div>\n                        <p class=\"text-muted\"><small>请输入用于连接守护程序的域名 (例如 <code>node.example.com</code>). 仅当您没有为此节点使用 SSL 时才可以使用 IP 地址.\n                                <a tabindex=\"0\" data-toggle=\"popover\" data-trigger=\"focus\" title=\"为什么需要(FQDN)域名？\" data-content=\"为了保护您的服务器与此节点之间的通信，我们需要使用 SSL。我们无法为 IP 地址生成 SSL 证书，因此您需要提供(FQDN)域名。\">为什么？</a>\n                            </small></p>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <label class=\"form-label\"><span class=\"label label-warning\"><i class=\"fa fa-power-off\"></i></span>面板前端以 SSL 通信</label>\n                        <div>\n                            <div class=\"radio radio-success radio-inline\">\n                                <input type=\"radio\" id=\"pSSLTrue\" value=\"https\" name=\"scheme\" {{ (old('scheme', $node->scheme) === 'https') ? 'checked' : '' }}>\n                                <label for=\"pSSLTrue\"> 使用 SSL 通信</label>\n                            </div>\n                            <div class=\"radio radio-danger radio-inline\">\n                                <input type=\"radio\" id=\"pSSLFalse\" value=\"http\" name=\"scheme\" {{ (old('scheme', $node->scheme) !== 'https') ? 'checked' : '' }}>\n                                <label for=\"pSSLFalse\"> 使用 HTTP 通信 (无 SSL)</label>\n                            </div>\n                        </div>\n                        <p class=\"text-muted small\">在大多数情况下，您应该选择使用 SSL 连接。如果使用 IP 地址或者您根本不想使用 SSL，请选择 HTTP 连接.</p>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <label class=\"form-label\"><span class=\"label label-warning\"><i class=\"fa fa-power-off\"></i></span> 通过代理</label>\n                        <div>\n                            <div class=\"radio radio-success radio-inline\">\n                                <input type=\"radio\" id=\"pProxyFalse\" value=\"0\" name=\"behind_proxy\" {{ (old('behind_proxy', $node->behind_proxy) == false) ? 'checked' : '' }}>\n                                <label for=\"pProxyFalse\"> 不通过代理 </label>\n                            </div>\n                            <div class=\"radio radio-info radio-inline\">\n                                <input type=\"radio\" id=\"pProxyTrue\" value=\"1\" name=\"behind_proxy\" {{ (old('behind_proxy', $node->behind_proxy) == true) ? 'checked' : '' }}>\n                                <label for=\"pProxyTrue\"> 通过代理 </label>\n                            </div>\n                        </div>\n                        <p class=\"text-muted small\">如果您在 Cloudflare 等代理CDN运行守护程序，请选择此选项以使守护程序在启动时跳过查找证书。</p>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <label class=\"form-label\"><span class=\"label label-warning\"><i class=\"fa fa-wrench\"></i></span> 维护模式</label>\n                        <div>\n                            <div class=\"radio radio-success radio-inline\">\n                                <input type=\"radio\" id=\"pMaintenanceFalse\" value=\"0\" name=\"maintenance_mode\" {{ (old('maintenance_mode', $node->maintenance_mode) == false) ? 'checked' : '' }}>\n                                <label for=\"pMaintenanceFalse\"> 关闭</label>\n                            </div>\n                            <div class=\"radio radio-warning radio-inline\">\n                                <input type=\"radio\" id=\"pMaintenanceTrue\" value=\"1\" name=\"maintenance_mode\" {{ (old('maintenance_mode', $node->maintenance_mode) == true) ? 'checked' : '' }}>\n                                <label for=\"pMaintenanceTrue\"> 开启</label>\n                            </div>\n                        </div>\n                        <p class=\"text-muted small\">如果节点被标记为“维护中”，用户将无法访问该节点上的服务器.</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-sm-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">分配限制</h3>\n                </div>\n                <div class=\"box-body row\">\n                    <div class=\"col-xs-12\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-xs-6\">\n                                <label for=\"memory\" class=\"control-label\">总内存</label>\n                                <div class=\"input-group\">\n                                    <input type=\"text\" name=\"memory\" class=\"form-control\" data-multiplicator=\"true\" value=\"{{ old('memory', $node->memory) }}\"/>\n                                    <span class=\"input-group-addon\">MiB</span>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-xs-6\">\n                                <label for=\"memory_overallocate\" class=\"control-label\">超额分配百分比</label>\n                                <div class=\"input-group\">\n                                    <input type=\"text\" name=\"memory_overallocate\" class=\"form-control\" value=\"{{ old('memory_overallocate', $node->memory_overallocate) }}\"/>\n                                    <span class=\"input-group-addon\">%</span>\n                                </div>\n                            </div>\n                        </div>\n                        <p class=\"text-muted small\">输入此节点上可用于分配给服务器的内存总量。您还可以提供一个百分比，允许分配超过定义的内存.</p>\n                    </div>\n                    <div class=\"col-xs-12\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-xs-6\">\n                                <label for=\"disk\" class=\"control-label\">总存储空间</label>\n                                <div class=\"input-group\">\n                                    <input type=\"text\" name=\"disk\" class=\"form-control\" data-multiplicator=\"true\" value=\"{{ old('disk', $node->disk) }}\"/>\n                                    <span class=\"input-group-addon\">MiB</span>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-xs-6\">\n                                <label for=\"disk_overallocate\" class=\"control-label\">超额分配百分比</label>\n                                <div class=\"input-group\">\n                                    <input type=\"text\" name=\"disk_overallocate\" class=\"form-control\" value=\"{{ old('disk_overallocate', $node->disk_overallocate) }}\"/>\n                                    <span class=\"input-group-addon\">%</span>\n                                </div>\n                            </div>\n                        </div>\n                        <p class=\"text-muted small\">输入此节点上可用于服务器分配存储空间总量。您还可以提供一个百分比来确定超出设置限制的存储空间量以允许.</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-sm-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">常规配置</h3>\n                </div>\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"disk_overallocate\" class=\"control-label\">最大网页文件上传大小</label>\n                        <div class=\"input-group\">\n                            <input type=\"text\" name=\"upload_size\" class=\"form-control\" value=\"{{ old('upload_size', $node->upload_size) }}\"/>\n                            <span class=\"input-group-addon\">MiB</span>\n                        </div>\n                        <p class=\"text-muted\"><small>输入可以通过基于 Web 的文件管理器上传的文件的最大大小.</small></p>\n                    </div>\n                    <div class=\"col-xs-12\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-6\">\n                                <label for=\"daemonListen\" class=\"control-label\"><span class=\"label label-warning\"><i class=\"fa fa-power-off\"></i></span> 守护进程端口</label>\n                                <div>\n                                    <input type=\"text\" name=\"daemonListen\" class=\"form-control\" value=\"{{ old('daemonListen', $node->daemonListen) }}\"/>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-6\">\n                                <label for=\"daemonSFTP\" class=\"control-label\"><span class=\"label label-warning\"><i class=\"fa fa-power-off\"></i></span> 守护进程 SFTP 端口</label>\n                                <div>\n                                    <input type=\"text\" name=\"daemonSFTP\" class=\"form-control\" value=\"{{ old('daemonSFTP', $node->daemonSFTP) }}\"/>\n                                </div>\n                            </div>\n                        </div>\n                        <div class=\"row\">\n                            <div class=\"col-md-12\">\n                                <p class=\"text-muted\"><small>守护进程运行自己的 SFTP 管理容器，不使用主物理服务器上的 SSHd 进程. <Strong>不要使用为物理服务器的 SSH 进程分配的相同端口.</strong></small></p>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-xs-12\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">保存设置</h3>\n                </div>\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-sm-6\">\n                        <div>\n                            <input type=\"checkbox\" name=\"reset_secret\" id=\"reset_secret\" /> <label for=\"reset_secret\" class=\"control-label\">重置守护进程超级密钥</label>\n                        </div>\n                        <p class=\"text-muted\"><small>重置守护程序超级密钥将使来自旧密钥的任何请求无效。此密钥用于守护程序上的所有敏感操作，包括服务器创建和删除。我们建议定期更改此密钥以确保安全.</small></p>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! method_field('PATCH') !!}\n                    {!! csrf_field() !!}\n                    <button type=\"submit\" class=\"btn btn-primary pull-right\">保存更改</button>\n                </div>\n            </div>\n        </div>\n    </div>\n</form>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    $('[data-toggle=\"popover\"]').popover({\n        placement: 'auto'\n    });\n    $('select[name=\"location_id\"]').select2();\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/servers/index.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    服务器列表\n@endsection\n\n@section('content-header')\n    <h1>服务器列表<small>此系统上所有的可用服务器.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">服务器</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">服务器列表</h3>\n                <div class=\"box-tools search01\">\n                    <form action=\"{{ route('admin.servers') }}\" method=\"GET\">\n                        <div class=\"input-group input-group-sm\">\n                            <input type=\"text\" name=\"filter[*]\" class=\"form-control pull-right\" value=\"{{ request()->input()['filter']['*'] ?? '' }}\" placeholder=\"搜索服务器\">\n                            <div class=\"input-group-btn\">\n                                <button type=\"submit\" class=\"btn btn-default\"><i class=\"fa fa-search\"></i></button>\n                                <a href=\"{{ route('admin.servers.new') }}\"><button type=\"button\" class=\"btn btn-sm btn-primary\" style=\"border-radius: 0 3px 3px 0;margin-left:-1px;\">新建</button></a>\n                            </div>\n                        </div>\n                    </form>\n                </div>\n            </div>\n            <div class=\"box-body table-responsive no-padding\">\n                <table class=\"table table-hover\">\n                    <tbody>\n                        <tr>\n                            <th>名称</th>\n                            <th>UUID</th>\n                            <th>所有者</th>\n                            <th>节点</th>\n                            <th>连接地址</th>\n                            <th></th>\n                            <th></th>\n                        </tr>\n                        @foreach ($servers as $server)\n                            <tr data-server=\"{{ $server->uuidShort }}\">\n                                <td><a href=\"{{ route('admin.servers.view', $server->id) }}\">{{ $server->name }}</a></td>\n                                <td><code title=\"{{ $server->uuid }}\">{{ $server->uuid }}</code></td>\n                                <td><a href=\"{{ route('admin.users.view', $server->user->id) }}\">{{ $server->user->username }}</a></td>\n                                <td><a href=\"{{ route('admin.nodes.view', $server->node->id) }}\">{{ $server->node->name }}</a></td>\n                                <td>\n                                    <code>{{ $server->allocation->alias }}:{{ $server->allocation->port }}</code>\n                                </td>\n                                <td class=\"text-center\">\n                                    @if($server->isSuspended())\n                                        <span class=\"label bg-maroon\">冻结中</span>\n                                    @elseif(! $server->isInstalled())\n                                        <span class=\"label label-warning\">安装中</span>\n                                    @else\n                                        <span class=\"label label-success\">正常</span>\n                                    @endif\n                                </td>\n                                <td class=\"text-center\">\n                                    <a class=\"btn btn-xs btn-default\" href=\"/server/{{ $server->uuidShort }}\"><i class=\"fa fa-wrench\"></i></a>\n                                </td>\n                            </tr>\n                        @endforeach\n                    </tbody>\n                </table>\n            </div>\n            @if($servers->hasPages())\n                <div class=\"box-footer with-border\">\n                    <div class=\"col-md-12 text-center\">{!! $servers->appends(['filter' => Request::input('filter')])->render() !!}</div>\n                </div>\n            @endif\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n        $('.console-popout').on('click', function (event) {\n            event.preventDefault();\n            window.open($(this).attr('href'), 'Pterodactyl Console', 'width=800,height=400');\n        });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/servers/new.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    创建服务器\n@endsection\n\n@section('content-header')\n    <h1>创建服务器<small>创建一个新的服务器.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.servers') }}\">服务器</a></li>\n        <li class=\"active\">创建服务器</li>\n    </ol>\n@endsection\n\n@section('content')\n<form action=\"{{ route('admin.servers.new') }}\" method=\"POST\">\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">核心细节</h3>\n                </div>\n\n                <div class=\"box-body row\">\n                    <div class=\"col-md-6\">\n                        <div class=\"form-group\">\n                            <label for=\"pName\">名称</label>\n                            <input type=\"text\" class=\"form-control\" id=\"pName\" name=\"name\" value=\"{{ old('name') }}\" placeholder=\"服务器名称\">\n                            <p class=\"small text-muted no-margin\">字符限制: <code>a-z A-Z 0-9 _ - .</code> 和 <code>[空格]</code>.</p>\n                        </div>\n\n                        <div class=\"form-group\">\n                            <label for=\"pUserId\">所有者</label>\n                            <select id=\"pUserId\" name=\"owner_id\" class=\"form-control\" style=\"padding-left:0;\"></select>\n                            <p class=\"small text-muted no-margin\">所有者账户的电子邮箱地址.</p>\n                        </div>\n                    </div>\n\n                    <div class=\"col-md-6\">\n                        <div class=\"form-group\">\n                            <label for=\"pDescription\" class=\"control-label\">服务器描述</label>\n                            <textarea id=\"pDescription\" name=\"description\" rows=\"3\" class=\"form-control\">{{ old('description') }}</textarea>\n                            <p class=\"text-muted small\">服务器的简单介绍.</p>\n                        </div>\n\n                        <div class=\"form-group\">\n                            <div class=\"checkbox checkbox-primary no-margin-bottom\">\n                                <input id=\"pStartOnCreation\" name=\"start_on_completion\" type=\"checkbox\" {{ \\Pterodactyl\\Helpers\\Utilities::checked('start_on_completion', 1) }} />\n                                <label for=\"pStartOnCreation\" class=\"strong\">安装完成后启动</label>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"overlay\" id=\"allocationLoader\" style=\"display:none;\"><i class=\"fa fa-refresh fa-spin\"></i></div>\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">分配管理</h3>\n                </div>\n\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-sm-4\">\n                        <label for=\"pNodeId\">节点</label>\n                        <select name=\"node_id\" id=\"pNodeId\" class=\"form-control\">\n                            @foreach($locations as $location)\n                                <optgroup label=\"{{ $location->long }} ({{ $location->short }})\">\n                                @foreach($location->nodes as $node)\n\n                                <option value=\"{{ $node->id }}\"\n                                    @if($location->id === old('location_id')) selected @endif\n                                >{{ $node->name }}</option>\n\n                                @endforeach\n                                </optgroup>\n                            @endforeach\n                        </select>\n\n                        <p class=\"small text-muted no-margin\">该服务器将被部署到的节点。</p>\n                    </div>\n\n                    <div class=\"form-group col-sm-4\">\n                        <label for=\"pAllocation\">默认网络分配</label>\n                        <select id=\"pAllocation\" name=\"allocation_id\" class=\"form-control\"></select>\n                        <p class=\"small text-muted no-margin\">此服务器的默认网络分配.</p>\n                    </div>\n\n                    <div class=\"form-group col-sm-4\">\n                        <label for=\"pAllocationAdditional\">额外网络分配</label>\n                        <select id=\"pAllocationAdditional\" name=\"allocation_additional[]\" class=\"form-control\" multiple></select>\n                        <p class=\"small text-muted no-margin\">此服务器的额外网络分配.</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"overlay\" id=\"allocationLoader\" style=\"display:none;\"><i class=\"fa fa-refresh fa-spin\"></i></div>\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">应用功能限制</h3>\n                </div>\n\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-xs-6\">\n                        <label for=\"pDatabaseLimit\" class=\"control-label\">数据库限制</label>\n                        <div>\n                            <input type=\"text\" id=\"pDatabaseLimit\" name=\"database_limit\" class=\"form-control\" value=\"{{ old('database_limit', 0) }}\"/>\n                        </div>\n                        <p class=\"text-muted small\">允许用户为此服务器创建的数据库总数.</p>\n                    </div>\n                    <div class=\"form-group col-xs-6\">\n                        <label for=\"pAllocationLimit\" class=\"control-label\">网络分配限制</label>\n                        <div>\n                            <input type=\"text\" id=\"pAllocationLimit\" name=\"allocation_limit\" class=\"form-control\" value=\"{{ old('allocation_limit', 0) }}\"/>\n                        </div>\n                        <p class=\"text-muted small\">允许用户为此服务器创建的网络分配总数.</p>\n                    </div>\n                    <div class=\"form-group col-xs-6\">\n                        <label for=\"pBackupLimit\" class=\"control-label\">备份限制</label>\n                        <div>\n                            <input type=\"text\" id=\"pBackupLimit\" name=\"backup_limit\" class=\"form-control\" value=\"{{ old('backup_limit', 0) }}\"/>\n                        </div>\n                        <p class=\"text-muted small\">可以为此服务器创建的备份总数.</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">资源管理</h3>\n                </div>\n\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-xs-6\">\n                        <label for=\"pCPU\">CPU 限制</label>\n\n                        <div class=\"input-group\">\n                            <input type=\"text\" id=\"pCPU\" name=\"cpu\" class=\"form-control\" value=\"{{ old('cpu', 0) }}\" />\n                            <span class=\"input-group-addon\">%</span>\n                        </div>\n\n                        <p class=\"text-muted small\">如果您不想限制 CPU 使用率，请将值设置为 <code>0</code>. 要确定一个值，请将线程数乘以 100。例如，在没有超线程的四核系统上 <code>(4 * 100 = 400)</code> 填写 <code>400</code> . 要将服务器限制为使用单个线程的一半，您可以将值设置为 <code>50</code>. 要允许服务器最多使用两个线程，请将值设置为 <code>200</code>.<p>\n                    </div>\n\n                    <div class=\"form-group col-xs-6\">\n                        <label for=\"pThreads\">CPU 核心</label>\n\n                        <div>\n                            <input type=\"text\" id=\"pThreads\" name=\"threads\" class=\"form-control\" value=\"{{ old('threads') }}\" />\n                        </div>\n\n                        <p class=\"text-muted small\"><strong>高级:</strong> 输入此进程可以运行的特定 CPU 线程，或留空以允许所有线程。这可以是单个数字，也可以是逗号分隔的列表. 例如: <code>0</code>, <code>0-1,3</code>, 或 <code>0,1,3,4</code>.</p>\n                    </div>\n                </div>\n\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-xs-6\">\n                        <label for=\"pMemory\">内存</label>\n\n                        <div class=\"input-group\">\n                            <input type=\"text\" id=\"pMemory\" name=\"memory\" class=\"form-control\" value=\"{{ old('memory') }}\" />\n                            <span class=\"input-group-addon\">MiB</span>\n                        </div>\n\n                        <p class=\"text-muted small\">此容器允许的最大内存量。将此设置为 <code>0</code> 将允许此服务器无限制使用内存.</p>\n                    </div>\n\n                    <div class=\"form-group col-xs-6\">\n                        <label for=\"pSwap\">交换内存</label>\n\n                        <div class=\"input-group\">\n                            <input type=\"text\" id=\"pSwap\" name=\"swap\" class=\"form-control\" value=\"{{ old('swap', 0) }}\" />\n                            <span class=\"input-group-addon\">MiB</span>\n                        </div>\n\n                        <p class=\"text-muted small\">将此设置为 <code>0</code> 将禁用此服务器上的交换内存. 将此设置为 <code>-1</code> 将允许此服务器使用无限交换内存.</p>\n                    </div>\n                </div>\n\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-xs-6\">\n                        <label for=\"pDisk\">存储空间</label>\n\n                        <div class=\"input-group\">\n                            <input type=\"text\" id=\"pDisk\" name=\"disk\" class=\"form-control\" value=\"{{ old('disk') }}\" />\n                            <span class=\"input-group-addon\">MiB</span>\n                        </div>\n\n                        <p class=\"text-muted small\">如果此服务器使用的空间超过此数量，则将不允许它启动。如果服务器在运行时超过此限制，它将安全停止并锁定，直到有足够的可用空间。调成 <code>0</code> 将允许此服务器使用无限存储空间.</p>\n                    </div>\n\n                    <div class=\"form-group col-xs-6\">\n                        <label for=\"pIO\">IO 优先级</label>\n\n                        <div>\n                            <input type=\"text\" id=\"pIO\" name=\"io\" class=\"form-control\" value=\"{{ old('io', 500) }}\" />\n                        </div>\n\n                        <p class=\"text-muted small\"><strong>高级</strong>: 此服务器相对于其他 <em>运行中</em> 服务器的 IO 性能 . 此值应介于 <code>10</code> 至 <code>1000</code>. 请查阅 <a href=\"https://docs.docker.com/engine/reference/run/#block-io-bandwidth-blkio-constraint\" target=\"_blank\">此文档</a> 了解更多.</p>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <div class=\"checkbox checkbox-primary no-margin-bottom\">\n                            <input type=\"checkbox\" id=\"pOomDisabled\" name=\"oom_disabled\" value=\"0\" {{ \\Pterodactyl\\Helpers\\Utilities::checked('oom_disabled', 0) }} />\n                            <label for=\"pOomDisabled\" class=\"strong\">启用 OOM Killer</label>\n                        </div>\n\n                        <p class=\"small text-muted no-margin\">如果服务器超出内存限制，则终止服务器。启用 OOM Killer 可能会导致服务器进程意外退出.</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n\n    <div class=\"row\">\n        <div class=\"col-md-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">预设组设置</h3>\n                </div>\n\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"pNestId\">预设组</label>\n\n                        <select id=\"pNestId\" name=\"nest_id\" class=\"form-control\">\n                            @foreach($nests as $nest)\n                                <option value=\"{{ $nest->id }}\"\n                                    @if($nest->id === old('nest_id'))\n                                        selected=\"selected\"\n                                    @endif\n                                >{{ $nest->name }}</option>\n                            @endforeach\n                        </select>\n\n                        <p class=\"small text-muted no-margin\">选择此服务器将归入的预设组.</p>\n                    </div>\n\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"pEggId\">预设</label>\n                        <select id=\"pEggId\" name=\"egg_id\" class=\"form-control\"></select>\n                        <p class=\"small text-muted no-margin\">选择将定义此服务器如何正确运行的预设.</p>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <div class=\"checkbox checkbox-primary no-margin-bottom\">\n                            <input type=\"checkbox\" id=\"pSkipScripting\" name=\"skip_scripts\" value=\"1\" {{ \\Pterodactyl\\Helpers\\Utilities::checked('skip_scripts', 0) }} />\n                            <label for=\"pSkipScripting\" class=\"strong\">跳过预设安装脚本</label>\n                        </div>\n\n                        <p class=\"small text-muted no-margin\">如果选定的预设附加了安装脚本，则该程序将在安装期间运行。如果您想跳过此步骤，请选中此框.</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n\n        <div class=\"col-md-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">Docker 设置</h3>\n                </div>\n\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"pDefaultContainer\">Docker 镜像</label>\n                        <select id=\"pDefaultContainer\" name=\"image\" class=\"form-control\"></select>\n                        <input id=\"pDefaultContainerCustom\" name=\"custom_image\" value=\"{{ old('custom_image') }}\" class=\"form-control\" placeholder=\"或输入自定义镜像...\" style=\"margin-top:1rem\"/>\n                        <p class=\"small text-muted no-margin\">这是将用于运行此服务器的默认 Docker 映像。从上面的下拉列表中选择一个镜像，或在上面的文本字段中输入一个自定义镜像.</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n\n    <div class=\"row\">\n        <div class=\"col-md-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">启动设置</h3>\n                </div>\n\n                <div class=\"box-body row\">\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"pStartup\">启动指令</label>\n                        <input type=\"text\" id=\"pStartup\" name=\"startup\" value=\"{{ old('startup') }}\" class=\"form-control\" />\n                        <p class=\"small text-muted no-margin\">以下变量可用于启动命令: <code>@{{SERVER_MEMORY}}</code>, <code>@{{SERVER_IP}}</code>, 和 <code>@{{SERVER_PORT}}</code>. 它们将分别替换为分配的内存、服务器 IP 和服务器端口的值.</p>\n                    </div>\n                </div>\n\n                <div class=\"box-header with-border\" style=\"margin-top:-10px;\">\n                    <h3 class=\"box-title\">变量</h3>\n                </div>\n\n                <div class=\"box-body row\" id=\"appendVariablesTo\"></div>\n\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <input type=\"submit\" class=\"btn btn-success pull-right\" value=\"创建服务器\" />\n                </div>\n            </div>\n        </div>\n    </div>\n</form>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    {!! Theme::js('vendor/lodash/lodash.js') !!}\n\n    <script type=\"application/javascript\">\n        // Persist 'Service Variables'\n        function serviceVariablesUpdated(eggId, ids) {\n            @if (old('egg_id'))\n                // Check if the egg id matches.\n                if (eggId != '{{ old('egg_id') }}') {\n                    return;\n                }\n\n                @if (old('environment'))\n                    @foreach (old('environment') as $key => $value)\n                        $('#' + ids['{{ $key }}']).val('{{ $value }}');\n                    @endforeach\n                @endif\n            @endif\n            @if(old('image'))\n                $('#pDefaultContainer').val('{{ old('image') }}');\n            @endif\n        }\n        // END Persist 'Service Variables'\n    </script>\n\n    {!! Theme::js('js/admin/new-server.js?v=20220530') !!}\n\n    <script type=\"application/javascript\">\n        $(document).ready(function() {\n            // Persist 'Server Owner' select2\n            @if (old('owner_id'))\n                $.ajax({\n                    url: '/admin/users/accounts.json?user_id={{ old('owner_id') }}',\n                    dataType: 'json',\n                }).then(function (data) {\n                    initUserIdSelect([ data ]);\n                });\n            @else\n                initUserIdSelect();\n            @endif\n            // END Persist 'Server Owner' select2\n\n            // Persist 'Node' select2\n            @if (old('node_id'))\n                $('#pNodeId').val('{{ old('node_id') }}').change();\n\n                // Persist 'Default Allocation' select2\n                @if (old('allocation_id'))\n                    $('#pAllocation').val('{{ old('allocation_id') }}').change();\n                @endif\n                // END Persist 'Default Allocation' select2\n\n                // Persist 'Additional Allocations' select2\n                @if (old('allocation_additional'))\n                    const additional_allocations = [];\n\n                    @for ($i = 0; $i < count(old('allocation_additional')); $i++)\n                        additional_allocations.push('{{ old('allocation_additional.'.$i)}}');\n                    @endfor\n\n                    $('#pAllocationAdditional').val(additional_allocations).change();\n                @endif\n                // END Persist 'Additional Allocations' select2\n            @endif\n            // END Persist 'Node' select2\n\n            // Persist 'Nest' select2\n            @if (old('nest_id'))\n                $('#pNestId').val('{{ old('nest_id') }}').change();\n\n                // Persist 'Egg' select2\n                @if (old('egg_id'))\n                    $('#pEggId').val('{{ old('egg_id') }}').change();\n                @endif\n                // END Persist 'Egg' select2\n            @endif\n            // END Persist 'Nest' select2\n        });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/servers/partials/navigation.blade.php",
    "content": "@php\n    /** @var \\Pterodactyl\\Models\\Server $server */\n    $router = app('router');\n@endphp\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"nav-tabs-custom nav-tabs-floating\">\n            <ul class=\"nav nav-tabs\">\n                <li class=\"{{ $router->currentRouteNamed('admin.servers.view') ? 'active' : '' }}\">\n                    <a href=\"{{ route('admin.servers.view', $server->id) }}\">关于</a></li>\n                @if($server->isInstalled())\n                    <li class=\"{{ $router->currentRouteNamed('admin.servers.view.details') ? 'active' : '' }}\">\n                        <a href=\"{{ route('admin.servers.view.details', $server->id) }}\">详细信息</a>\n                    </li>\n                    <li class=\"{{ $router->currentRouteNamed('admin.servers.view.build') ? 'active' : '' }}\">\n                        <a href=\"{{ route('admin.servers.view.build', $server->id) }}\">构建配置</a>\n                    </li>\n                    <li class=\"{{ $router->currentRouteNamed('admin.servers.view.startup') ? 'active' : '' }}\">\n                        <a href=\"{{ route('admin.servers.view.startup', $server->id) }}\">启动</a>\n                    </li>\n                    <li class=\"{{ $router->currentRouteNamed('admin.servers.view.database') ? 'active' : '' }}\">\n                        <a href=\"{{ route('admin.servers.view.database', $server->id) }}\">数据库</a>\n                    </li>\n                    <li class=\"{{ $router->currentRouteNamed('admin.servers.view.mounts') ? 'active' : '' }}\">\n                        <a href=\"{{ route('admin.servers.view.mounts', $server->id) }}\">挂载</a>\n                    </li>\n                @endif\n                <li class=\"{{ $router->currentRouteNamed('admin.servers.view.manage') ? 'active' : '' }}\">\n                    <a href=\"{{ route('admin.servers.view.manage', $server->id) }}\">管理</a>\n                </li>\n                <li class=\"tab-danger {{ $router->currentRouteNamed('admin.servers.view.delete') ? 'active' : '' }}\">\n                    <a href=\"{{ route('admin.servers.view.delete', $server->id) }}\">删除</a>\n                </li>\n                <li class=\"tab-success\">\n                    <a href=\"/server/{{ $server->uuidShort }}\" target=\"_blank\"><i class=\"fa fa-external-link\"></i></a>\n                </li>\n            </ul>\n        </div>\n    </div>\n</div>\n"
  },
  {
    "path": "resources/views/admin/servers/view/build.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    服务器 — {{ $server->name }}: 构建配置\n@endsection\n\n@section('content-header')\n    <h1>{{ $server->name }}<small>控制此服务器的分配和系统资源。</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.servers') }}\">服务器</a></li>\n        <li><a href=\"{{ route('admin.servers.view', $server->id) }}\">{{ $server->name }}</a></li>\n        <li class=\"active\">构建配置</li>\n    </ol>\n@endsection\n\n@section('content')\n@include('admin.servers.partials.navigation')\n<div class=\"row\">\n    <form action=\"{{ route('admin.servers.view.build', $server->id) }}\" method=\"POST\">\n        <div class=\"col-sm-5\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">资源管理</h3>\n                </div>\n                <div class=\"box-body\">\n                <div class=\"form-group\">\n                        <label for=\"cpu\" class=\"control-label\">CPU 限制</label>\n                        <div class=\"input-group\">\n                            <input type=\"text\" name=\"cpu\" class=\"form-control\" value=\"{{ old('cpu', $server->cpu) }}\"/>\n                            <span class=\"input-group-addon\">%</span>\n                        </div>\n                        <p class=\"text-muted small\">每 <em>虚拟</em> 内核 (线程) 于此系统都将视为 <code>100%</code>. 将此值设置为 <code>0</code> 将允许此服务器无限制使用CPU虚拟线程.</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"threads\" class=\"control-label\">CPU 核心</label>\n                        <div>\n                            <input type=\"text\" name=\"threads\" class=\"form-control\" value=\"{{ old('threads', $server->threads) }}\"/>\n                        </div>\n                        <p class=\"text-muted small\"><strong>高级:</strong> 输入此进程可以在其上运行的特定 CPU 内核，或留空以允许所有内核。这可以是单个数字，也可以是逗号分隔的列表. 例如: <code>0</code>, <code>0-1,3</code>, 或者 <code>0,1,3,4</code>.</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"memory\" class=\"control-label\">分配内存</label>\n                        <div class=\"input-group\">\n                            <input type=\"text\" name=\"memory\" data-multiplicator=\"true\" class=\"form-control\" value=\"{{ old('memory', $server->memory) }}\"/>\n                            <span class=\"input-group-addon\">MiB</span>\n                        </div>\n                        <p class=\"text-muted small\">此服务器允许的最大内存使用量。将此设置为 <code>0</code> 将不限制此服务器内存使用。</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"swap\" class=\"control-label\">分配交换内存</label>\n                        <div class=\"input-group\">\n                            <input type=\"text\" name=\"swap\" data-multiplicator=\"true\" class=\"form-control\" value=\"{{ old('swap', $server->swap) }}\"/>\n                            <span class=\"input-group-addon\">MiB</span>\n                        </div>\n                        <p class=\"text-muted small\">将此设置为 <code>0</code> 将禁用此服务器的交换内存. 将此设置为 <code>-1</code> 将允许此服务器使用无限制交换内存.</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"cpu\" class=\"control-label\">存储空间限制</label>\n                        <div class=\"input-group\">\n                            <input type=\"text\" name=\"disk\" class=\"form-control\" value=\"{{ old('disk', $server->disk) }}\"/>\n                            <span class=\"input-group-addon\">MiB</span>\n                        </div>\n                        <p class=\"text-muted small\">如果此服务器使用的空间超过此数量，则将不允许它启动。如果服务器在运行时超过此限制，它将安全停止并锁定，直到有足够的可用空间。调成 <code>0</code> 允许此服务器无限制使用存储空间.</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"io\" class=\"control-label\">IO 优先级</label>\n                        <div>\n                            <input type=\"text\" name=\"io\" class=\"form-control\" value=\"{{ old('io', $server->io) }}\"/>\n                        </div>\n                        <p class=\"text-muted small\"><strong>高级</strong>: 此服务器相对于其他 <em>运行中</em> 服务器的 IO 性能 . 此值应介于 <code>10</code> 至 <code>1000</code>.</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"cpu\" class=\"control-label\">OOM Killer</label>\n                        <div>\n                            <div class=\"radio radio-danger radio-inline\">\n                                <input type=\"radio\" id=\"pOomKillerEnabled\" value=\"0\" name=\"oom_disabled\" @if(!$server->oom_disabled)checked @endif>\n                                <label for=\"pOomKillerEnabled\">启用</label>\n                            </div>\n                            <div class=\"radio radio-success radio-inline\">\n                                <input type=\"radio\" id=\"pOomKillerDisabled\" value=\"1\" name=\"oom_disabled\" @if($server->oom_disabled)checked @endif>\n                                <label for=\"pOomKillerDisabled\">禁用</label>\n                            </div>\n                            <p class=\"text-muted small\">\n                                启用 OOM killer 可能会导致服务器程序异常.\n                            </p>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-sm-7\">\n            <div class=\"row\">\n                <div class=\"col-xs-12\">\n                    <div class=\"box\">\n                        <div class=\"box-header with-border\">\n                            <h3 class=\"box-title\">应用程序功能限制</h3>\n                        </div>\n                        <div class=\"box-body\">\n                            <div class=\"row\">\n                                <div class=\"form-group col-xs-6\">\n                                    <label for=\"database_limit\" class=\"control-label\">数据库限制</label>\n                                    <div>\n                                        <input type=\"text\" name=\"database_limit\" class=\"form-control\" value=\"{{ old('database_limit', $server->database_limit) }}\"/>\n                                    </div>\n                                    <p class=\"text-muted small\">允许用户为此服务器创建的数据库总数.</p>\n                                </div>\n                                <div class=\"form-group col-xs-6\">\n                                    <label for=\"allocation_limit\" class=\"control-label\">网络分配限制</label>\n                                    <div>\n                                        <input type=\"text\" name=\"allocation_limit\" class=\"form-control\" value=\"{{ old('allocation_limit', $server->allocation_limit) }}\"/>\n                                    </div>\n                                    <p class=\"text-muted small\">允许用户为此服务器创建的网络分配总数。</p>\n                                </div>\n                                <div class=\"form-group col-xs-6\">\n                                    <label for=\"backup_limit\" class=\"control-label\">备份限制</label>\n                                    <div>\n                                        <input type=\"text\" name=\"backup_limit\" class=\"form-control\" value=\"{{ old('backup_limit', $server->backup_limit) }}\"/>\n                                    </div>\n                                    <p class=\"text-muted small\">可以为此服务器创建的备份总数。</p>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"col-xs-12\">\n                    <div class=\"box\">\n                        <div class=\"box-header with-border\">\n                            <h3 class=\"box-title\">网络分配</h3>\n                        </div>\n                        <div class=\"box-body\">\n                            <div class=\"form-group\">\n                                <label for=\"pAllocation\" class=\"control-label\">端口</label>\n                                <select id=\"pAllocation\" name=\"allocation_id\" class=\"form-control\">\n                                    @foreach ($assigned as $assignment)\n                                        <option value=\"{{ $assignment->id }}\"\n                                            @if($assignment->id === $server->allocation_id)\n                                                selected=\"selected\"\n                                            @endif\n                                        >{{ $assignment->alias }}:{{ $assignment->port }}</option>\n                                    @endforeach\n                                </select>\n                                <p class=\"text-muted small\">将用于此服务器的默认连接地址。</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pAddAllocations\" class=\"control-label\">分配额外端口</label>\n                                <div>\n                                    <select name=\"add_allocations[]\" class=\"form-control\" multiple id=\"pAddAllocations\">\n                                        @foreach ($unassigned as $assignment)\n                                            <option value=\"{{ $assignment->id }}\">{{ $assignment->alias }}:{{ $assignment->port }}</option>\n                                        @endforeach\n                                    </select>\n                                </div>\n                                <p class=\"text-muted small\">请注意，由于软件限制，您不能将不同 IP 上的相同端口分配给同一台服务器.</p>\n                            </div>\n                            <div class=\"form-group\">\n                                <label for=\"pRemoveAllocations\" class=\"control-label\">移除额外端口</label>\n                                <div>\n                                    <select name=\"remove_allocations[]\" class=\"form-control\" multiple id=\"pRemoveAllocations\">\n                                        @foreach ($assigned as $assignment)\n                                            <option value=\"{{ $assignment->id }}\">{{ $assignment->alias }}:{{ $assignment->port }}</option>\n                                        @endforeach\n                                    </select>\n                                </div>\n                                <p class=\"text-muted small\">只需从上面的列表中选择您要删除的端口。如果您想在已使用的不同 IP 上分配一个端口，您可以从左侧选择它并在此处将其删除.</p>\n                            </div>\n                        </div>\n                        <div class=\"box-footer\">\n                            {!! csrf_field() !!}\n                            <button type=\"submit\" class=\"btn btn-primary pull-right\">更新构建配置</button>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </form>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    $('#pAddAllocations').select2();\n    $('#pRemoveAllocations').select2();\n    $('#pAllocation').select2();\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/servers/view/database.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    服务器 — {{ $server->name }}: 数据库\n@endsection\n\n@section('content-header')\n    <h1>{{ $server->name }}<small>管理服务器数据库.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.servers') }}\">服务器</a></li>\n        <li><a href=\"{{ route('admin.servers.view', $server->id) }}\">{{ $server->name }}</a></li>\n        <li class=\"active\">数据库</li>\n    </ol>\n@endsection\n\n@section('content')\n@include('admin.servers.partials.navigation')\n<div class=\"row\">\n    <div class=\"col-sm-7\">\n        <div class=\"alert alert-info\">\n            数据库密码可以在 <a href=\"/server/{{ $server->uuidShort }}/databases\">访问此服务器</a> 用户界面时查看.\n        </div>\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">活跃的数据库</h3>\n            </div>\n            <div class=\"box-body table-responsible no-padding\">\n                <table class=\"table table-hover\">\n                    <tr>\n                        <th>数据库</th>\n                        <th>用户名</th>\n                        <th>连接白名单</th>\n                        <th>域名</th>\n                        <th>最大连接数</th>\n                        <th></th>\n                    </tr>\n                    @foreach($server->databases as $database)\n                        <tr>\n                            <td>{{ $database->database }}</td>\n                            <td>{{ $database->username }}</td>\n                            <td>{{ $database->remote }}</td>\n                            <td><code>{{ $database->host->host }}:{{ $database->host->port }}</code></td>\n                            @if($database->max_connections != null)\n                                <td>{{ $database->max_connections }}</td>\n                            @else\n                                <td>无限制</td>\n                            @endif\n                            <td class=\"text-center\">\n                                <button data-action=\"reset-password\" data-id=\"{{ $database->id }}\" class=\"btn btn-xs btn-primary\"><i class=\"fa fa-refresh\"></i></button>\n                                <button data-action=\"remove\" data-id=\"{{ $database->id }}\" class=\"btn btn-xs btn-danger\"><i class=\"fa fa-trash\"></i></button>\n                            </td>\n                        </tr>\n                    @endforeach\n                </table>\n            </div>\n        </div>\n    </div>\n    <div class=\"col-sm-5\">\n        <div class=\"box box-success\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">创建新数据库</h3>\n            </div>\n            <form action=\"{{ route('admin.servers.view.database', $server->id) }}\" method=\"POST\">\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"pDatabaseHostId\" class=\"control-label\">数据库主机</label>\n                        <select id=\"pDatabaseHostId\" name=\"database_host_id\" class=\"form-control\">\n                            @foreach($hosts as $host)\n                                <option value=\"{{ $host->id }}\">{{ $host->name }}</option>\n                            @endforeach\n                        </select>\n                        <p class=\"text-muted small\">选择应在其上创建此数据库的主机数据库服务器.</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pDatabaseName\" class=\"control-label\">数据库</label>\n                        <div class=\"input-group\">\n                            <span class=\"input-group-addon\">s{{ $server->id }}_</span>\n                            <input id=\"pDatabaseName\" type=\"text\" name=\"database\" class=\"form-control\" placeholder=\"数据库名\" />\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pRemote\" class=\"control-label\">连接白名单</label>\n                        <input id=\"pRemote\" type=\"text\" name=\"remote\" class=\"form-control\" value=\"%\" />\n                        <p class=\"text-muted small\">这应该反映允许连接的 IP 地址。使用标准 MySQL 表示法。如果不确定请填写 <code>%</code>。</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pmax_connections\" class=\"control-label\">最大连接数</label>\n                        <input id=\"pmax_connections\" type=\"text\" name=\"max_connections\" class=\"form-control\"/>\n                        <p class=\"text-muted small\">这应该反映从该用户到数据库的最大并发连接数。留空表示无限制。</p>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <p class=\"text-muted small no-margin\">该数据库的用户名和密码将在此表单提交后随机生成。</p>\n                    <input type=\"submit\" class=\"btn btn-sm btn-success pull-right\" value=\"创建数据库\" />\n                </div>\n            </form>\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    $('#pDatabaseHost').select2();\n    $('[data-action=\"remove\"]').click(function (event) {\n        event.preventDefault();\n        var self = $(this);\n        swal({\n            title: '',\n            type: 'warning',\n            text: '您确定要删除此数据库吗？ 没有回头路，所有数据将立即被删除。',\n            showCancelButton: true,\n            confirmButtonText: '删除',\n            confirmButtonColor: '#d9534f',\n            closeOnConfirm: false,\n            showLoaderOnConfirm: true,\n        }, function () {\n            $.ajax({\n                method: 'DELETE',\n                url: '/admin/servers/view/{{ $server->id }}/database/' + self.data('id') + '/delete',\n                headers: { 'X-CSRF-TOKEN': $('meta[name=\"_token\"]').attr('content') },\n            }).done(function () {\n                self.parent().parent().slideUp();\n                swal.close();\n            }).fail(function (jqXHR) {\n                console.error(jqXHR);\n                swal({\n                    type: 'error',\n                    title: '呜呼!',\n                    text: (typeof jqXHR.responseJSON.error !== 'undefined') ? jqXHR.responseJSON.error : '处理此请求时发生错误，此请求无法继续处理！'\n                });\n            });\n        });\n    });\n    $('[data-action=\"reset-password\"]').click(function (e) {\n        e.preventDefault();\n        var block = $(this);\n        $(this).addClass('disabled').find('i').addClass('fa-spin');\n        $.ajax({\n            type: 'PATCH',\n            url: '/admin/servers/view/{{ $server->id }}/database',\n            headers: { 'X-CSRF-TOKEN': $('meta[name=\"_token\"]').attr('content') },\n            data: { database: $(this).data('id') },\n        }).done(function (data) {\n            swal({\n                type: 'success',\n                title: '',\n                text: '数据库密码已重置.',\n            });\n        }).fail(function(jqXHR, textStatus, errorThrown) {\n            console.error(jqXHR);\n            var error = '处理此请求时发生错误，此请求无法继续处理！';\n            if (typeof jqXHR.responseJSON !== 'undefined' && typeof jqXHR.responseJSON.error !== 'undefined') {\n                error = jqXHR.responseJSON.error;\n            }\n            swal({\n                type: 'error',\n                title: '呜呼!',\n                text: error\n            });\n        }).always(function () {\n            block.removeClass('disabled').find('i').removeClass('fa-spin');\n        });\n    });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/servers/view/delete.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    服务器 — {{ $server->name }}: 删除\n@endsection\n\n@section('content-header')\n    <h1>{{ $server->name }}<small>将此服务器从面板上删除.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.servers') }}\">服务器</a></li>\n        <li><a href=\"{{ route('admin.servers.view', $server->id) }}\">{{ $server->name }}</a></li>\n        <li class=\"active\">删除</li>\n    </ol>\n@endsection\n\n@section('content')\n@include('admin.servers.partials.navigation')\n<div class=\"row\">\n    <div class=\"col-md-6\">\n        <div class=\"box\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">安全删除服务器</h3>\n            </div>\n            <div class=\"box-body\">\n                <p>此操作将尝试从面板和守护程序中删除服务器。如果其中任何流程一个报告错误，则该操作将被取消.</p>\n                <p class=\"text-danger small\">删除服务器是不可逆的操作. <strong>所有服务器数据</strong> (包括文件和用户) 都会被删除.</p>\n            </div>\n            <div class=\"box-footer\">\n                <form id=\"deleteform\" action=\"{{ route('admin.servers.view.delete', $server->id) }}\" method=\"POST\">\n                    {!! csrf_field() !!}\n                    <button id=\"deletebtn\" class=\"btn btn-danger\">安全删除此服务器</button>\n                </form>\n            </div>\n        </div>\n    </div>\n    <div class=\"col-md-6\">\n        <div class=\"box box-danger\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">强制删除服务器</h3>\n            </div>\n            <div class=\"box-body\">\n                <p>此操作将尝试从面板和守护程序中删除服务器。如果守护进程没有响应，或报告错误，删除操作将继续.</p>\n                <p class=\"text-danger small\">删除服务器是不可逆的操作. <strong>所有服务器数据</strong> (包括文件和用户) 都会被删除. 如果出现错误报告，此方法可能会在您的守护程序服务器上留下垃圾文件.</p>\n            </div>\n            <div class=\"box-footer\">\n                <form id=\"forcedeleteform\" action=\"{{ route('admin.servers.view.delete', $server->id) }}\" method=\"POST\">\n                    {!! csrf_field() !!}\n                    <input type=\"hidden\" name=\"force_delete\" value=\"1\" />\n                    <button id=\"forcedeletebtn\"\" class=\"btn btn-danger\">强制删除此服务器</button>\n                </form>\n            </div>\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    $('#deletebtn').click(function (event) {\n        event.preventDefault();\n        swal({\n            title: '',\n            type: 'warning',\n            text: '您确定要删除此服务器吗？ 没有回头路，所有数据将立即被删除。',\n            showCancelButton: true,\n            confirmButtonText: '删除',\n            confirmButtonColor: '#d9534f',\n            closeOnConfirm: false\n        }, function () {\n            $('#deleteform').submit()\n        });\n    });\n\n    $('#forcedeletebtn').click(function (event) {\n        event.preventDefault();\n        swal({\n            title: '',\n            type: 'warning',\n            text: '您确定要删除此服务器吗？ 没有回头路，所有数据将立即被删除。',\n            showCancelButton: true,\n            confirmButtonText: '删除',\n            confirmButtonColor: '#d9534f',\n            closeOnConfirm: false\n        }, function () {\n            $('#forcedeleteform').submit()\n        });\n    });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/servers/view/details.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    服务器 — {{ $server->name }}: 详细信息\n@endsection\n\n@section('content-header')\n    <h1>{{ $server->name }}<small>编辑此服务器的详细信息，包括所有者和容器.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.servers') }}\">服务器</a></li>\n        <li><a href=\"{{ route('admin.servers.view', $server->id) }}\">{{ $server->name }}</a></li>\n        <li class=\"active\">详细信息</li>\n    </ol>\n@endsection\n\n@section('content')\n@include('admin.servers.partials.navigation')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">基础信息</h3>\n            </div>\n            <form action=\"{{ route('admin.servers.view.details', $server->id) }}\" method=\"POST\">\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"name\" class=\"control-label\">服务器名称 <span class=\"field-required\"></span></label>\n                        <input type=\"text\" name=\"name\" value=\"{{ old('name', $server->name) }}\" class=\"form-control\" />\n                        <p class=\"text-muted small\">字符限制: <code>a-zA-Z0-9_-</code> 和 <code>[空格]</code>.</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"external_id\" class=\"control-label\">外部 ID</label>\n                        <input type=\"text\" name=\"external_id\" value=\"{{ old('external_id', $server->external_id) }}\" class=\"form-control\" />\n                        <p class=\"text-muted small\">留空以不为此服务器分配外部标识符。外部 ID 对于此服务器应该是唯一的，并且未被任何其他服务器使用。</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"pUserId\" class=\"control-label\">服务器所有者 <span class=\"field-required\"></span></label>\n                        <select name=\"owner_id\" class=\"form-control\" id=\"pUserId\">\n                            <option value=\"{{ $server->owner_id }}\" selected>{{ $server->user->email }}</option>\n                        </select>\n                        <p class=\"text-muted small\">您可以通过将此字段更改为与此系统上的其他用途匹配的电子邮箱来更改此服务器的所有者。如果您这样做，将自动生成一个新的守护程序安全令牌。</p>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"description\" class=\"control-label\">服务器描述</label>\n                        <textarea name=\"description\" rows=\"3\" class=\"form-control\">{{ old('description', $server->description) }}</textarea>\n                        <p class=\"text-muted small\">服务器的简介.</p>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    {!! method_field('PATCH') !!}\n                    <input type=\"submit\" class=\"btn btn-sm btn-primary\" value=\"更新详细信息\" />\n                </div>\n            </form>\n        </div>\n    </div>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>\n    function escapeHtml(str) {\n        var div = document.createElement('div');\n        div.appendChild(document.createTextNode(str));\n        return div.innerHTML;\n    }\n\n    $('#pUserId').select2({\n        ajax: {\n            url: '/admin/users/accounts.json',\n            dataType: 'json',\n            delay: 250,\n            data: function (params) {\n                return {\n                    filter: { email: params.term },\n                    page: params.page,\n                };\n            },\n            processResults: function (data, params) {\n                return { results: data };\n            },\n            cache: true,\n        },\n        escapeMarkup: function (markup) { return markup; },\n        minimumInputLength: 2,\n        templateResult: function (data) {\n            if (data.loading) return escapeHtml(data.text);\n\n            return '<div class=\"user-block\"> \\\n                <img class=\"img-circle img-bordered-xs\" src=\"https://cravatar.cn/avatar/' + escapeHtml(data.md5) + '?s=120\" alt=\"User Image\"> \\\n                <span class=\"username\"> \\\n                    <a href=\"#\">' + escapeHtml(data.name_first) + ' ' + escapeHtml(data.name_last) +'</a> \\\n                </span> \\\n                <span class=\"description\"><strong>' + escapeHtml(data.email) + '</strong> - ' + escapeHtml(data.username) + '</span> \\\n            </div>';\n        },\n        templateSelection: function (data) {\n            if (typeof data.name_first === 'undefined') {\n                data = {\n                    md5: '{{ md5(strtolower($server->user->email)) }}',\n                    name_first: '{{ $server->user->name_first }}',\n                    name_last: '{{ $server->user->name_last }}',\n                    email: '{{ $server->user->email }}',\n                    id: {{ $server->owner_id }}\n                };\n            }\n\n            return '<div> \\\n                <span> \\\n                    <img class=\"img-rounded img-bordered-xs\" src=\"https://cravatar.cn/avatar/' + escapeHtml(data.md5) + '?s=120\" style=\"height:28px;margin-top:-4px;\" alt=\"User Image\"> \\\n                </span> \\\n                <span style=\"padding-left:5px;\"> \\\n                    ' + escapeHtml(data.name_first) + ' ' + escapeHtml(data.name_last) + ' (<strong>' + escapeHtml(data.email) + '</strong>) \\\n                </span> \\\n            </div>';\n        }\n    });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/servers/view/index.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    服务器 — {{ $server->name }}\n@endsection\n\n@section('content-header')\n    <h1>{{ $server->name }}<small>{{ str_limit($server->description) }}</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.servers') }}\">服务器</a></li>\n        <li class=\"active\">{{ $server->name }}</li>\n    </ol>\n@endsection\n\n@section('content')\n@include('admin.servers.partials.navigation')\n<div class=\"row\">\n    <div class=\"col-sm-8\">\n        <div class=\"row\">\n            <div class=\"col-xs-12\">\n                <div class=\"box box-primary\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">信息</h3>\n                    </div>\n                    <div class=\"box-body table-responsive no-padding\">\n                        <table class=\"table table-hover\">\n                            <tr>\n                                <td>内部 ID</td>\n                                <td><code>{{ $server->id }}</code></td>\n                            </tr>\n                            <tr>\n                                <td>外部 ID</td>\n                                @if(is_null($server->external_id))\n                                    <td><span class=\"label label-default\">未设置</span></td>\n                                @else\n                                    <td><code>{{ $server->external_id }}</code></td>\n                                @endif\n                            </tr>\n                            <tr>\n                                <td>UUID / Docker 镜像 ID</td>\n                                <td><code>{{ $server->uuid }}</code></td>\n                            </tr>\n                            <tr>\n                                <td>使用预设</td>\n                                <td>\n                                    <a href=\"{{ route('admin.nests.view', $server->nest_id) }}\">{{ $server->nest->name }}</a> ::\n                                    <a href=\"{{ route('admin.nests.egg.view', $server->egg_id) }}\">{{ $server->egg->name }}</a>\n                                </td>\n                            </tr>\n                            <tr>\n                                <td>服务器名称</td>\n                                <td>{{ $server->name }}</td>\n                            </tr>\n                            <tr>\n                                <td>CPU 限制</td>\n                                <td>\n                                    @if($server->cpu === 0)\n                                        <code>无限制</code>\n                                    @else\n                                        <code>{{ $server->cpu }}%</code>\n                                    @endif\n                                </td>\n                            </tr>\n                            <tr>\n                                <td>CPU 核心</td>\n                                <td>\n                                    @if($server->threads != null)\n                                        <code>{{ $server->threads }}</code>\n                                    @else\n                                        <span class=\"label label-default\">未设置</span>\n                                    @endif\n                                </td>\n                            </tr>\n                            <tr>\n                                <td>内存使用</td>\n                                <td>\n                                    @if($server->memory === 0)\n                                        <code>无限制</code>\n                                    @else\n                                        <code>{{ $server->memory }}MiB</code>\n                                    @endif\n                                    /\n                                    @if($server->swap === 0)\n                                        <code data-toggle=\"tooltip\" data-placement=\"top\" title=\"交换空间\">未设置</code>\n                                    @elseif($server->swap === -1)\n                                        <code data-toggle=\"tooltip\" data-placement=\"top\" title=\"交换空间\">无限制</code>\n                                    @else\n                                        <code data-toggle=\"tooltip\" data-placement=\"top\" title=\"交换空间\"> {{ $server->swap }}MiB</code>\n                                    @endif\n                                </td>\n                            </tr>\n                            <tr>\n                                <td>存储空间</td>\n                                <td>\n                                    @if($server->disk === 0)\n                                        <code>无限制</code>\n                                    @else\n                                        <code>{{ $server->disk }}MiB</code>\n                                    @endif\n                                </td>\n                            </tr>\n                            <tr>\n                                <td>IO 优先级</td>\n                                <td><code>{{ $server->io }}</code></td>\n                            </tr>\n                            <tr>\n                                <td>默认连接</td>\n                                <td><code>{{ $server->allocation->ip }}:{{ $server->allocation->port }}</code></td>\n                            </tr>\n                            <tr>\n                                <td>连接别名</td>\n                                <td>\n                                    @if($server->allocation->alias !== $server->allocation->ip)\n                                        <code>{{ $server->allocation->alias }}:{{ $server->allocation->port }}</code>\n                                    @else\n                                        <span class=\"label label-default\">未分配</span>\n                                    @endif\n                                </td>\n                            </tr>\n                        </table>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n    <div class=\"col-sm-4\">\n        <div class=\"box box-primary\">\n            <div class=\"box-body\" style=\"padding-bottom: 0px;\">\n                <div class=\"row\">\n                    @if($server->isSuspended())\n                        <div class=\"col-sm-12\">\n                            <div class=\"small-box bg-yellow\">\n                                <div class=\"inner\">\n                                    <h3 class=\"no-margin\">已冻结</h3>\n                                </div>\n                            </div>\n                        </div>\n                    @endif\n                    @if(!$server->isInstalled())\n                        <div class=\"col-sm-12\">\n                            <div class=\"small-box {{ (! $server->isInstalled()) ? 'bg-blue' : 'bg-maroon' }}\">\n                                <div class=\"inner\">\n                                    <h3 class=\"no-margin\">{{ (! $server->isInstalled()) ? '正在安装' : '安装失败' }}</h3>\n                                </div>\n                            </div>\n                        </div>\n                    @endif\n                    <div class=\"col-sm-12\">\n                        <div class=\"small-box bg-gray\">\n                            <div class=\"inner\">\n                                <h3>{{ str_limit($server->user->username, 16) }}</h3>\n                                <p>服务器所有者</p>\n                            </div>\n                            <div class=\"icon\"><i class=\"fa fa-user\"></i></div>\n                            <a href=\"{{ route('admin.users.view', $server->user->id) }}\" class=\"small-box-footer\">\n                                详情 <i class=\"fa fa-arrow-circle-right\"></i>\n                            </a>\n                        </div>\n                    </div>\n                    <div class=\"col-sm-12\">\n                        <div class=\"small-box bg-gray\">\n                            <div class=\"inner\">\n                                <h3>{{ str_limit($server->node->name, 16) }}</h3>\n                                <p>服务器节点</p>\n                            </div>\n                            <div class=\"icon\"><i class=\"fa fa-codepen\"></i></div>\n                            <a href=\"{{ route('admin.nodes.view', $server->node->id) }}\" class=\"small-box-footer\">\n                                详情 <i class=\"fa fa-arrow-circle-right\"></i>\n                            </a>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </div>\n</div>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/servers/view/manage.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    服务器 — {{ $server->name }}: 管理\n@endsection\n\n@section('content-header')\n    <h1>{{ $server->name }}<small>控制此服务器的其他操作.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.servers') }}\">服务器</a></li>\n        <li><a href=\"{{ route('admin.servers.view', $server->id) }}\">{{ $server->name }}</a></li>\n        <li class=\"active\">管理</li>\n    </ol>\n@endsection\n\n@section('content')\n    @include('admin.servers.partials.navigation')\n    <div class=\"row equal-height\">\n        <div class=\"col-sm-4\">\n            <div class=\"box box-danger\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">重新安装服务器</h3>\n                </div>\n                <div class=\"box-body\">\n                    <p>此操作将使用预设的安装脚本重新安装服务器。<strong>危险!</strong> 这可能会覆盖服务器数据。</p>\n                </div>\n                <div class=\"box-footer\">\n                    @if($server->isInstalled())\n                        <form action=\"{{ route('admin.servers.view.manage.reinstall', $server->id) }}\" method=\"POST\">\n                            {!! csrf_field() !!}\n                            <button type=\"submit\" class=\"btn btn-danger\">重新安装服务器</button>\n                        </form>\n                    @else\n                        <button class=\"btn btn-danger disabled\">服务器必须正常安装之后才可重新安装</button>\n                    @endif\n                </div>\n            </div>\n        </div>\n        <div class=\"col-sm-4\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">安装状态</h3>\n                </div>\n                <div class=\"box-body\">\n                    <p>如果您需要将安装状态从已卸载更改为已安装，反之亦然，您可以使用下面的按钮进行操作。</p>\n                </div>\n                <div class=\"box-footer\">\n                    <form action=\"{{ route('admin.servers.view.manage.toggle', $server->id) }}\" method=\"POST\">\n                        {!! csrf_field() !!}\n                        <button type=\"submit\" class=\"btn btn-primary\">更改安装状态</button>\n                    </form>\n                </div>\n            </div>\n        </div>\n\n        @if(! $server->isSuspended())\n            <div class=\"col-sm-4\">\n                <div class=\"box box-warning\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">冻结服务器</h3>\n                    </div>\n                    <div class=\"box-body\">\n                        <p>这将暂停服务器，停止任何正在运行的进程，并立即阻止用户访问他们的文件或通过面板或 API 管理服务器.</p>\n                    </div>\n                    <div class=\"box-footer\">\n                        <form action=\"{{ route('admin.servers.view.manage.suspension', $server->id) }}\" method=\"POST\">\n                            {!! csrf_field() !!}\n                            <input type=\"hidden\" name=\"action\" value=\"suspend\" />\n                            <button type=\"submit\" class=\"btn btn-warning @if(! is_null($server->transfer)) disabled @endif\">冻结服务器</button>\n                        </form>\n                    </div>\n                </div>\n            </div>\n        @else\n            <div class=\"col-sm-4\">\n                <div class=\"box box-success\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">撤销冻结服务器</h3>\n                    </div>\n                    <div class=\"box-body\">\n                        <p>这将撤销服务器的冻结，且用户将有权限管理此服务器.</p>\n                    </div>\n                    <div class=\"box-footer\">\n                        <form action=\"{{ route('admin.servers.view.manage.suspension', $server->id) }}\" method=\"POST\">\n                            {!! csrf_field() !!}\n                            <input type=\"hidden\" name=\"action\" value=\"unsuspend\" />\n                            <button type=\"submit\" class=\"btn btn-success\">撤销冻结服务器</button>\n                        </form>\n                    </div>\n                </div>\n            </div>\n        @endif\n\n        @if(is_null($server->transfer))\n            <div class=\"col-sm-4\">\n                <div class=\"box box-success\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">转移服务器</h3>\n                    </div>\n                    <div class=\"box-body\">\n                        <p>\n                            将此服务器转移到连接到此面板的另一个节点.\n                            <strong>警告!</strong> 此功能未完全测试可能有BUG.\n                        </p>\n                    </div>\n\n                    <div class=\"box-footer\">\n                        @if($canTransfer)\n                            <button class=\"btn btn-success\" data-toggle=\"modal\" data-target=\"#transferServerModal\">转移服务器</button>\n                        @else\n                            <button class=\"btn btn-success disabled\">转移服务器</button>\n                            <p style=\"padding-top: 1rem;\">转移一台服务器需要在您的面板上配置多个节点。</p>\n                        @endif\n                    </div>\n                </div>\n            </div>\n        @else\n            <div class=\"col-sm-4\">\n                <div class=\"box box-success\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">转移服务器</h3>\n                    </div>\n                    <div class=\"box-body\">\n                        <p>\n                            此服务器正在转移至另一个节点.\n                            转移开始于 <strong>{{ $server->transfer->created_at }}</strong>\n                        </p>\n                    </div>\n\n                    <div class=\"box-footer\">\n                        <button class=\"btn btn-success disabled\">转移服务器</button>\n                    </div>\n                </div>\n            </div>\n        @endif\n    </div>\n\n    <div class=\"modal fade\" id=\"transferServerModal\" tabindex=\"-1\" role=\"dialog\">\n        <div class=\"modal-dialog\" role=\"document\">\n            <div class=\"modal-content\">\n                <form action=\"{{ route('admin.servers.view.manage.transfer', $server->id) }}\" method=\"POST\">\n                    <div class=\"modal-header\">\n                        <button type=\"button\" class=\"close\" data-dismiss=\"modal\" aria-label=\"Close\"><span aria-hidden=\"true\">&times;</span></button>\n                        <h4 class=\"modal-title\">转移服务器</h4>\n                    </div>\n\n                    <div class=\"modal-body\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-12\">\n                                <label for=\"pNodeId\">节点</label>\n                                <select name=\"node_id\" id=\"pNodeId\" class=\"form-control\">\n                                    @foreach($locations as $location)\n                                        <optgroup label=\"{{ $location->long }} ({{ $location->short }})\">\n                                            @foreach($location->nodes as $node)\n\n                                                @if($node->id != $server->node_id)\n                                                    <option value=\"{{ $node->id }}\"\n                                                            @if($location->id === old('location_id')) selected @endif\n                                                    >{{ $node->name }}</option>\n                                                @endif\n\n                                            @endforeach\n                                        </optgroup>\n                                    @endforeach\n                                </select>\n                                <p class=\"small text-muted no-margin\">该服务器将被转移到的节点.</p>\n                            </div>\n\n                            <div class=\"form-group col-md-12\">\n                                <label for=\"pAllocation\">默认分配</label>\n                                <select name=\"allocation_id\" id=\"pAllocation\" class=\"form-control\"></select>\n                                <p class=\"small text-muted no-margin\">将分配给此服务器的主要分配。</p>\n                            </div>\n\n                            <div class=\"form-group col-md-12\">\n                                <label for=\"pAllocationAdditional\">额外分配</label>\n                                <select name=\"allocation_additional[]\" id=\"pAllocationAdditional\" class=\"form-control\" multiple></select>\n                                <p class=\"small text-muted no-margin\">将分配给此服务器的额外分配。</p>\n                            </div>\n                        </div>\n                    </div>\n\n                    <div class=\"modal-footer\">\n                        {!! csrf_field() !!}\n                        <button type=\"button\" class=\"btn btn-default btn-sm pull-left\" data-dismiss=\"modal\">取消</button>\n                        <button type=\"submit\" class=\"btn btn-success btn-sm\">确定</button>\n                    </div>\n                </form>\n            </div>\n        </div>\n    </div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    {!! Theme::js('vendor/lodash/lodash.js') !!}\n\n    @if($canTransfer)\n        {!! Theme::js('js/admin/server/transfer.js') !!}\n    @endif\n@endsection\n"
  },
  {
    "path": "resources/views/admin/servers/view/mounts.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    服务器 — {{ $server->name }}: 挂载\n@endsection\n\n@section('content-header')\n    <h1>{{ $server->name }}<small>管理服务器的挂载.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.servers') }}\">服务器</a></li>\n        <li><a href=\"{{ route('admin.servers.view', $server->id) }}\">{{ $server->name }}</a></li>\n        <li class=\"active\">挂载</li>\n    </ol>\n@endsection\n\n@section('content')\n    @include('admin.servers.partials.navigation')\n\n    <div class=\"row\">\n        <div class=\"col-sm-12\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">可用的挂载点</h3>\n                </div>\n\n                <div class=\"box-body table-responsible no-padding\">\n                    <table class=\"table table-hover\">\n                        <tr>\n                            <th>ID</th>\n                            <th>名称</th>\n                            <th>来源路径</th>\n                            <th>挂载路径</th>\n                            <th>状态</th>\n                            <th></th>\n                        </tr>\n\n                        @foreach ($mounts as $mount)\n                            <tr>\n                                <td class=\"col-sm-1 middle\"><code>{{ $mount->id }}</code></td>\n                                <td class=\"middle\"><a href=\"{{ route('admin.mounts.view', $mount->id) }}\">{{ $mount->name }}</a></td>\n                                <td class=\"middle\"><code>{{ $mount->source }}</code></td>\n                                <td class=\"col-sm-2 middle\"><code>{{ $mount->target }}</code></td>\n\n                                @if (! in_array($mount->id, $server->mounts->pluck('id')->toArray()))\n                                    <td class=\"col-sm-2 middle\">\n                                        <span class=\"label label-primary\">已卸载</span>\n                                    </td>\n\n                                    <td class=\"col-sm-1 middle\">\n                                        <form action=\"{{ route('admin.servers.view.mounts.store', [ 'server' => $server->id ]) }}\" method=\"POST\">\n                                            {!! csrf_field() !!}\n                                            <input type=\"hidden\" value=\"{{ $mount->id }}\" name=\"mount_id\" />\n                                            <button type=\"submit\" class=\"btn btn-xs btn-success\"><i class=\"fa fa-plus\"></i></button>\n                                        </form>\n                                    </td>\n                                @else\n                                    <td class=\"col-sm-2 middle\">\n                                        <span class=\"label label-success\">已挂载</span>\n                                    </td>\n\n                                    <td class=\"col-sm-1 middle\">\n                                        <form action=\"{{ route('admin.servers.view.mounts.delete', [ 'server' => $server->id, 'mount' => $mount->id ]) }}\" method=\"POST\">\n                                            @method('DELETE')\n                                            {!! csrf_field() !!}\n\n                                            <button type=\"submit\" class=\"btn btn-xs btn-danger\"><i class=\"fa fa-times\"></i></button>\n                                        </form>\n                                    </td>\n                                @endif\n                            </tr>\n                        @endforeach\n                    </table>\n                </div>\n            </div>\n        </div>\n    </div>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/servers/view/startup.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    服务器 — {{ $server->name }}: 启动\n@endsection\n\n@section('content-header')\n    <h1>{{ $server->name }}<small>管理启动命令与其变量.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.servers') }}\">服务器</a></li>\n        <li><a href=\"{{ route('admin.servers.view', $server->id) }}\">{{ $server->name }}</a></li>\n        <li class=\"active\">启动</li>\n    </ol>\n@endsection\n\n@section('content')\n@include('admin.servers.partials.navigation')\n<form action=\"{{ route('admin.servers.view.startup', $server->id) }}\" method=\"POST\">\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">启动命令编辑</h3>\n                </div>\n                <div class=\"box-body\">\n                    <label for=\"pStartup\" class=\"form-label\">启动命令</label>\n                    <input id=\"pStartup\" name=\"startup\" class=\"form-control\" type=\"text\" value=\"{{ old('startup', $server->startup) }}\" />\n                    <p class=\"small text-muted\">于此编辑服务器的启动命令. 默认可用的变量有: <code>@{{SERVER_MEMORY}}</code>, <code>@{{SERVER_IP}}</code>, 和 <code>@{{SERVER_PORT}}</code>.</p>\n                </div>\n                <div class=\"box-body\">\n                    <label for=\"pDefaultStartupCommand\" class=\"form-label\">默认启动命令</label>\n                    <input id=\"pDefaultStartupCommand\" class=\"form-control\" type=\"text\" readonly />\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <button type=\"submit\" class=\"btn btn-primary btn-sm pull-right\">保存编辑</button>\n                </div>\n            </div>\n        </div>\n    </div>\n    <div class=\"row\">\n        <div class=\"col-md-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">预设设置</h3>\n                </div>\n                <div class=\"box-body row\">\n                    <div class=\"col-xs-12\">\n                        <p class=\"small text-danger\">\n                            更改以下任何值将导致服务器处理重新安装命令。服务器将停止运行，然后重启。\n                            如果您不希望服务程序运行，请确保选中底部的框。\n                        </p>\n                        <p class=\"small text-danger\">\n                            <strong>在许多情况下，这是一种破坏性操作。此服务器将立即停止，以便此操作继续进行.</strong>\n                        </p>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"pNestId\">预设组</label>\n                        <select name=\"nest_id\" id=\"pNestId\" class=\"form-control\">\n                            @foreach($nests as $nest)\n                                <option value=\"{{ $nest->id }}\"\n                                    @if($nest->id === $server->nest_id)\n                                        selected\n                                    @endif\n                                >{{ $nest->name }}</option>\n                            @endforeach\n                        </select>\n                        <p class=\"small text-muted no-margin\">选择服务器使用的预设组.</p>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <label for=\"pEggId\">预设</label>\n                        <select name=\"egg_id\" id=\"pEggId\" class=\"form-control\"></select>\n                        <p class=\"small text-muted no-margin\">选择将为该服务器提供处理数据的预设.</p>\n                    </div>\n                    <div class=\"form-group col-xs-12\">\n                        <div class=\"checkbox checkbox-primary no-margin-bottom\">\n                            <input id=\"pSkipScripting\" name=\"skip_scripts\" type=\"checkbox\" value=\"1\" @if($server->skip_scripts) checked @endif />\n                            <label for=\"pSkipScripting\" class=\"strong\">跳过预设安装脚本</label>\n                        </div>\n                        <p class=\"small text-muted no-margin\">如果选定的预设附加了安装脚本，则该程序将在安装期间运行。如果您想跳过此步骤，请选中此框.</p>\n                    </div>\n                </div>\n            </div>\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">Docker 镜像设置</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"pDockerImage\">镜像</label>\n                        <select id=\"pDockerImage\" name=\"docker_image\" class=\"form-control\"></select>\n                        <input id=\"pDockerImageCustom\" name=\"custom_docker_image\" value=\"{{ old('custom_docker_image') }}\" class=\"form-control\" placeholder=\"或输入自定义镜像...\" style=\"margin-top:1rem\"/>\n                        <p class=\"small text-muted no-margin\">这是将用于运行此服务器的 Docker 映像。从下拉列表中选择镜像或在上面的文本字段中输入自定义镜像.</p>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-md-6\">\n            <div class=\"row\" id=\"appendVariablesTo\"></div>\n        </div>\n    </div>\n</form>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    {!! Theme::js('vendor/lodash/lodash.js') !!}\n    <script>\n    function escapeHtml(str) {\n        var div = document.createElement('div');\n        div.appendChild(document.createTextNode(str));\n        return div.innerHTML;\n    }\n\n    $(document).ready(function () {\n        $('#pEggId').select2({placeholder: '选择预设'}).on('change', function () {\n            var selectedEgg = _.isNull($(this).val()) ? $(this).find('option').first().val() : $(this).val();\n            var parentChain = _.get(Pterodactyl.nests, $(\"#pNestId\").val());\n            var objectChain = _.get(parentChain, 'eggs.' + selectedEgg);\n\n            const images = _.get(objectChain, 'docker_images', [])\n            $('#pDockerImage').html('');\n            const keys = Object.keys(images);\n            for (let i = 0; i < keys.length; i++) {\n                let opt = document.createElement('option');\n                opt.value = images[keys[i]];\n                opt.innerText = keys[i] + \" (\" + images[keys[i]] + \")\";\n                if (objectChain.id === parseInt(Pterodactyl.server.egg_id) && Pterodactyl.server.image == opt.value) {\n                    opt.selected = true\n                }\n                $('#pDockerImage').append(opt);\n            }\n            $('#pDockerImage').on('change', function () {\n                $('#pDockerImageCustom').val('');\n            })\n\n            if (objectChain.id === parseInt(Pterodactyl.server.egg_id)) {\n                if ($('#pDockerImage').val() != Pterodactyl.server.image) {\n                    $('#pDockerImageCustom').val(Pterodactyl.server.image);\n                }\n            }\n\n            if (!_.get(objectChain, 'startup', false)) {\n                $('#pDefaultStartupCommand').val(_.get(parentChain, 'startup', '错误：未定义启动项！'));\n            } else {\n                $('#pDefaultStartupCommand').val(_.get(objectChain, 'startup'));\n            }\n\n            $('#appendVariablesTo').html('');\n            $.each(_.get(objectChain, 'variables', []), function (i, item) {\n                var setValue = _.get(Pterodactyl.server_variables, item.env_variable, item.default_value);\n                var isRequired = (item.required === 1) ? '<span class=\"label label-danger\">必填</span> ' : '';\n                var dataAppend = ' \\\n                    <div class=\"col-xs-12\"> \\\n                        <div class=\"box\"> \\\n                            <div class=\"box-header with-border\"> \\\n                                <h3 class=\"box-title\">' + isRequired + escapeHtml(item.name) + '</h3> \\\n                            </div> \\\n                            <div class=\"box-body\"> \\\n                                <input name=\"environment[' + escapeHtml(item.env_variable) + ']\" class=\"form-control\" type=\"text\" id=\"egg_variable_' + escapeHtml(item.env_variable) + '\" /> \\\n                                <p class=\"no-margin small text-muted\">' + escapeHtml(item.description) + '</p> \\\n                            </div> \\\n                            <div class=\"box-footer\"> \\\n                                <p class=\"no-margin text-muted small\"><strong>启动命令变量:</strong> <code>' + escapeHtml(item.env_variable) + '</code></p> \\\n                                <p class=\"no-margin text-muted small\"><strong>输入规则:</strong> <code>' + escapeHtml(item.rules) + '</code></p> \\\n                            </div> \\\n                        </div> \\\n                    </div>';\n                $('#appendVariablesTo').append(dataAppend).find('#egg_variable_' + item.env_variable).val(setValue);\n            });\n        });\n\n        $('#pNestId').select2({placeholder: '选择预设组'}).on('change', function () {\n            $('#pEggId').html('').select2({\n                data: $.map(_.get(Pterodactyl.nests, $(this).val() + '.eggs', []), function (item) {\n                    return {\n                        id: item.id,\n                        text: item.name,\n                    };\n                }),\n            });\n\n            if (_.isObject(_.get(Pterodactyl.nests, $(this).val() + '.eggs.' + Pterodactyl.server.egg_id))) {\n                $('#pEggId').val(Pterodactyl.server.egg_id);\n            }\n\n            $('#pEggId').change();\n        }).change();\n    });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/settings/advanced.blade.php",
    "content": "@extends('layouts.admin')\n@include('partials/admin.settings.nav', ['activeTab' => 'advanced'])\n\n@section('title')\n    高级设置\n@endsection\n\n@section('content-header')\n    <h1>高级设置<small>翼龙面板的高级设置.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">设置</li>\n    </ol>\n@endsection\n\n@section('content')\n    @yield('settings::nav')\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <form action=\"\" method=\"POST\">\n                <div class=\"box\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">reCAPTCHA</h3>\n                    </div>\n                    <div class=\"box-body\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">状态</label>\n                                <div>\n                                    <select class=\"form-control\" name=\"recaptcha:enabled\">\n                                        <option value=\"true\">启用</option>\n                                        <option value=\"false\" @if(old('recaptcha:enabled', config('recaptcha.enabled')) == '0') selected @endif>禁用</option>\n                                    </select>\n                                    <p class=\"text-muted small\">如果启用，登录表单和密码重置表单将进行静默验证码检查，并在需要时显示可见验证码.</p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">Site Key</label>\n                                <div>\n                                    <input type=\"text\" required class=\"form-control\" name=\"recaptcha:website_key\" value=\"{{ old('recaptcha:website_key', config('recaptcha.website_key')) }}\">\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">Secret Key</label>\n                                <div>\n                                    <input type=\"text\" required class=\"form-control\" name=\"recaptcha:secret_key\" value=\"{{ old('recaptcha:secret_key', config('recaptcha.secret_key')) }}\">\n                                    <p class=\"text-muted small\">用于您的网站与 Google 之间的通信。</p>\n                                </div>\n                            </div>\n                        </div>\n                        @if($showRecaptchaWarning)\n                            <div class=\"row\">\n                                <div class=\"col-xs-12\">\n                                    <div class=\"alert alert-warning no-margin\">\n                                        您当前正在使用随此面板提供的 reCAPTCHA 密钥。为了提高安全性，建议专门为此网站 <a href=\"https://www.google.com/recaptcha/admin\">生成新的 reCAPTCHA 密钥</a>.\n                                    </div>\n                                </div>\n                            </div>\n                        @endif\n                    </div>\n                </div>\n                <div class=\"box\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">ICP许可证</h3>\n                    </div>\n                    <div class=\"box-body\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">状态</label>\n                                <div>\n                                    <select class=\"form-control\" name=\"icp:enabled\">\n                                        <option value=\"true\">启用</option>\n                                        <option value=\"false\" @if(old('icp:enabled', config('icp.enabled')) == '0') selected @endif>禁用</option>\n                                    </select>\n                                    <p class=\"text-muted small\">如果启用，会在登录页显示备案号以便在中国运营站点.</p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">ICP备案号</label>\n                                <div>\n                                    <input type=\"text\" class=\"form-control\" name=\"icp:record\" value=\"{{ old('icp:record', config('icp.record')) }}\">\n                                    <p class=\"text-muted small\">中国网络服务需要的网站经营许可证，如果您的站点架设在中国，您应向服务提供商申请 ICP 许可证并填写此参数.</p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">公安备案号</label>\n                                <div>\n                                    <input type=\"text\" class=\"form-control\" name=\"icp:security_record\" value=\"{{ old('icp:security_record', config('icp.security_record')) }}\">\n                                    <p class=\"text-muted small\">该参数可不填，但网站只要是放在中国境内（大陆地区），您就应该公安备案并填写此参数.</p>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">HTTP 连接</h3>\n                    </div>\n                    <div class=\"box-body\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-6\">\n                                <label class=\"control-label\">连接超时</label>\n                                <div>\n                                    <input type=\"number\" required class=\"form-control\" name=\"pterodactyl:guzzle:connect_timeout\" value=\"{{ old('pterodactyl:guzzle:connect_timeout', config('pterodactyl.guzzle.connect_timeout')) }}\">\n                                    <p class=\"text-muted small\">在引发错误提示之前等待连接完成的时间（以秒为单位）.</p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-6\">\n                                <label class=\"control-label\">请求超时</label>\n                                <div>\n                                    <input type=\"number\" required class=\"form-control\" name=\"pterodactyl:guzzle:timeout\" value=\"{{ old('pterodactyl:guzzle:timeout', config('pterodactyl.guzzle.timeout')) }}\">\n                                    <p class=\"text-muted small\">在引发错误提示之前等待请求完成的时间（以秒为单位）.</p>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">自动分配创建</h3>\n                    </div>\n                    <div class=\"box-body\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">状态</label>\n                                <div>\n                                    <select class=\"form-control\" name=\"pterodactyl:client_features:allocations:enabled\">\n                                        <option value=\"false\">禁用</option>\n                                        <option value=\"true\" @if(old('pterodactyl:client_features:allocations:enabled', config('pterodactyl.client_features.allocations.enabled'))) selected @endif>启用</option>\n                                    </select>\n                                    <p class=\"text-muted small\">如果启用，用户将可以选择通过前端自动为其服务器创建新分配.</p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">起始端口</label>\n                                <div>\n                                    <input type=\"number\" class=\"form-control\" name=\"pterodactyl:client_features:allocations:range_start\" value=\"{{ old('pterodactyl:client_features:allocations:range_start', config('pterodactyl.client_features.allocations.range_start')) }}\">\n                                    <p class=\"text-muted small\">可自动分配范围内的起始端口.</p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">结束端口</label>\n                                <div>\n                                    <input type=\"number\" class=\"form-control\" name=\"pterodactyl:client_features:allocations:range_end\" value=\"{{ old('pterodactyl:client_features:allocations:range_end', config('pterodactyl.client_features.allocations.range_end')) }}\">\n                                    <p class=\"text-muted small\">可自动分配范围内的结束端口.</p>\n                                </div>\n                            </div>\n                        </div>\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">连续端口创建</label>\n                                <div>\n                                    <select class=\"form-control\" name=\"pterodactyl:client_features:allocations:consecutive_enabled\">\n                                        <option value=\"false\">禁用</option>\n                                        <option value=\"true\" @if(old('pterodactyl:client_features:allocations:consecutive_enabled', config('pterodactyl.client_features.allocations.consecutive_enabled'))) selected @endif>启用</option>\n                                    </select>\n                                    <p class=\"text-muted small\">如果启用，用户在创建新分配时可以选择申请多个连续端口.</p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">最大连续端口数</label>\n                                <div>\n                                    <input type=\"number\" class=\"form-control\" name=\"pterodactyl:client_features:allocations:consecutive_limit\" min=\"2\" max=\"10\" value=\"{{ old('pterodactyl:client_features:allocations:consecutive_limit', config('pterodactyl.client_features.allocations.consecutive_limit', 3)) }}\">\n                                    <p class=\"text-muted small\">用户一次最多可申请的连续端口数量（2-10）.</p>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box\">\n                    <div class=\"box-header with-border\">\n                        <h3 class=\"box-title\">允许前台切换预设</h3>\n                    </div>\n                    <div class=\"box-body\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-6\">\n                                <label class=\"control-label\">模式</label>\n                                <div>\n                                    <select class=\"form-control\" name=\"pterodactyl:client_features:egg_change:mode\">\n                                        <option value=\"disabled\" @if(old('pterodactyl:client_features:egg_change:mode', config('pterodactyl.client_features.egg_change.mode')) === 'disabled') selected @endif>禁用</option>\n                                        <option value=\"egg_only\" @if(old('pterodactyl:client_features:egg_change:mode', config('pterodactyl.client_features.egg_change.mode')) === 'egg_only') selected @endif>只允许切换预设</option>\n                                        <option value=\"both\" @if(old('pterodactyl:client_features:egg_change:mode', config('pterodactyl.client_features.egg_change.mode')) === 'both') selected @endif>允许切换预设和预设组</option>\n                                    </select>\n                                    <p class=\"text-muted small\">\n                                        控制拥有相应权限的用户在服务器启动设置页面中可执行的切换操作：<br>\n                                        <strong>只允许切换预设</strong>：显示预设组（仅作为过滤器）和预设下拉框，手动选择预设后应用；<br>\n                                        <strong>允许切换预设和预设组</strong>：同时显示两个下拉框，切换预设组时自动应用第一个预设，也可手动切换预设。\n                                    </p>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box box-primary\">\n                    <div class=\"box-footer\">\n                        {{ csrf_field() }}\n                        <button type=\"submit\" name=\"_method\" value=\"PATCH\" class=\"btn btn-sm btn-primary pull-right\">保存</button>\n                    </div>\n                </div>\n            </form>\n        </div>\n    </div>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/settings/index.blade.php",
    "content": "@extends('layouts.admin')\n@include('partials/admin.settings.nav', ['activeTab' => 'basic'])\n\n@section('title')\n    设置\n@endsection\n\n@section('content-header')\n    <h1>面板设置<small>配置面板.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">设置</li>\n    </ol>\n@endsection\n\n@section('content')\n    @yield('settings::nav')\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">面板设置</h3>\n                </div>\n                <form action=\"{{ route('admin.settings') }}\" method=\"POST\">\n                    <div class=\"box-body\">\n                        <div class=\"row\">\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">公司名称</label>\n                                <div>\n                                    <input type=\"text\" class=\"form-control\" name=\"app:name\" value=\"{{ old('app:name', config('app.name')) }}\" />\n                                    <p class=\"text-muted\"><small>这是整个面板和发送给用户的电子邮箱中使用的名称.</small></p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">要求动态口令认证登录</label>\n                                <div>\n                                    <div class=\"btn-group\" data-toggle=\"buttons\">\n                                        @php\n                                            $level = old('pterodactyl:auth:2fa_required', config('pterodactyl.auth.2fa_required'));\n                                        @endphp\n                                        <label class=\"btn btn-primary @if ($level == 0) active @endif\">\n                                            <input type=\"radio\" name=\"pterodactyl:auth:2fa_required\" autocomplete=\"off\" value=\"0\" @if ($level == 0) checked @endif> 不要求\n                                        </label>\n                                        <label class=\"btn btn-primary @if ($level == 1) active @endif\">\n                                            <input type=\"radio\" name=\"pterodactyl:auth:2fa_required\" autocomplete=\"off\" value=\"1\" @if ($level == 1) checked @endif> 仅限管理员\n                                        </label>\n                                        <label class=\"btn btn-primary @if ($level == 2) active @endif\">\n                                            <input type=\"radio\" name=\"pterodactyl:auth:2fa_required\" autocomplete=\"off\" value=\"2\" @if ($level == 2) checked @endif> 所有用户\n                                        </label>\n                                    </div>\n                                    <p class=\"text-muted\"><small>如果启用，任何属于所选分组的帐户都需要启用动态口令认证才能使用面板.</small></p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">默认语言</label>\n                                <div>\n                                    <select name=\"app:locale\" class=\"form-control\">\n                                        @foreach($languages as $key => $value)\n                                            <option value=\"{{ $key }}\" @if(config('app.locale') === $key) selected @endif>{{ $value }}</option>\n                                        @endforeach\n                                    </select>\n                                    <p class=\"text-muted\"><small>此功能需要面板的首位用户设置为相应的语言，返回这里并再按一次保存，即可同步</small></p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">标题LOGO</label>\n                                <div>\n                                    <input type=\"text\" class=\"form-control\" name=\"logo:title\" value=\"{{ old('logo:title', config('logo.title')) }}\" />\n                                    <p class=\"text-muted\"><small>这是在首页左上角文字的LOGO，如果不填则默认为\"公司名称\".</small></p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">网站LOGO</label>\n                                <div>\n                                    <input type=\"text\" class=\"form-control\" name=\"logo:favicon\" value=\"{{ old('logo:favicon', config('logo.favicon')) }}\" />\n                                    <p class=\"text-muted\"><small>这是站点的 favicon 图标，不填则为默认LOGO.</small></p>\n                                </div>\n                            </div>\n                            <div class=\"form-group col-md-4\">\n                                <label class=\"control-label\">登录页LOGO</label>\n                                <div>\n                                    <input type=\"text\" class=\"form-control\" name=\"logo:auth\" value=\"{{ old('logo:auth', config('logo.auth')) }}\" />\n                                    <p class=\"text-muted\"><small>这是面板登录页展示的LOGO，不填则为默认LOGO.(此功能并未完善)</small></p>\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                    <div class=\"box-footer\">\n                        {!! csrf_field() !!}\n                        <button type=\"submit\" name=\"_method\" value=\"PATCH\" class=\"btn btn-sm btn-primary pull-right\">保存</button>\n                    </div>\n                </form>\n            </div>\n        </div>\n    </div>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/settings/mail.blade.php",
    "content": "@extends('layouts.admin')\n@include('partials/admin.settings.nav', ['activeTab' => 'mail'])\n\n@section('title')\n    邮件设置\n@endsection\n\n@section('content-header')\n    <h1>邮件设置<small>配置翼龙面板如何发送邮件.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">设置</li>\n    </ol>\n@endsection\n\n@section('content')\n    @yield('settings::nav')\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">邮件设置</h3>\n                </div>\n                @if($disabled)\n                    <div class=\"box-body\">\n                        <div class=\"row\">\n                            <div class=\"col-xs-12\">\n                                <div class=\"alert alert-info no-margin-bottom\">\n                                    此接口仅限于使用 SMTP 作为邮件驱动程序的实例。请使用 <code>php artisan p:environment:mail</code> 指令更新你的邮件设置, 或更改 <code>MAIL_DRIVER=smtp</code> 于你的 .env 环境文件内.\n                                </div>\n                            </div>\n                        </div>\n                    </div>\n                @else\n                    <form>\n                        <div class=\"box-body\">\n                            <div class=\"row\">\n                                <div class=\"form-group col-md-6\">\n                                    <label class=\"control-label\">SMTP 主机</label>\n                                    <div>\n                                        <input required type=\"text\" class=\"form-control\" name=\"mail:mailers:smtp:host\" value=\"{{ old('mail:mailers:smtp:host', config('mail.mailers.smtp.host')) }}\" />\n                                        <p class=\"text-muted small\">输入发送邮件的 SMTP 服务器地址.</p>\n                                    </div>\n                                </div>\n                                <div class=\"form-group col-md-2\">\n                                    <label class=\"control-label\">SMTP 主机端口</label>\n                                    <div>\n                                        <input required type=\"number\" class=\"form-control\" name=\"mail:mailers:smtp:port\" value=\"{{ old('mail:mailers:smtp:port', config('mail.mailers.smtp.port')) }}\" />\n                                        <p class=\"text-muted small\">输入发送邮件的 SMTP 服务器端口.</p>\n                                    </div>\n                                </div>\n                                <div class=\"form-group col-md-4\">\n                                    <label class=\"control-label\">加密方式</label>\n                                    <div>\n                                        @php\n                                            $encryption = old('mail:mailers:smtp:encryption', config('mail.mailers.smtp.encryption'));\n                                        @endphp\n                                        <select name=\"mail:mailers:smtp:encryption\" class=\"form-control\">\n                                            <option value=\"\" @if($encryption === '') selected @endif>无</option>\n                                            <option value=\"tls\" @if($encryption === 'tls') selected @endif>传输层安全 (TLS)</option>\n                                            <option value=\"ssl\" @if($encryption === 'ssl') selected @endif>安全链路层 (SSL)</option>\n                                        </select>\n                                        <p class=\"text-muted small\">选择发送邮件时使用的加密类型.</p>\n                                    </div>\n                                </div>\n                                <div class=\"form-group col-md-6\">\n                                    <label class=\"control-label\">用户名 <span class=\"field-optional\"></span></label>\n                                    <div>\n                                        <input type=\"text\" class=\"form-control\" name=\"mail:mailers:smtp:username\" value=\"{{ old('mail:mailers:smtp:username', config('mail.mailers.smtp.username')) }}\" />\n                                        <p class=\"text-muted small\">连接到 SMTP 服务器时使用的用户名.</p>\n                                    </div>\n                                </div>\n                                <div class=\"form-group col-md-6\">\n                                    <label class=\"control-label\">密码 <span class=\"field-optional\"></span></label>\n                                    <div>\n                                        <input type=\"password\" class=\"form-control\" name=\"mail:mailers:smtp:password\"/>\n                                        <p class=\"text-muted small\">与 SMTP 用户名一起使用的密码。留空以继续使用现有密码。要将密码设置为空值，请输入 <code>!e</code> .</p>\n                                    </div>\n                                </div>\n                            </div>\n                            <div class=\"row\">\n                                <hr />\n                                <div class=\"form-group col-md-6\">\n                                    <label class=\"control-label\">邮件发件人</label>\n                                    <div>\n                                        <input required type=\"email\" class=\"form-control\" name=\"mail:from:address\" value=\"{{ old('mail:from:address', config('mail.from.address')) }}\" />\n                                        <p class=\"text-muted small\">输入所有外发电子邮件都来自的电子邮箱地址.</p>\n                                    </div>\n                                </div>\n                                <div class=\"form-group col-md-6\">\n                                    <label class=\"control-label\">发件人名称 <span class=\"field-optional\"></span></label>\n                                    <div>\n                                        <input type=\"text\" class=\"form-control\" name=\"mail:from:name\" value=\"{{ old('mail:from:name', config('mail.from.name')) }}\" />\n                                        <p class=\"text-muted small\">邮件发件人名称.</p>\n                                    </div>\n                                </div>\n                            </div>\n                        </div>\n                        <div class=\"box-footer\">\n                            {{ csrf_field() }}\n                            <div class=\"pull-right\">\n                                <button type=\"button\" id=\"testButton\" class=\"btn btn-sm btn-success\">测试</button>\n                                <button type=\"button\" id=\"saveButton\" class=\"btn btn-sm btn-primary\">保存</button>\n                            </div>\n                        </div>\n                    </form>\n                @endif\n            </div>\n        </div>\n    </div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n\n    <script>\n        function saveSettings() {\n            return $.ajax({\n                method: 'PATCH',\n                url: '/admin/settings/mail',\n                contentType: 'application/json',\n                data: JSON.stringify({\n                    'mail:mailers:smtp:host': $('input[name=\"mail:mailers:smtp:host\"]').val(),\n                    'mail:mailers:smtp:port': $('input[name=\"mail:mailers:smtp:port\"]').val(),\n                    'mail:mailers:smtp:encryption': $('select[name=\"mail:mailers:smtp:encryption\"]').val(),\n                    'mail:mailers:smtp:username': $('input[name=\"mail:mailers:smtp:username\"]').val(),\n                    'mail:mailers:smtp:password': $('input[name=\"mail:mailers:smtp:password\"]').val(),\n                    'mail:from:address': $('input[name=\"mail:from:address\"]').val(),\n                    'mail:from:name': $('input[name=\"mail:from:name\"]').val()\n                }),\n                headers: { 'X-CSRF-Token': $('input[name=\"_token\"]').val() }\n            }).fail(function (jqXHR) {\n                showErrorDialog(jqXHR, 'save');\n            });\n        }\n\n        function testSettings() {\n            swal({\n                type: 'info',\n                title: '测试邮件设置',\n                text: '点击 \"测试\" 开始测试.',\n                showCancelButton: true,\n                confirmButtonText: '测试',\n                closeOnConfirm: false,\n                showLoaderOnConfirm: true\n            }, function () {\n                $.ajax({\n                    method: 'POST',\n                    url: '/admin/settings/mail/test',\n                    headers: { 'X-CSRF-TOKEN': $('input[name=\"_token\"]').val() }\n                }).fail(function (jqXHR) {\n                    showErrorDialog(jqXHR, 'test');\n                }).done(function () {\n                    swal({\n                        title: '成功',\n                        text: '测试信息已发送成功.',\n                        type: 'success'\n                    });\n                });\n            });\n        }\n\n        function saveAndTestSettings() {\n            saveSettings().done(testSettings);\n        }\n\n        function showErrorDialog(jqXHR, verb) {\n            console.error(jqXHR);\n            var errorText = '';\n            if (!jqXHR.responseJSON) {\n                errorText = jqXHR.responseText;\n            } else if (jqXHR.responseJSON.error) {\n                errorText = jqXHR.responseJSON.error;\n            } else if (jqXHR.responseJSON.errors) {\n                $.each(jqXHR.responseJSON.errors, function (i, v) {\n                    if (v.detail) {\n                        errorText += v.detail + ' ';\n                    }\n                });\n            }\n\n            swal({\n                title: '呜呼!',\n                text: '尝试执行时出错 ' + verb + ' 邮箱设置: ' + errorText,\n                type: 'error'\n            });\n        }\n\n        $(document).ready(function () {\n            $('#testButton').on('click', saveAndTestSettings);\n            $('#saveButton').on('click', function () {\n                saveSettings().done(function () {\n                    swal({\n                        title: '成功',\n                        text: '邮件设置已成功更新，队列工作器已重新启动以应用这些更改.',\n                        type: 'success'\n                    });\n                });\n            });\n        });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/users/index.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    用户列表\n@endsection\n\n@section('content-header')\n    <h1>用户<small>此系统上所有注册用户。</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li class=\"active\">用户</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <div class=\"col-xs-12\">\n        <div class=\"box box-primary\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">用户列表</h3>\n                <div class=\"box-tools search01\">\n                    <form action=\"{{ route('admin.users') }}\" method=\"GET\">\n                        <div class=\"input-group input-group-sm\">\n                            <input type=\"text\" name=\"filter[email]\" class=\"form-control pull-right\" value=\"{{ request()->input('filter.email') }}\" placeholder=\"搜索\">\n                            <div class=\"input-group-btn\">\n                                <button type=\"submit\" class=\"btn btn-default\"><i class=\"fa fa-search\"></i></button>\n                                <a href=\"{{ route('admin.users.new') }}\"><button type=\"button\" class=\"btn btn-sm btn-primary\" style=\"border-radius: 0 3px 3px 0;margin-left:-1px;\">新建</button></a>\n                            </div>\n                        </div>\n                    </form>\n                </div>\n            </div>\n            <div class=\"box-body table-responsive no-padding\">\n                <table class=\"table table-hover\">\n                    <thead>\n                        <tr>\n                            <th>ID</th>\n                            <th>电子邮箱地址</th>\n                            <th>姓名</th>\n                            <th>用户名</th>\n                            <th class=\"text-center\">动态口令认证</th>\n                            <th class=\"text-center\"><span data-toggle=\"tooltip\" data-placement=\"top\" title=\"此用户作为所有者的服务器。\">拥有的服务器</span></th>\n                            <th class=\"text-center\"><span data-toggle=\"tooltip\" data-placement=\"top\" title=\"此用户作为子用户可以访问的服务器。\">可访问</span></th>\n                            <th></th>\n                        </tr>\n                    </thead>\n                    <tbody>\n                        @foreach ($users as $user)\n                            <tr class=\"align-middle\">\n                                <td><code>{{ $user->id }}</code></td>\n                                <td><a href=\"{{ route('admin.users.view', $user->id) }}\">{{ $user->email }}</a> @if($user->root_admin)<i class=\"fa fa-star text-yellow\"></i>@endif</td>\n                                <td>{{ $user->name_last }}, {{ $user->name_first }}</td>\n                                <td>{{ $user->username }}</td>\n                                <td class=\"text-center\">\n                                    @if($user->use_totp)\n                                        <i class=\"fa fa-lock text-green\"></i>\n                                    @else\n                                        <i class=\"fa fa-unlock text-red\"></i>\n                                    @endif\n                                </td>\n                                <td class=\"text-center\">\n                                    <a href=\"{{ route('admin.servers', ['filter[owner_id]' => $user->id]) }}\">{{ $user->servers_count }}</a>\n                                </td>\n                                <td class=\"text-center\">{{ $user->subuser_of_count }}</td>\n                                <td class=\"text-center\"><img src=\"https://cravatar.cn/avatar/{{ md5(strtolower($user->email)) }}?s=100\" style=\"height:20px;\" class=\"img-circle\" /></td>\n                            </tr>\n                        @endforeach\n                    </tbody>\n                </table>\n            </div>\n            @if($users->hasPages())\n                <div class=\"box-footer with-border\">\n                    <div class=\"col-md-12 text-center\">{!! $users->appends(['query' => Request::input('query')])->render() !!}</div>\n                </div>\n            @endif\n        </div>\n    </div>\n</div>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/users/new.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    创建用户\n@endsection\n\n@section('content-header')\n    <h1>创建用户<small>创建一个新用户.</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.users') }}\">用户</a></li>\n        <li class=\"active\">新建</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <form method=\"post\">\n        <div class=\"col-md-6\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">身份</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"email\" class=\"control-label\">电子邮箱地址</label>\n                        <div>\n                            <input type=\"text\" autocomplete=\"off\" name=\"email\" value=\"{{ old('email') }}\" class=\"form-control\" />\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"username\" class=\"control-label\">用户名</label>\n                        <div>\n                            <input type=\"text\" autocomplete=\"off\" name=\"username\" value=\"{{ old('username') }}\" class=\"form-control\" />\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"name_last\" class=\"control-label\">姓</label>\n                        <div>\n                            <input type=\"text\" autocomplete=\"off\" name=\"name_last\" value=\"{{ old('name_last') }}\" class=\"form-control\" />\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"name_first\" class=\"control-label\">名</label>\n                        <div>\n                            <input type=\"text\" autocomplete=\"off\" name=\"name_first\" value=\"{{ old('name_first') }}\" class=\"form-control\" />\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"control-label\">默认语言</label>\n                        <div>\n                            <select name=\"language\" class=\"form-control\">\n                                @foreach($languages as $key => $value)\n                                    <option value=\"{{ $key }}\" @if(config('app.locale') === $key) selected @endif>{{ $value }}</option>\n                                @endforeach\n                            </select>\n                            <p class=\"text-muted\"><small>用户使用的默认语言.</small></p>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    <input type=\"submit\" value=\"创建用户\" class=\"btn btn-success btn-sm\">\n                </div>\n            </div>\n        </div>\n        <div class=\"col-md-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">权限</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"form-group col-md-12\">\n                        <label for=\"root_admin\" class=\"control-label\">系统管理员</label>\n                        <div>\n                            <select name=\"root_admin\" class=\"form-control\">\n                                <option value=\"0\">@lang('strings.no')</option>\n                                <option value=\"1\">@lang('strings.yes')</option>\n                            </select>\n                            <p class=\"text-muted\"><small>将此设置为“是”为用户提供完全的管理访问权限.</small></p>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-md-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">密码</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"alert alert-info\">\n                        <p>提供用户密码是可选的。新用户将会收到电子邮件并提示用户在首次登录时创建密码。如果此处提供了密码，您将需要找到一种不同的方法将其提供给用户.</p>\n                    </div>\n                    <div id=\"gen_pass\" class=\" alert alert-success\" style=\"display:none;margin-bottom: 10px;\"></div>\n                    <div class=\"form-group\">\n                        <label for=\"pass\" class=\"control-label\">密码</label>\n                        <div>\n                            <input type=\"password\" name=\"password\" class=\"form-control\" />\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </form>\n</div>\n@endsection\n\n@section('footer-scripts')\n    @parent\n    <script>$(\"#gen_pass_bttn\").click(function (event) {\n            event.preventDefault();\n            $.ajax({\n                type: \"GET\",\n                url: \"/password-gen/12\",\n                headers: {\n                    'X-CSRF-TOKEN': '{{ csrf_token() }}'\n               },\n                success: function(data) {\n                    $(\"#gen_pass\").html('<strong>生成的密码：</strong> ' + data).slideDown();\n                    $('input[name=\"password\"], input[name=\"password_confirmation\"]').val(data);\n                    return false;\n                }\n            });\n            return false;\n        });\n    </script>\n@endsection\n"
  },
  {
    "path": "resources/views/admin/users/view.blade.php",
    "content": "@extends('layouts.admin')\n\n@section('title')\n    管理用户: {{ $user->username }}\n@endsection\n\n@section('content-header')\n    <h1>{{ $user->name_last }} {{ $user->name_first}}<small>{{ $user->username }}</small></h1>\n    <ol class=\"breadcrumb\">\n        <li><a href=\"{{ route('admin.index') }}\">管理</a></li>\n        <li><a href=\"{{ route('admin.users') }}\">用户</a></li>\n        <li class=\"active\">{{ $user->username }}</li>\n    </ol>\n@endsection\n\n@section('content')\n<div class=\"row\">\n    <form action=\"{{ route('admin.users.view', $user->id) }}\" method=\"post\">\n        <div class=\"col-md-6\">\n            <div class=\"box box-primary\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">身份</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"email\" class=\"control-label\">电子邮箱地址</label>\n                        <div>\n                            <input type=\"email\" name=\"email\" value=\"{{ $user->email }}\" class=\"form-control form-autocomplete-stop\">\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"registered\" class=\"control-label\">用户名</label>\n                        <div>\n                            <input type=\"text\" name=\"username\" value=\"{{ $user->username }}\" class=\"form-control form-autocomplete-stop\">\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"registered\" class=\"control-label\">姓</label>\n                        <div>\n                            <input type=\"text\" name=\"name_last\" value=\"{{ $user->name_last }}\" class=\"form-control form-autocomplete-stop\">\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label for=\"registered\" class=\"control-label\">名</label>\n                        <div>\n                            <input type=\"text\" name=\"name_first\" value=\"{{ $user->name_first }}\" class=\"form-control form-autocomplete-stop\">\n                        </div>\n                    </div>\n                    <div class=\"form-group\">\n                        <label class=\"control-label\">默认语言</label>\n                        <div>\n                            <select name=\"language\" class=\"form-control\">\n                                @foreach($languages as $key => $value)\n                                    <option value=\"{{ $key }}\" @if($user->language === $key) selected @endif>{{ $value }}</option>\n                                @endforeach\n                            </select>\n                            <p class=\"text-muted\"><small>用户使用的默认语言.</small></p>\n                        </div>\n                    </div>\n                </div>\n                <div class=\"box-footer\">\n                    {!! csrf_field() !!}\n                    {!! method_field('PATCH') !!}\n                    <input type=\"submit\" value=\"更新用户\" class=\"btn btn-primary btn-sm\">\n                </div>\n            </div>\n        </div>\n        <div class=\"col-md-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">密码</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"alert alert-success\" style=\"display:none;margin-bottom:10px;\" id=\"gen_pass\"></div>\n                    <div class=\"form-group no-margin-bottom\">\n                        <label for=\"password\" class=\"control-label\">密码 <span class=\"field-optional\"></span></label>\n                        <div>\n                            <input type=\"password\" id=\"password\" name=\"password\" class=\"form-control form-autocomplete-stop\">\n                            <p class=\"text-muted small\">留空以保持此用户的密码相同。如果更改密码，用户将不会收到任何通知.</p>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n        <div class=\"col-md-6\">\n            <div class=\"box\">\n                <div class=\"box-header with-border\">\n                    <h3 class=\"box-title\">权限</h3>\n                </div>\n                <div class=\"box-body\">\n                    <div class=\"form-group\">\n                        <label for=\"root_admin\" class=\"control-label\">系统管理员</label>\n                        <div>\n                            <select name=\"root_admin\" class=\"form-control\">\n                                <option value=\"0\">@lang('strings.no')</option>\n                                <option value=\"1\" {{ $user->root_admin ? 'selected=\"selected\"' : '' }}>@lang('strings.yes')</option>\n                            </select>\n                            <p class=\"text-muted\"><small>将此设置为“是”为用户提供完全的管理访问权限.</small></p>\n                        </div>\n                    </div>\n                </div>\n            </div>\n        </div>\n    </form>\n    <div class=\"col-xs-12\">\n        <div class=\"box box-danger\">\n            <div class=\"box-header with-border\">\n                <h3 class=\"box-title\">删除此用户</h3>\n            </div>\n            <div class=\"box-body\">\n                <p class=\"no-margin\">必须没有与此帐户关联的服务器才能删除此用户.</p>\n            </div>\n            <div class=\"box-footer\">\n                <form action=\"{{ route('admin.users.view', $user->id) }}\" method=\"POST\">\n                    {!! csrf_field() !!}\n                    {!! method_field('DELETE') !!}\n                    <input id=\"delete\" type=\"submit\" class=\"btn btn-sm btn-danger pull-right\" {{ $user->servers->count() < 1 ?: 'disabled' }} value=\"删除此用户\" />\n                </form>\n            </div>\n        </div>\n    </div>\n</div>\n@endsection\n"
  },
  {
    "path": "resources/views/layouts/admin.blade.php",
    "content": "<!DOCTYPE html>\n<html>\n    <head>\n        <meta charset=\"utf-8\">\n        <meta http-equiv=\"X-UA-Compatible\" content=\"IE=edge\">\n        <title>{{ config('app.name', 'Pterodactyl') }} - @yield('title')</title>\n        <meta content=\"width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no\" name=\"viewport\">\n        <meta name=\"_token\" content=\"{{ csrf_token() }}\">\n\n        <link rel=\"apple-touch-icon\" sizes=\"180x180\" href=\"/favicons/apple-touch-icon.png\">\n        <link rel=\"icon\" type=\"image/png\" href=\"/favicons/favicon-32x32.png\" sizes=\"32x32\">\n        <link rel=\"icon\" type=\"image/png\" href=\"/favicons/favicon-16x16.png\" sizes=\"16x16\">\n        <link rel=\"manifest\" href=\"/favicons/manifest.json\">\n        <link rel=\"mask-icon\" href=\"/favicons/safari-pinned-tab.svg\" color=\"#bc6e3c\">\n        <link rel=\"shortcut icon\" href=\"/favicons/favicon.ico\">\n        <meta name=\"msapplication-config\" content=\"/favicons/browserconfig.xml\">\n        <meta name=\"theme-color\" content=\"#0e4688\">\n\n        @include('layouts.scripts')\n\n        @section('scripts')\n            {!! Theme::css('vendor/select2/select2.min.css?t={cache-version}') !!}\n            {!! Theme::css('vendor/bootstrap/bootstrap.min.css?t={cache-version}') !!}\n            {!! Theme::css('vendor/adminlte/admin.min.css?t={cache-version}') !!}\n            {!! Theme::css('vendor/adminlte/colors/skin-blue.min.css?t={cache-version}') !!}\n            {!! Theme::css('vendor/sweetalert/sweetalert.min.css?t={cache-version}') !!}\n            {!! Theme::css('vendor/animate/animate.min.css?t={cache-version}') !!}\n            {!! Theme::css('css/pterodactyl.css?t={cache-version}') !!}\n            <link rel=\"stylesheet\" href=\"https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css\">\n            <link rel=\"stylesheet\" href=\"https://cdnjs.cloudflare.com/ajax/libs/ionicons/2.0.1/css/ionicons.min.css\">\n\n            <!--[if lt IE 9]>\n            <script src=\"https://oss.maxcdn.com/html5shiv/3.7.3/html5shiv.min.js\"></script>\n            <script src=\"https://oss.maxcdn.com/respond/1.4.2/respond.min.js\"></script>\n            <![endif]-->\n        @show\n    </head>\n    <body class=\"hold-transition skin-blue fixed sidebar-mini\">\n        <div class=\"wrapper\">\n            <header class=\"main-header\">\n                <a href=\"{{ route('index') }}\" class=\"logo\">\n                    <span>{{ config('app.name', 'Pterodactyl') }}</span>\n                </a>\n                <nav class=\"navbar navbar-static-top\">\n                    <a href=\"#\" class=\"sidebar-toggle\" data-toggle=\"push-menu\" role=\"button\">\n                        <span class=\"sr-only\">切换导航</span>\n                        <span class=\"icon-bar\"></span>\n                        <span class=\"icon-bar\"></span>\n                        <span class=\"icon-bar\"></span>\n                    </a>\n                    <div class=\"navbar-custom-menu\">\n                        <ul class=\"nav navbar-nav\">\n                            <li class=\"user-menu\">\n                                <a href=\"{{ route('account') }}\">\n                                    <img src=\"https://cravatar.cn/avatar/{{ md5(strtolower(Auth::user()->email)) }}?s=160\" class=\"user-image\" alt=\"User Image\">\n                                    <span class=\"hidden-xs\">{{ Auth::user()->name_last }} {{ Auth::user()->name_first }}</span>\n                                </a>\n                            </li>\n                            <li>\n                                <li><a href=\"{{ route('index') }}\" data-toggle=\"tooltip\" data-placement=\"bottom\" title=\"退出管理员后台\"><i class=\"fa fa-server\"></i></a></li>\n                            </li>\n                            <li>\n                                <li><a href=\"{{ route('auth.logout') }}\" id=\"logoutButton\" data-toggle=\"tooltip\" data-placement=\"bottom\" title=\"登出\"><i class=\"fa fa-sign-out\"></i></a></li>\n                            </li>\n                        </ul>\n                    </div>\n                </nav>\n            </header>\n            <aside class=\"main-sidebar\">\n                <section class=\"sidebar\">\n                    <ul class=\"sidebar-menu\">\n                        <li class=\"header\">基础管理</li>\n                        <li class=\"{{ Route::currentRouteName() !== 'admin.index' ?: 'active' }}\">\n                            <a href=\"{{ route('admin.index') }}\">\n                                <i class=\"fa fa-home\"></i> <span>概况</span>\n                            </a>\n                        </li>\n                        <li class=\"{{ ! starts_with(Route::currentRouteName(), 'admin.settings') ?: 'active' }}\">\n                            <a href=\"{{ route('admin.settings')}}\">\n                                <i class=\"fa fa-wrench\"></i> <span>设置</span>\n                            </a>\n                        </li>\n                        <li class=\"{{ ! starts_with(Route::currentRouteName(), 'admin.api') ?: 'active' }}\">\n                            <a href=\"{{ route('admin.api.index')}}\">\n                                <i class=\"fa fa-gamepad\"></i> <span>应用 API</span>\n                            </a>\n                        </li>\n                        <li class=\"header\">高级管理</li>\n                        <li class=\"{{ ! starts_with(Route::currentRouteName(), 'admin.databases') ?: 'active' }}\">\n                            <a href=\"{{ route('admin.databases') }}\">\n                                <i class=\"fa fa-database\"></i> <span>数据库</span>\n                            </a>\n                        </li>\n                        <li class=\"{{ ! starts_with(Route::currentRouteName(), 'admin.locations') ?: 'active' }}\">\n                            <a href=\"{{ route('admin.locations') }}\">\n                                <i class=\"fa fa-globe\"></i> <span>地域</span>\n                            </a>\n                        </li>\n                        <li class=\"{{ ! starts_with(Route::currentRouteName(), 'admin.nodes') ?: 'active' }}\">\n                            <a href=\"{{ route('admin.nodes') }}\">\n                                <i class=\"fa fa-sitemap\"></i> <span>节点</span>\n                            </a>\n                        </li>\n                        <li class=\"{{ ! starts_with(Route::currentRouteName(), 'admin.servers') ?: 'active' }}\">\n                            <a href=\"{{ route('admin.servers') }}\">\n                                <i class=\"fa fa-server\"></i> <span>服务器</span>\n                            </a>\n                        </li>\n                        <li class=\"{{ ! starts_with(Route::currentRouteName(), 'admin.users') ?: 'active' }}\">\n                            <a href=\"{{ route('admin.users') }}\">\n                                <i class=\"fa fa-users\"></i> <span>用户</span>\n                            </a>\n                        </li>\n                        <li class=\"header\">服务管理</li>\n                        <li class=\"{{ ! starts_with(Route::currentRouteName(), 'admin.mounts') ?: 'active' }}\">\n                            <a href=\"{{ route('admin.mounts') }}\">\n                                <i class=\"fa fa-magic\"></i> <span>挂载</span>\n                            </a>\n                        </li>\n                        <li class=\"{{ ! starts_with(Route::currentRouteName(), 'admin.nests') ?: 'active' }}\">\n                            <a href=\"{{ route('admin.nests') }}\">\n                                <i class=\"fa fa-th-large\"></i> <span>预设组</span>\n                            </a>\n                        </li>\n                    </ul>\n                </section>\n            </aside>\n            <div class=\"content-wrapper\">\n                <section class=\"content-header\">\n                    @yield('content-header')\n                </section>\n                <section class=\"content\">\n                    <div class=\"row\">\n                        <div class=\"col-xs-12\">\n                            @if (count($errors) > 0)\n                                <div class=\"alert alert-danger\">\n                                    验证提供的数据时出错.<br><br>\n                                    <ul>\n                                        @foreach ($errors->all() as $error)\n                                            <li>{{ $error }}</li>\n                                        @endforeach\n                                    </ul>\n                                </div>\n                            @endif\n                            @foreach (Alert::getMessages() as $type => $messages)\n                                @foreach ($messages as $message)\n                                    <div class=\"alert alert-{{ $type }} alert-dismissable\" role=\"alert\">\n                                        {{ $message }}\n                                    </div>\n                                @endforeach\n                            @endforeach\n                        </div>\n                    </div>\n                    @yield('content')\n                </section>\n            </div>\n            <footer class=\"main-footer\">\n                <div class=\"pull-right small text-gray\" style=\"margin-right:10px;margin-top:-7px;\">\n                    <strong><i class=\"fa fa-fw {{ $appIsGit ? 'fa-git-square' : 'fa-code-fork' }}\"></i></strong> {{ $appVersion }}<br />\n                    <strong><i class=\"fa fa-fw fa-clock-o\"></i></strong> {{ round(microtime(true) - LARAVEL_START, 3) }}s\n                </div>\n                Copyright &copy; 2015 - {{ date('Y') }} <a href=\"https://pterodactyl.io/\">Pterodactyl Software</a>. | Sinicizated by <a href=\"https://pterodactyl.top\">翼龙中国</a>\n            </footer>\n        </div>\n        @section('footer-scripts')\n            <script src=\"/js/keyboard.polyfill.js\" type=\"application/javascript\"></script>\n            <script>keyboardeventKeyPolyfill.polyfill();</script>\n\n            {!! Theme::js('vendor/jquery/jquery.min.js?t={cache-version}') !!}\n            {!! Theme::js('vendor/sweetalert/sweetalert.min.js?t={cache-version}') !!}\n            {!! Theme::js('vendor/bootstrap/bootstrap.min.js?t={cache-version}') !!}\n            {!! Theme::js('vendor/slimscroll/jquery.slimscroll.min.js?t={cache-version}') !!}\n            {!! Theme::js('vendor/adminlte/app.min.js?t={cache-version}') !!}\n            {!! Theme::js('vendor/bootstrap-notify/bootstrap-notify.min.js?t={cache-version}') !!}\n            {!! Theme::js('vendor/select2/select2.full.min.js?t={cache-version}') !!}\n            {!! Theme::js('js/admin/functions.js?t={cache-version}') !!}\n            <script src=\"/js/autocomplete.js\" type=\"application/javascript\"></script>\n\n            @if(Auth::user()->root_admin)\n                <script>\n                    $('#logoutButton').on('click', function (event) {\n                        event.preventDefault();\n\n                        var that = this;\n                        swal({\n                            title: '你要登出此账户吗?',\n                            type: 'warning',\n                            showCancelButton: true,\n                            confirmButtonColor: '#d9534f',\n                            cancelButtonColor: '#d33',\n                            confirmButtonText: '登出'\n                        }, function () {\n                             $.ajax({\n                                type: 'POST',\n                                url: '{{ route('auth.logout') }}',\n                                data: {\n                                    _token: '{{ csrf_token() }}'\n                                },complete: function () {\n                                    window.location.href = '{{route('auth.login')}}';\n                                }\n                        });\n                    });\n                });\n                </script>\n            @endif\n\n            <script>\n                $(function () {\n                    $('[data-toggle=\"tooltip\"]').tooltip();\n                })\n            </script>\n        @show\n    </body>\n</html>\n"
  },
  {
    "path": "resources/views/layouts/scripts.blade.php",
    "content": "{{-- Just here as a binder for dynamically rendered content. --}}\n"
  },
  {
    "path": "resources/views/partials/admin/settings/nav.blade.php",
    "content": "@include('partials/admin.settings.notice')\n\n@section('settings::nav')\n    @yield('settings::notice')\n    <div class=\"row\">\n        <div class=\"col-xs-12\">\n            <div class=\"nav-tabs-custom nav-tabs-floating\">\n                <ul class=\"nav nav-tabs\">\n                    <li @if($activeTab === 'basic')class=\"active\"@endif><a href=\"{{ route('admin.settings') }}\">一般设置</a></li>\n                    <li @if($activeTab === 'mail')class=\"active\"@endif><a href=\"{{ route('admin.settings.mail') }}\">邮件设置</a></li>\n                    <li @if($activeTab === 'advanced')class=\"active\"@endif><a href=\"{{ route('admin.settings.advanced') }}\">高级设置</a></li>\n                </ul>\n            </div>\n        </div>\n    </div>\n@endsection\n"
  },
  {
    "path": "resources/views/partials/admin/settings/notice.blade.php",
    "content": "@section('settings::notice')\n    @if(config('pterodactyl.load_environment_only', false))\n        <div class=\"row\">\n            <div class=\"col-xs-12\">\n                <div class=\"alert alert-danger\">\n                    您的面板当前配置为仅从环境中读取设置。您需要在环境文件中设置 <code>APP_ENVIRONMENT_ONLY=false</code> 才能动态加载设置。\n                </div>\n            </div>\n        </div>\n    @endif\n@endsection\n"
  },
  {
    "path": "resources/views/partials/schedules/task-template.blade.php",
    "content": "@section('tasks::chain-template')\n<div class=\"box-footer with-border task-list-item\" data-target=\"task-clone\">\n    <div class=\"row\">\n        <div class=\"form-group col-md-3\">\n            <label class=\"control-label\">@lang('server.schedule.task.time')</label>\n            <div class=\"row\">\n                <div class=\"col-xs-4\">\n                    <select name=\"tasks[time_value][]\" class=\"form-control\">\n                        @foreach(range(0, 59) as $number)\n                            <option value=\"{{ $number }}\">{{ $number }}</option>\n                        @endforeach\n                    </select>\n                </div>\n                <div class=\"col-xs-8\">\n                    <select name=\"tasks[time_interval][]\" class=\"form-control\">\n                        <option value=\"s\">@lang('strings.seconds')</option>\n                        <option value=\"m\">@lang('strings.minutes')</option>\n                    </select>\n                </div>\n            </div>\n        </div>\n        <div class=\"form-group col-md-3\">\n            <label class=\"control-label\">@lang('server.schedule.task.action')</label>\n            <div>\n                <select name=\"tasks[action][]\" class=\"form-control\">\n                    <option value=\"command\">@lang('server.schedule.actions.command')</option>\n                    <option value=\"power\">@lang('server.schedule.actions.power')</option>\n                </select>\n            </div>\n        </div>\n        <div class=\"form-group col-md-6\">\n            <label class=\"control-label\">@lang('server.schedule.task.payload')</label>\n            <div data-attribute=\"remove-task-element\">\n                <input type=\"text\" name=\"tasks[payload][]\" class=\"form-control\">\n                <div class=\"input-group-btn hidden\">\n                    <button type=\"button\" class=\"btn btn-danger\" data-action=\"remove-task\"><i class=\"fa fa-close\"></i></button>\n                </div>\n            </div>\n        </div>\n    </div>\n</div>\n@show\n"
  },
  {
    "path": "resources/views/templates/auth/core.blade.php",
    "content": "@extends('templates/wrapper', [\n    'css' => ['body' => 'bg-neutral-900']\n])\n\n@section('container')\n    <div id=\"app\"></div>\n@endsection\n"
  },
  {
    "path": "resources/views/templates/base/core.blade.php",
    "content": "@extends('templates/wrapper', [\n    'css' => ['body' => 'bg-neutral-800'],\n])\n\n@section('container')\n    <div id=\"modal-portal\"></div>\n    <div id=\"app\"></div>\n@endsection\n"
  },
  {
    "path": "resources/views/templates/wrapper.blade.php",
    "content": "<!DOCTYPE html>\n<html>\n    <head>\n        <title>{{ config('app.name', 'Pterodactyl') }}</title>\n\n        @section('meta')\n            <meta charset=\"utf-8\">\n            <meta http-equiv=\"X-UA-Compatible\" content=\"IE=edge\">\n            <meta content=\"width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no\" name=\"viewport\">\n            <meta name=\"csrf-token\" content=\"{{ csrf_token() }}\">\n            <meta name=\"robots\" content=\"noindex\">\n            <link rel=\"apple-touch-icon\" sizes=\"180x180\" href=\"/favicons/apple-touch-icon.png\">\n            <link rel=\"icon\" type=\"image/png\" href=\"{{ config('logo.favicon', '/favicons/favicon-32x32.png') }}\" sizes=\"32x32\">\n            <link rel=\"icon\" type=\"image/png\" href=\"{{ config('logo.favicon', '/favicons/favicon-16x16.png') }}\" sizes=\"16x16\">\n            <link rel=\"manifest\" href=\"/favicons/manifest.json\">\n            <link rel=\"mask-icon\" href=\"/favicons/safari-pinned-tab.svg\" color=\"#bc6e3c\">\n            <link rel=\"shortcut icon\" href=\"{{ config('logo.favicon', '/favicons/favicon.ico') }}\">\n            <link rel=\"icon\" type=\"image/png\" href=\"{{ config('logo.favicon', '/favicons/favicon.ico') }}\">\n            <meta name=\"msapplication-config\" content=\"/favicons/browserconfig.xml\">\n            <meta name=\"theme-color\" content=\"#0e4688\">\n        @show\n\n        @section('user-data')\n            @if(!is_null(Auth::user()))\n                <script>\n                    window.PterodactylUser = {!! json_encode(Auth::user()->toVueObject()) !!};\n                </script>\n            @endif\n            @if(!empty($siteConfiguration))\n                <script>\n                    window.SiteConfiguration = {!! json_encode($siteConfiguration) !!};\n                </script>\n            @endif\n        @show\n\n        @yield('assets')\n\n        @include('layouts.scripts')\n    </head>\n    <body class=\"{{ $css['body'] ?? 'bg-neutral-50' }}\">\n        @section('content')\n            @yield('above-container')\n            @yield('container')\n            @yield('below-container')\n        @show\n        @section('scripts')\n            {!! $asset->js('main.js') !!}\n        @show\n    </body>\n</html>\n"
  },
  {
    "path": "resources/views/vendor/notifications/email-plain.blade.php",
    "content": "<?php\n\nif (! empty($greeting)) {\n    echo $greeting, \"\\n\\n\";\n} else {\n    echo $level == 'error' ? '噢!' : '你好!', \"\\n\\n\";\n}\n\nif (! empty($introLines)) {\n    echo implode(\"\\n\", $introLines), \"\\n\\n\";\n}\n\nif (isset($actionText)) {\n    echo \"{$actionText}: {$actionUrl}\", \"\\n\\n\";\n}\n\nif (! empty($outroLines)) {\n    echo implode(\"\\n\", $outroLines), \"\\n\\n\";\n}\n\necho '向您问候,', \"\\n\";\necho config('app.name'), \"\\n\";\n"
  },
  {
    "path": "resources/views/vendor/notifications/email.blade.php",
    "content": "<!DOCTYPE html>\n<html>\n\n<head>\n    <meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0\" />\n    <meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\" />\n\n    <style type=\"text/css\" rel=\"stylesheet\" media=\"all\">\n        /* Media Queries */\n        @media only screen and (max-width: 500px) {\n            .button {\n                width: 100% !important;\n            }\n        }\n    </style>\n</head>\n\n<?php\n\n$style = [\n    /* Layout ------------------------------ */\n\n    'body' => 'margin: 0; padding: 0; width: 100%; background-color: #F2F4F6;',\n    'email-wrapper' => 'width: 100%; margin: 0; padding: 0; background-color: #F2F4F6;',\n\n    /* Masthead ----------------------- */\n\n    'email-masthead' => 'padding: 25px 0; text-align: center;',\n    'email-masthead_name' => 'font-size: 16px; font-weight: bold; color: #2F3133; text-decoration: none; text-shadow: 0 1px 0 white;',\n\n    'email-body' => 'width: 100%; margin: 0; padding: 0; border-top: 1px solid #EDEFF2; border-bottom: 1px solid #EDEFF2; background-color: #FFF;',\n    'email-body_inner' => 'width: auto; max-width: 570px; margin: 0 auto; padding: 0;',\n    'email-body_cell' => 'padding: 35px;',\n\n    'email-footer' => 'width: auto; max-width: 570px; margin: 0 auto; padding: 0; text-align: center;',\n    'email-footer_cell' => 'color: #AEAEAE; padding: 35px; text-align: center;',\n\n    /* Body ------------------------------ */\n\n    'body_action' => 'width: 100%; margin: 30px auto; padding: 0; text-align: center;',\n    'body_sub' => 'margin-top: 25px; padding-top: 25px; border-top: 1px solid #EDEFF2;',\n\n    /* Type ------------------------------ */\n\n    'anchor' => 'color: #3869D4;',\n    'header-1' => 'margin-top: 0; color: #2F3133; font-size: 19px; font-weight: bold; text-align: left;',\n    'paragraph' => 'margin-top: 0; color: #74787E; font-size: 16px; line-height: 1.5em;',\n    'paragraph-sub' => 'margin-top: 0; color: #74787E; font-size: 12px; line-height: 1.5em;',\n    'paragraph-center' => 'text-align: center;',\n\n    /* Buttons ------------------------------ */\n\n    'button' => 'display: block; display: inline-block; width: 200px; min-height: 20px; padding: 10px;\n                 background-color: #3869D4; border-radius: 3px; color: #ffffff; font-size: 15px; line-height: 25px;\n                 text-align: center; text-decoration: none; -webkit-text-size-adjust: none;',\n\n    'button--green' => 'background-color: #22BC66;',\n    'button--red' => 'background-color: #dc4d2f;',\n    'button--blue' => 'background-color: #3869D4;',\n];\n?>\n\n<?php $fontFamily = 'font-family: Arial, \\'Helvetica Neue\\', Helvetica, sans-serif;'; ?>\n\n<body style=\"{{ $style['body'] }}\">\n    <table width=\"100%\" cellpadding=\"0\" cellspacing=\"0\">\n        <tr>\n            <td style=\"{{ $style['email-wrapper'] }}\" align=\"center\">\n                <table width=\"100%\" cellpadding=\"0\" cellspacing=\"0\">\n                    <!-- Logo -->\n                    <tr>\n                        <td style=\"{{ $style['email-masthead'] }}\">\n                            <a style=\"{{ $fontFamily }} {{ $style['email-masthead_name'] }}\" href=\"{{ url('/') }}\" target=\"_blank\">\n                                {{ config('app.name') }}\n                            </a>\n                        </td>\n                    </tr>\n\n                    <!-- Email Body -->\n                    <tr>\n                        <td style=\"{{ $style['email-body'] }}\" width=\"100%\">\n                            <table style=\"{{ $style['email-body_inner'] }}\" align=\"center\" width=\"570\" cellpadding=\"0\" cellspacing=\"0\">\n                                <tr>\n                                    <td style=\"{{ $fontFamily }} {{ $style['email-body_cell'] }}\">\n                                        <!-- Greeting -->\n                                        <h1 style=\"{{ $style['header-1'] }}\">\n                                            @if (! empty($greeting))\n                                                {{ $greeting }}\n                                            @else\n                                                @if ($level == 'error')\n                                                    噢!\n                                                @else\n                                                    你好!\n                                                @endif\n                                            @endif\n                                        </h1>\n\n                                        <!-- Intro -->\n                                        @foreach ($introLines as $line)\n                                            <p style=\"{{ $style['paragraph'] }}\">\n                                                {{ $line }}\n                                            </p>\n                                        @endforeach\n\n                                        <!-- Action Button -->\n                                        @if (isset($actionText))\n                                            <table style=\"{{ $style['body_action'] }}\" align=\"center\" width=\"100%\" cellpadding=\"0\" cellspacing=\"0\">\n                                                <tr>\n                                                    <td align=\"center\">\n                                                        <?php\n                                                            switch ($level) {\n                                                                case 'success':\n                                                                    $actionColor = 'button--green';\n                                                                    break;\n                                                                case 'error':\n                                                                    $actionColor = 'button--red';\n                                                                    break;\n                                                                default:\n                                                                    $actionColor = 'button--blue';\n                                                            }\n                                                        ?>\n\n                                                        <a href=\"{{ $actionUrl }}\"\n                                                            style=\"{{ $fontFamily }} {{ $style['button'] }} {{ $style[$actionColor] }}\"\n                                                            class=\"button\"\n                                                            target=\"_blank\">\n                                                            {{ $actionText }}\n                                                        </a>\n                                                    </td>\n                                                </tr>\n                                            </table>\n                                        @endif\n\n                                        <!-- Outro -->\n                                        @foreach ($outroLines as $line)\n                                            <p style=\"{{ $style['paragraph'] }}\">\n                                                {{ $line }}\n                                            </p>\n                                        @endforeach\n\n                                        <!-- Salutation -->\n                                        <p style=\"{{ $style['paragraph'] }}\">\n                                            向您问候,<br>{{ config('app.name') }}\n                                        </p>\n\n                                        <!-- Sub Copy -->\n                                        @if (isset($actionText))\n                                            <table style=\"{{ $style['body_sub'] }}\">\n                                                <tr>\n                                                    <td style=\"{{ $fontFamily }}\">\n                                                        <p style=\"{{ $style['paragraph-sub'] }}\">\n                                                            如果您无法点击 \"{{ $actionText }}\" 按钮,\n                                                            请将下方地址复制至浏览器地址栏打开:\n                                                        </p>\n\n                                                        <p style=\"{{ $style['paragraph-sub'] }}\">\n                                                            <a style=\"{{ $style['anchor'] }}\" href=\"{{ $actionUrl }}\" target=\"_blank\">\n                                                                {{ $actionUrl }}\n                                                            </a>\n                                                        </p>\n                                                    </td>\n                                                </tr>\n                                            </table>\n                                        @endif\n                                    </td>\n                                </tr>\n                            </table>\n                        </td>\n                    </tr>\n\n                    <!-- Footer -->\n                    <tr>\n                        <td>\n                            <table style=\"{{ $style['email-footer'] }}\" align=\"center\" width=\"570\" cellpadding=\"0\" cellspacing=\"0\">\n                                <tr>\n                                    <td style=\"{{ $fontFamily }} {{ $style['email-footer_cell'] }}\">\n                                        <p style=\"{{ $style['paragraph-sub'] }}\">\n                                            &copy; {{ date('Y') }}\n                                            <a style=\"{{ $style['anchor'] }}\" href=\"{{ url('/') }}\" target=\"_blank\">{{ config('app.name') }}</a>.\n                                            All rights reserved.\n                                        </p>\n                                    </td>\n                                </tr>\n                            </table>\n                        </td>\n                    </tr>\n                </table>\n            </td>\n        </tr>\n    </table>\n</body>\n</html>\n"
  },
  {
    "path": "resources/views/vendor/pagination/default.blade.php",
    "content": "@if ($paginator->lastPage() > 1)\n    <ul class=\"pagination pull-right no-margin\">\n        <!-- Previous Page Link -->\n        @if ($paginator->onFirstPage())\n            {{-- <li class=\"disabled\"><span>&laquo;</span></li> --}}\n        @else\n            <li><a href=\"{{ $paginator->previousPageUrl() }}\" rel=\"prev\">&laquo;</a></li>\n        @endif\n\n        <!-- Pagination Elements -->\n        @foreach ($elements as $element)\n            <!-- \"Three Dots\" Separator -->\n            @if (is_string($element))\n                <li class=\"disabled\"><span>{{ $element }}</span></li>\n            @endif\n\n            <!-- Array Of Links -->\n            @if (is_array($element))\n                @foreach ($element as $page => $url)\n                    @if ($page == $paginator->currentPage())\n                        <li class=\"active\"><span>{{ $page }}</span></li>\n                    @else\n                        <li><a href=\"{{ $url }}\">{{ $page }}</a></li>\n                    @endif\n                @endforeach\n            @endif\n        @endforeach\n\n        <!-- Next Page Link -->\n        @if ($paginator->hasMorePages())\n            <li><a href=\"{{ $paginator->nextPageUrl() }}\" rel=\"next\">&raquo;</a></li>\n        @else\n            {{-- <li class=\"disabled\"><span>&raquo;</span></li> --}}\n        @endif\n    </ul>\n@endif\n"
  },
  {
    "path": "routes/admin.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Route;\nuse Pterodactyl\\Http\\Controllers\\Admin;\nuse Pterodactyl\\Http\\Middleware\\Admin\\Servers\\ServerInstalled;\n\nRoute::get('/', [Admin\\BaseController::class, 'index'])->name('admin.index');\n\n/*\n|--------------------------------------------------------------------------\n| Location Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /admin/api\n|\n*/\nRoute::group(['prefix' => 'api'], function () {\n    Route::get('/', [Admin\\ApiController::class, 'index'])->name('admin.api.index');\n    Route::get('/new', [Admin\\ApiController::class, 'create'])->name('admin.api.new');\n\n    Route::post('/new', [Admin\\ApiController::class, 'store']);\n\n    Route::delete('/revoke/{identifier}', [Admin\\ApiController::class, 'delete'])->name('admin.api.delete');\n});\n\n/*\n|--------------------------------------------------------------------------\n| Location Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /admin/locations\n|\n*/\nRoute::group(['prefix' => 'locations'], function () {\n    Route::get('/', [Admin\\LocationController::class, 'index'])->name('admin.locations');\n    Route::get('/view/{location:id}', [Admin\\LocationController::class, 'view'])->name('admin.locations.view');\n\n    Route::post('/', [Admin\\LocationController::class, 'create']);\n    Route::patch('/view/{location:id}', [Admin\\LocationController::class, 'update']);\n});\n\n/*\n|--------------------------------------------------------------------------\n| Database Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /admin/databases\n|\n*/\nRoute::group(['prefix' => 'databases'], function () {\n    Route::get('/', [Admin\\DatabaseController::class, 'index'])->name('admin.databases');\n    Route::get('/view/{host:id}', [Admin\\DatabaseController::class, 'view'])->name('admin.databases.view');\n\n    Route::post('/', [Admin\\DatabaseController::class, 'create']);\n    Route::patch('/view/{host:id}', [Admin\\DatabaseController::class, 'update']);\n    Route::delete('/view/{host:id}', [Admin\\DatabaseController::class, 'delete']);\n});\n\n/*\n|--------------------------------------------------------------------------\n| Settings Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /admin/settings\n|\n*/\nRoute::group(['prefix' => 'settings'], function () {\n    Route::get('/', [Admin\\Settings\\IndexController::class, 'index'])->name('admin.settings');\n    Route::get('/mail', [Admin\\Settings\\MailController::class, 'index'])->name('admin.settings.mail');\n    Route::get('/advanced', [Admin\\Settings\\AdvancedController::class, 'index'])->name('admin.settings.advanced');\n\n    Route::post('/mail/test', [Admin\\Settings\\MailController::class, 'test'])->name('admin.settings.mail.test');\n\n    Route::patch('/', [Admin\\Settings\\IndexController::class, 'update']);\n    Route::patch('/mail', [Admin\\Settings\\MailController::class, 'update']);\n    Route::patch('/advanced', [Admin\\Settings\\AdvancedController::class, 'update']);\n});\n\n/*\n|--------------------------------------------------------------------------\n| User Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /admin/users\n|\n*/\nRoute::group(['prefix' => 'users'], function () {\n    Route::get('/', [Admin\\UserController::class, 'index'])->name('admin.users');\n    Route::get('/accounts.json', [Admin\\UserController::class, 'json'])->name('admin.users.json');\n    Route::get('/new', [Admin\\UserController::class, 'create'])->name('admin.users.new');\n    Route::get('/view/{user:id}', [Admin\\UserController::class, 'view'])->name('admin.users.view');\n\n    Route::post('/new', [Admin\\UserController::class, 'store']);\n\n    Route::patch('/view/{user:id}', [Admin\\UserController::class, 'update']);\n    Route::delete('/view/{user:id}', [Admin\\UserController::class, 'delete'])->name('admin.users.delete');\n});\n\n/*\n|--------------------------------------------------------------------------\n| Server Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /admin/servers\n|\n*/\nRoute::group(['prefix' => 'servers'], function () {\n    Route::get('/', [Admin\\Servers\\ServerController::class, 'index'])->name('admin.servers');\n    Route::get('/new', [Admin\\Servers\\CreateServerController::class, 'index'])->name('admin.servers.new');\n    Route::get('/view/{server:id}', [Admin\\Servers\\ServerViewController::class, 'index'])->name('admin.servers.view');\n\n    Route::group(['middleware' => [ServerInstalled::class]], function () {\n        Route::get('/view/{server:id}/details', [Admin\\Servers\\ServerViewController::class, 'details'])->name('admin.servers.view.details');\n        Route::get('/view/{server:id}/build', [Admin\\Servers\\ServerViewController::class, 'build'])->name('admin.servers.view.build');\n        Route::get('/view/{server:id}/startup', [Admin\\Servers\\ServerViewController::class, 'startup'])->name('admin.servers.view.startup');\n        Route::get('/view/{server:id}/database', [Admin\\Servers\\ServerViewController::class, 'database'])->name('admin.servers.view.database');\n        Route::get('/view/{server:id}/mounts', [Admin\\Servers\\ServerViewController::class, 'mounts'])->name('admin.servers.view.mounts');\n    });\n\n    Route::get('/view/{server:id}/manage', [Admin\\Servers\\ServerViewController::class, 'manage'])->name('admin.servers.view.manage');\n    Route::get('/view/{server:id}/delete', [Admin\\Servers\\ServerViewController::class, 'delete'])->name('admin.servers.view.delete');\n\n    Route::post('/new', [Admin\\Servers\\CreateServerController::class, 'store']);\n    Route::post('/view/{server:id}/build', [Admin\\ServersController::class, 'updateBuild']);\n    Route::post('/view/{server:id}/startup', [Admin\\ServersController::class, 'saveStartup']);\n    Route::post('/view/{server:id}/database', [Admin\\ServersController::class, 'newDatabase']);\n    Route::post('/view/{server:id}/mounts', [Admin\\ServersController::class, 'addMount'])->name('admin.servers.view.mounts.store');\n    Route::post('/view/{server:id}/manage/toggle', [Admin\\ServersController::class, 'toggleInstall'])->name('admin.servers.view.manage.toggle');\n    Route::post('/view/{server:id}/manage/suspension', [Admin\\ServersController::class, 'manageSuspension'])->name('admin.servers.view.manage.suspension');\n    Route::post('/view/{server:id}/manage/reinstall', [Admin\\ServersController::class, 'reinstallServer'])->name('admin.servers.view.manage.reinstall');\n    Route::post('/view/{server:id}/manage/transfer', [Admin\\Servers\\ServerTransferController::class, 'transfer'])->name('admin.servers.view.manage.transfer');\n    Route::post('/view/{server:id}/delete', [Admin\\ServersController::class, 'delete']);\n\n    Route::patch('/view/{server:id}/details', [Admin\\ServersController::class, 'setDetails']);\n    Route::patch('/view/{server:id}/database', [Admin\\ServersController::class, 'resetDatabasePassword']);\n\n    Route::delete('/view/{server:id}/database/{database:id}/delete', [Admin\\ServersController::class, 'deleteDatabase'])->name('admin.servers.view.database.delete');\n    Route::delete('/view/{server:id}/mounts/{mount:id}', [Admin\\ServersController::class, 'deleteMount'])\n        ->name('admin.servers.view.mounts.delete');\n});\n\n/*\n|--------------------------------------------------------------------------\n| Node Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /admin/nodes\n|\n*/\nRoute::group(['prefix' => 'nodes'], function () {\n    Route::get('/', [Admin\\Nodes\\NodeController::class, 'index'])->name('admin.nodes');\n    Route::get('/new', [Admin\\NodesController::class, 'create'])->name('admin.nodes.new');\n    Route::get('/view/{node:id}', [Admin\\Nodes\\NodeViewController::class, 'index'])->name('admin.nodes.view');\n    Route::get('/view/{node:id}/settings', [Admin\\Nodes\\NodeViewController::class, 'settings'])->name('admin.nodes.view.settings');\n    Route::get('/view/{node:id}/configuration', [Admin\\Nodes\\NodeViewController::class, 'configuration'])->name('admin.nodes.view.configuration');\n    Route::get('/view/{node:id}/allocation', [Admin\\Nodes\\NodeViewController::class, 'allocations'])->name('admin.nodes.view.allocation');\n    Route::get('/view/{node:id}/servers', [Admin\\Nodes\\NodeViewController::class, 'servers'])->name('admin.nodes.view.servers');\n    Route::get('/view/{node:id}/system-information', Admin\\Nodes\\SystemInformationController::class);\n\n    Route::post('/new', [Admin\\NodesController::class, 'store']);\n    Route::post('/view/{node:id}/allocation', [Admin\\NodesController::class, 'createAllocation']);\n    Route::post('/view/{node:id}/allocation/remove', [Admin\\NodesController::class, 'allocationRemoveBlock'])->name('admin.nodes.view.allocation.removeBlock');\n    Route::post('/view/{node:id}/allocation/alias', [Admin\\NodesController::class, 'allocationSetAlias'])->name('admin.nodes.view.allocation.setAlias');\n    Route::post('/view/{node:id}/settings/token', Admin\\NodeAutoDeployController::class)->name('admin.nodes.view.configuration.token');\n\n    Route::patch('/view/{node:id}/settings', [Admin\\NodesController::class, 'updateSettings']);\n\n    Route::delete('/view/{node:id}/delete', [Admin\\NodesController::class, 'delete'])->name('admin.nodes.view.delete');\n    Route::delete('/view/{node:id}/allocation/remove/{allocation:id}', [Admin\\NodesController::class, 'allocationRemoveSingle'])->name('admin.nodes.view.allocation.removeSingle');\n    Route::delete('/view/{node:id}/allocations', [Admin\\NodesController::class, 'allocationRemoveMultiple'])->name('admin.nodes.view.allocation.removeMultiple');\n});\n\n/*\n|--------------------------------------------------------------------------\n| Mount Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /admin/mounts\n|\n*/\nRoute::group(['prefix' => 'mounts'], function () {\n    Route::get('/', [Admin\\MountController::class, 'index'])->name('admin.mounts');\n    Route::get('/view/{mount:id}', [Admin\\MountController::class, 'view'])->name('admin.mounts.view');\n\n    Route::post('/', [Admin\\MountController::class, 'create']);\n    Route::post('/{mount:id}/eggs', [Admin\\MountController::class, 'addEggs'])->name('admin.mounts.eggs');\n    Route::post('/{mount:id}/nodes', [Admin\\MountController::class, 'addNodes'])->name('admin.mounts.nodes');\n\n    Route::patch('/view/{mount:id}', [Admin\\MountController::class, 'update']);\n\n    Route::delete('/{mount:id}/eggs/{egg_id}', [Admin\\MountController::class, 'deleteEgg']);\n    Route::delete('/{mount:id}/nodes/{node_id}', [Admin\\MountController::class, 'deleteNode']);\n});\n\n/*\n|--------------------------------------------------------------------------\n| Nest Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /admin/nests\n|\n*/\nRoute::group(['prefix' => 'nests'], function () {\n    Route::get('/', [Admin\\Nests\\NestController::class, 'index'])->name('admin.nests');\n    Route::get('/new', [Admin\\Nests\\NestController::class, 'create'])->name('admin.nests.new');\n    Route::get('/view/{nest:id}', [Admin\\Nests\\NestController::class, 'view'])->name('admin.nests.view');\n    Route::get('/egg/new', [Admin\\Nests\\EggController::class, 'create'])->name('admin.nests.egg.new');\n    Route::get('/egg/{egg:id}', [Admin\\Nests\\EggController::class, 'view'])->name('admin.nests.egg.view');\n    Route::get('/egg/{egg:id}/export', [Admin\\Nests\\EggShareController::class, 'export'])->name('admin.nests.egg.export');\n    Route::get('/egg/{egg:id}/variables', [Admin\\Nests\\EggVariableController::class, 'view'])->name('admin.nests.egg.variables');\n    Route::get('/egg/{egg:id}/scripts', [Admin\\Nests\\EggScriptController::class, 'index'])->name('admin.nests.egg.scripts');\n\n    Route::post('/new', [Admin\\Nests\\NestController::class, 'store']);\n    Route::post('/import', [Admin\\Nests\\EggShareController::class, 'import'])->name('admin.nests.egg.import');\n    Route::post('/egg/new', [Admin\\Nests\\EggController::class, 'store']);\n    Route::post('/egg/{egg:id}/variables', [Admin\\Nests\\EggVariableController::class, 'store']);\n\n    Route::put('/egg/{egg:id}', [Admin\\Nests\\EggShareController::class, 'update']);\n\n    Route::patch('/view/{nest:id}', [Admin\\Nests\\NestController::class, 'update']);\n    Route::patch('/egg/{egg:id}', [Admin\\Nests\\EggController::class, 'update']);\n    Route::patch('/egg/{egg:id}/scripts', [Admin\\Nests\\EggScriptController::class, 'update']);\n    Route::patch('/egg/{egg:id}/variables/{variable:id}', [Admin\\Nests\\EggVariableController::class, 'update'])->name('admin.nests.egg.variables.edit');\n\n    Route::delete('/view/{nest:id}', [Admin\\Nests\\NestController::class, 'destroy']);\n    Route::delete('/egg/{egg:id}', [Admin\\Nests\\EggController::class, 'destroy']);\n    Route::delete('/egg/{egg:id}/variables/{variable:id}', [Admin\\Nests\\EggVariableController::class, 'destroy']);\n});\n"
  },
  {
    "path": "routes/api-application.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Route;\nuse Pterodactyl\\Http\\Controllers\\Api\\Application;\n\n/*\n|--------------------------------------------------------------------------\n| User Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /api/application/users\n|\n*/\n\nRoute::group(['prefix' => '/users'], function () {\n    Route::get('/', [Application\\Users\\UserController::class, 'index'])->name('api.application.users');\n    Route::get('/{user:id}', [Application\\Users\\UserController::class, 'view'])->name('api.application.users.view');\n    Route::get('/external/{external_id}', [Application\\Users\\ExternalUserController::class, 'index'])->name('api.application.users.external');\n\n    Route::post('/', [Application\\Users\\UserController::class, 'store']);\n    Route::patch('/{user:id}', [Application\\Users\\UserController::class, 'update']);\n\n    Route::delete('/{user:id}', [Application\\Users\\UserController::class, 'delete']);\n});\n\n/*\n|--------------------------------------------------------------------------\n| Node Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /api/application/nodes\n|\n*/\nRoute::group(['prefix' => '/nodes'], function () {\n    Route::get('/', [Application\\Nodes\\NodeController::class, 'index'])->name('api.application.nodes');\n    Route::get('/deployable', Application\\Nodes\\NodeDeploymentController::class);\n    Route::get('/{node:id}', [Application\\Nodes\\NodeController::class, 'view'])->name('api.application.nodes.view');\n    Route::get('/{node:id}/configuration', Application\\Nodes\\NodeConfigurationController::class);\n\n    Route::post('/', [Application\\Nodes\\NodeController::class, 'store']);\n    Route::patch('/{node:id}', [Application\\Nodes\\NodeController::class, 'update'])->name('api.application.nodes.update');\n\n    Route::delete('/{node:id}', [Application\\Nodes\\NodeController::class, 'delete']);\n\n    Route::group(['prefix' => '/{node:id}/allocations'], function () {\n        Route::get('/', [Application\\Nodes\\AllocationController::class, 'index'])->name('api.application.allocations');\n        Route::post('/', [Application\\Nodes\\AllocationController::class, 'store']);\n        Route::delete('/{allocation:id}', [Application\\Nodes\\AllocationController::class, 'delete'])->name('api.application.allocations.view');\n    });\n});\n\n/*\n|--------------------------------------------------------------------------\n| Location Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /api/application/locations\n|\n*/\nRoute::group(['prefix' => '/locations'], function () {\n    Route::get('/', [Application\\Locations\\LocationController::class, 'index'])->name('api.applications.locations');\n    Route::get('/{location:id}', [Application\\Locations\\LocationController::class, 'view'])->name('api.application.locations.view');\n\n    Route::post('/', [Application\\Locations\\LocationController::class, 'store']);\n    Route::patch('/{location:id}', [Application\\Locations\\LocationController::class, 'update']);\n\n    Route::delete('/{location:id}', [Application\\Locations\\LocationController::class, 'delete']);\n});\n\n/*\n|--------------------------------------------------------------------------\n| Server Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /api/application/servers\n|\n*/\nRoute::group(['prefix' => '/servers'], function () {\n    Route::get('/', [Application\\Servers\\ServerController::class, 'index'])->name('api.application.servers');\n    Route::get('/{server:id}', [Application\\Servers\\ServerController::class, 'view'])->name('api.application.servers.view');\n    Route::get('/external/{external_id}', [Application\\Servers\\ExternalServerController::class, 'index'])->name('api.application.servers.external');\n\n    Route::patch('/{server:id}/details', [Application\\Servers\\ServerDetailsController::class, 'details'])->name('api.application.servers.details');\n    Route::patch('/{server:id}/build', [Application\\Servers\\ServerDetailsController::class, 'build'])->name('api.application.servers.build');\n    Route::patch('/{server:id}/startup', [Application\\Servers\\StartupController::class, 'index'])->name('api.application.servers.startup');\n\n    Route::post('/', [Application\\Servers\\ServerController::class, 'store']);\n    Route::post('/{server:id}/suspend', [Application\\Servers\\ServerManagementController::class, 'suspend'])->name('api.application.servers.suspend');\n    Route::post('/{server:id}/unsuspend', [Application\\Servers\\ServerManagementController::class, 'unsuspend'])->name('api.application.servers.unsuspend');\n    Route::post('/{server:id}/reinstall', [Application\\Servers\\ServerManagementController::class, 'reinstall'])->name('api.application.servers.reinstall');\n\n    Route::delete('/{server:id}', [Application\\Servers\\ServerController::class, 'delete']);\n    Route::delete('/{server:id}/{force?}', [Application\\Servers\\ServerController::class, 'delete']);\n\n    // Database Management Endpoint\n    Route::group(['prefix' => '/{server:id}/databases'], function () {\n        Route::get('/', [Application\\Servers\\DatabaseController::class, 'index'])->name('api.application.servers.databases');\n        Route::get('/{database:id}', [Application\\Servers\\DatabaseController::class, 'view'])->name('api.application.servers.databases.view');\n\n        Route::post('/', [Application\\Servers\\DatabaseController::class, 'store']);\n        Route::post('/{database:id}/reset-password', [Application\\Servers\\DatabaseController::class, 'resetPassword']);\n\n        Route::delete('/{database:id}', [Application\\Servers\\DatabaseController::class, 'delete']);\n    });\n});\n\n/*\n|--------------------------------------------------------------------------\n| Nest Controller Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /api/application/nests\n|\n*/\nRoute::group(['prefix' => '/nests'], function () {\n    Route::get('/', [Application\\Nests\\NestController::class, 'index'])->name('api.application.nests');\n    Route::get('/{nest:id}', [Application\\Nests\\NestController::class, 'view'])->name('api.application.nests.view');\n\n    // Egg Management Endpoint\n    Route::group(['prefix' => '/{nest:id}/eggs'], function () {\n        Route::get('/', [Application\\Nests\\EggController::class, 'index'])->name('api.application.nests.eggs');\n        Route::get('/{egg:id}', [Application\\Nests\\EggController::class, 'view'])->name('api.application.nests.eggs.view');\n    });\n});\n"
  },
  {
    "path": "routes/api-client.php",
    "content": "<?php\n\nuse Pterodactyl\\Enum\\ResourceLimit;\nuse Illuminate\\Support\\Facades\\Route;\nuse Pterodactyl\\Http\\Controllers\\Api\\Client;\nuse Pterodactyl\\Http\\Middleware\\Activity\\ServerSubject;\nuse Pterodactyl\\Http\\Middleware\\Activity\\AccountSubject;\nuse Pterodactyl\\Http\\Middleware\\RequireTwoFactorAuthentication;\nuse Pterodactyl\\Http\\Middleware\\Api\\Client\\Server\\ResourceBelongsToServer;\nuse Pterodactyl\\Http\\Middleware\\Api\\Client\\Server\\AuthenticateServerAccess;\n\n/*\n|--------------------------------------------------------------------------\n| Client Control API\n|--------------------------------------------------------------------------\n|\n| Endpoint: /api/client\n|\n*/\nRoute::get('/', [Client\\ClientController::class, 'index'])->name('api:client.index');\nRoute::get('/permissions', [Client\\ClientController::class, 'permissions']);\n\nRoute::prefix('/account')->middleware(AccountSubject::class)->group(function () {\n    Route::prefix('/')->withoutMiddleware(RequireTwoFactorAuthentication::class)->group(function () {\n        Route::get('/', [Client\\AccountController::class, 'index'])->name('api:client.account');\n        Route::get('/two-factor', [Client\\TwoFactorController::class, 'index']);\n        Route::post('/two-factor', [Client\\TwoFactorController::class, 'store']);\n        Route::post('/two-factor/disable', [Client\\TwoFactorController::class, 'delete']);\n    });\n\n    Route::put('/email', [Client\\AccountController::class, 'updateEmail'])\n        ->middleware('throttle')\n        ->name('api:client.account.update-email');\n    Route::put('/password', [Client\\AccountController::class, 'updatePassword'])->name('api:client.account.update-password');\n\n    Route::get('/activity', Client\\ActivityLogController::class)->name('api:client.account.activity');\n\n    Route::get('/api-keys', [Client\\ApiKeyController::class, 'index']);\n    Route::post('/api-keys', [Client\\ApiKeyController::class, 'store']);\n    Route::delete('/api-keys/{identifier}', [Client\\ApiKeyController::class, 'delete']);\n\n    Route::prefix('/ssh-keys')->group(function () {\n        Route::get('/', [Client\\SSHKeyController::class, 'index']);\n        Route::post('/', [Client\\SSHKeyController::class, 'store']);\n        Route::post('/remove', [Client\\SSHKeyController::class, 'delete']);\n    });\n});\n\n/*\n|--------------------------------------------------------------------------\n| Client Control API\n|--------------------------------------------------------------------------\n|\n| Endpoint: /api/client/servers/{server}\n|\n*/\nRoute::group([\n    'prefix' => '/servers/{server}',\n    'middleware' => [\n        ServerSubject::class,\n        AuthenticateServerAccess::class,\n        ResourceBelongsToServer::class,\n    ],\n], function () {\n    Route::get('/', [Client\\Servers\\ServerController::class, 'index'])->name('api:client:server.view');\n    Route::middleware([ResourceLimit::Websocket->middleware()])\n        ->get('/websocket', Client\\Servers\\WebsocketController::class)\n        ->name('api:client:server.ws');\n    Route::get('/resources', Client\\Servers\\ResourceUtilizationController::class)->name('api:client:server.resources');\n    Route::get('/activity', Client\\Servers\\ActivityLogController::class)->name('api:client:server.activity');\n\n    Route::post('/command', [Client\\Servers\\CommandController::class, 'index']);\n    Route::post('/power', [Client\\Servers\\PowerController::class, 'index']);\n\n    Route::group(['prefix' => '/databases'], function () {\n        Route::get('/', [Client\\Servers\\DatabaseController::class, 'index']);\n        Route::middleware([ResourceLimit::Database->middleware()])\n            ->post('/', [Client\\Servers\\DatabaseController::class, 'store']);\n        Route::post('/{database}/rotate-password', [Client\\Servers\\DatabaseController::class, 'rotatePassword']);\n        Route::delete('/{database}', [Client\\Servers\\DatabaseController::class, 'delete']);\n    });\n\n    Route::group(['prefix' => '/files'], function () {\n        Route::get('/list', [Client\\Servers\\FileController::class, 'directory']);\n        Route::get('/contents', [Client\\Servers\\FileController::class, 'contents']);\n        Route::get('/download', [Client\\Servers\\FileController::class, 'download']);\n        Route::put('/rename', [Client\\Servers\\FileController::class, 'rename']);\n        Route::post('/copy', [Client\\Servers\\FileController::class, 'copy']);\n        Route::post('/write', [Client\\Servers\\FileController::class, 'write']);\n        Route::post('/compress', [Client\\Servers\\FileController::class, 'compress']);\n        Route::post('/decompress', [Client\\Servers\\FileController::class, 'decompress']);\n        Route::post('/delete', [Client\\Servers\\FileController::class, 'delete']);\n        Route::post('/create-folder', [Client\\Servers\\FileController::class, 'create']);\n        Route::post('/chmod', [Client\\Servers\\FileController::class, 'chmod']);\n        Route::middleware([ResourceLimit::FilePull->middleware()])\n            ->post('/pull', [Client\\Servers\\FileController::class, 'pull']);\n        Route::get('/upload', Client\\Servers\\FileUploadController::class);\n    });\n\n    Route::group(['prefix' => '/schedules'], function () {\n        Route::get('/', [Client\\Servers\\ScheduleController::class, 'index']);\n        Route::middleware([ResourceLimit::Schedule->middleware()])\n            ->post('/', [Client\\Servers\\ScheduleController::class, 'store']);\n        Route::get('/{schedule}', [Client\\Servers\\ScheduleController::class, 'view']);\n        Route::post('/{schedule}', [Client\\Servers\\ScheduleController::class, 'update']);\n        Route::post('/{schedule}/execute', [Client\\Servers\\ScheduleController::class, 'execute']);\n        Route::delete('/{schedule}', [Client\\Servers\\ScheduleController::class, 'delete']);\n\n        Route::post('/{schedule}/tasks', [Client\\Servers\\ScheduleTaskController::class, 'store']);\n        Route::post('/{schedule}/tasks/{task}', [Client\\Servers\\ScheduleTaskController::class, 'update']);\n        Route::delete('/{schedule}/tasks/{task}', [Client\\Servers\\ScheduleTaskController::class, 'delete']);\n    });\n\n    Route::group(['prefix' => '/network'], function () {\n        Route::get('/allocations', [Client\\Servers\\NetworkAllocationController::class, 'index']);\n        Route::middleware([ResourceLimit::Allocation->middleware()])\n            ->post('/allocations', [Client\\Servers\\NetworkAllocationController::class, 'store']);\n        Route::post('/allocations/{allocation}', [Client\\Servers\\NetworkAllocationController::class, 'update']);\n        Route::post('/allocations/{allocation}/primary', [Client\\Servers\\NetworkAllocationController::class, 'setPrimary']);\n        Route::delete('/allocations/{allocation}', [Client\\Servers\\NetworkAllocationController::class, 'delete']);\n    });\n\n    Route::group(['prefix' => '/users'], function () {\n        Route::get('/', [Client\\Servers\\SubuserController::class, 'index']);\n        Route::middleware([ResourceLimit::Subuser->middleware()])\n            ->post('/', [Client\\Servers\\SubuserController::class, 'store']);\n        Route::get('/{user}', [Client\\Servers\\SubuserController::class, 'view']);\n        Route::post('/{user}', [Client\\Servers\\SubuserController::class, 'update']);\n        Route::delete('/{user}', [Client\\Servers\\SubuserController::class, 'delete']);\n    });\n\n    Route::group(['prefix' => '/backups'], function () {\n        Route::get('/', [Client\\Servers\\BackupController::class, 'index']);\n        Route::post('/', [Client\\Servers\\BackupController::class, 'store']);\n        Route::get('/{backup}', [Client\\Servers\\BackupController::class, 'view']);\n        Route::get('/{backup}/download', [Client\\Servers\\BackupController::class, 'download']);\n        Route::post('/{backup}/lock', [Client\\Servers\\BackupController::class, 'toggleLock']);\n        Route::middleware([ResourceLimit::Backup->middleware()])\n            ->post('/{backup}/restore', [Client\\Servers\\BackupController::class, 'restore']);\n        Route::delete('/{backup}', [Client\\Servers\\BackupController::class, 'delete']);\n    });\n\n    Route::group(['prefix' => '/startup'], function () {\n        Route::get('/', [Client\\Servers\\StartupController::class, 'index']);\n        Route::put('/variable', [Client\\Servers\\StartupController::class, 'update']);\n        Route::put('/egg', [Client\\Servers\\StartupController::class, 'updateEgg']);\n    });\n\n    Route::group(['prefix' => '/settings'], function () {\n        Route::post('/rename', [Client\\Servers\\SettingsController::class, 'rename']);\n        Route::post('/reinstall', [Client\\Servers\\SettingsController::class, 'reinstall']);\n        Route::put('/docker-image', [Client\\Servers\\SettingsController::class, 'dockerImage']);\n    });\n});\n"
  },
  {
    "path": "routes/api-remote.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Route;\nuse Pterodactyl\\Http\\Controllers\\Api\\Remote;\n\n// Routes for the Wings daemon.\nRoute::post('/sftp/auth', Remote\\SftpAuthenticationController::class);\n\nRoute::get('/servers', [Remote\\Servers\\ServerDetailsController::class, 'list']);\nRoute::post('/servers/reset', [Remote\\Servers\\ServerDetailsController::class, 'resetState']);\nRoute::post('/activity', Remote\\ActivityProcessingController::class);\n\nRoute::group(['prefix' => '/servers/{uuid}'], function () {\n    Route::get('/', Remote\\Servers\\ServerDetailsController::class);\n    Route::get('/install', [Remote\\Servers\\ServerInstallController::class, 'index']);\n    Route::post('/install', [Remote\\Servers\\ServerInstallController::class, 'store']);\n    Route::post('/transfer/failure', [Remote\\Servers\\ServerTransferController::class, 'failure']);\n    Route::post('/transfer/success', [Remote\\Servers\\ServerTransferController::class, 'success']);\n});\n\nRoute::group(['prefix' => '/backups'], function () {\n    Route::get('/{backup}', Remote\\Backups\\BackupRemoteUploadController::class);\n    Route::post('/{backup}', [Remote\\Backups\\BackupStatusController::class, 'index']);\n    Route::post('/{backup}/restore', [Remote\\Backups\\BackupStatusController::class, 'restore']);\n});\n"
  },
  {
    "path": "routes/auth.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Route;\nuse Pterodactyl\\Http\\Controllers\\Auth;\n\n/*\n|--------------------------------------------------------------------------\n| Authentication Routes\n|--------------------------------------------------------------------------\n|\n| Endpoint: /auth\n|\n*/\n\n// These routes are defined so that we can continue to reference them programmatically.\n// They all route to the same controller function which passes off to React.\nRoute::get('/login', [Auth\\LoginController::class, 'index'])->name('auth.login');\nRoute::get('/password', [Auth\\LoginController::class, 'index'])->name('auth.forgot-password');\nRoute::get('/password/reset/{token}', [Auth\\LoginController::class, 'index'])->name('auth.reset');\n\n// Apply a throttle to authentication action endpoints, in addition to the\n// recaptcha endpoints to slow down manual attack spammers even more. 🤷‍\n//\n// @see \\Pterodactyl\\Providers\\RouteServiceProvider\nRoute::middleware(['throttle:authentication'])->group(function () {\n    // Login endpoints.\n    Route::post('/login', [Auth\\LoginController::class, 'login'])->middleware('recaptcha');\n    Route::post('/login/checkpoint', Auth\\LoginCheckpointController::class)->name('auth.login-checkpoint');\n\n    // Forgot password route. A post to this endpoint will trigger an\n    // email to be sent containing a reset token.\n    Route::post('/password', [Auth\\ForgotPasswordController::class, 'sendResetLinkEmail'])\n        ->name('auth.post.forgot-password')\n        ->middleware('recaptcha');\n});\n\n// Password reset routes. This endpoint is hit after going through\n// the forgot password routes to acquire a token (or after an account\n// is created).\nRoute::post('/password/reset', Auth\\ResetPasswordController::class)->name('auth.reset-password');\n\n// Remove the guest middleware and apply the authenticated middleware to this endpoint,\n// so it cannot be used unless you're already logged in.\nRoute::post('/logout', [Auth\\LoginController::class, 'logout'])\n    ->withoutMiddleware('guest')\n    ->middleware('auth')\n    ->name('auth.logout');\n\n// Catch any other combinations of routes and pass them off to the React component.\nRoute::fallback([Auth\\LoginController::class, 'index']);\n"
  },
  {
    "path": "routes/base.php",
    "content": "<?php\n\nuse Illuminate\\Support\\Facades\\Route;\nuse Pterodactyl\\Http\\Controllers\\Base;\nuse Pterodactyl\\Http\\Middleware\\RequireTwoFactorAuthentication;\n\nRoute::get('/', [Base\\IndexController::class, 'index'])->name('index')->fallback();\nRoute::get('/account', [Base\\IndexController::class, 'index'])\n    ->withoutMiddleware(RequireTwoFactorAuthentication::class)\n    ->name('account');\n\nRoute::get('/locales/locale.json', Base\\LocaleController::class)\n    ->withoutMiddleware(['auth', RequireTwoFactorAuthentication::class])\n    ->where('namespace', '.*');\n\nRoute::get('/{react}', [Base\\IndexController::class, 'index'])\n    ->where('react', '^(?!(\\/)?(api|auth|admin|daemon)).+');\n"
  },
  {
    "path": "shell.nix",
    "content": "{\n  composer ? null,\n  phpWithExtensions ? null,\n  pkgs ? import <nixpkgs> {},\n}:\nwith pkgs;\n  mkShell rec {\n    buildInputs = [\n      alejandra\n      composer\n      nodejs_18\n      nodePackages.yarn\n      phpWithExtensions\n    ];\n\n    shellHook = ''\n      PATH=\"$PATH:${pkgs.docker-compose}/libexec/docker/cli-plugins\"\n    '';\n  }\n"
  },
  {
    "path": "storage/app/.gitignore",
    "content": "*\n!private/\n!public/\n!.gitignore\n"
  },
  {
    "path": "storage/clockwork/.gitignore",
    "content": "*\n!.gitignore\n"
  },
  {
    "path": "storage/logs/.gitignore",
    "content": "*\n!.gitignore\n"
  },
  {
    "path": "tailwind.config.js",
    "content": "const colors = require('tailwindcss/colors');\n\nconst gray = {\n    50: 'hsl(216, 33%, 97%)',\n    100: 'hsl(214, 15%, 91%)',\n    200: 'hsl(210, 16%, 82%)',\n    300: 'hsl(211, 13%, 65%)',\n    400: 'hsl(211, 10%, 53%)',\n    500: 'hsl(211, 12%, 43%)',\n    600: 'hsl(209, 14%, 37%)',\n    700: 'hsl(209, 18%, 30%)',\n    800: 'hsl(209, 20%, 25%)',\n    900: 'hsl(210, 24%, 16%)',\n};\n\nmodule.exports = {\n    content: [\n        './resources/scripts/**/*.{js,ts,tsx}',\n    ],\n    theme: {\n        extend: {\n            fontFamily: {\n                header: ['\"IBM Plex Sans\"', '\"Roboto\"', 'system-ui', 'sans-serif'],\n            },\n            colors: {\n                black: '#131a20',\n                // \"primary\" and \"neutral\" are deprecated, prefer the use of \"blue\" and \"gray\"\n                // in new code.\n                primary: colors.blue,\n                gray: gray,\n                neutral: gray,\n                cyan: colors.cyan,\n            },\n            fontSize: {\n                '2xs': '0.625rem',\n            },\n            transitionDuration: {\n                250: '250ms',\n            },\n            borderColor: theme => ({\n                default: theme('colors.neutral.400', 'currentColor'),\n            }),\n        },\n    },\n    plugins: [\n        require('@tailwindcss/line-clamp'),\n        require('@tailwindcss/forms')({\n            strategy: 'class',\n        }),\n    ]\n};\n"
  },
  {
    "path": "tests/Assertions/AssertsActivityLogged.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Assertions;\n\nuse PHPUnit\\Framework\\Assert;\nuse Illuminate\\Support\\Facades\\Event;\nuse Pterodactyl\\Events\\ActivityLogged;\nuse Illuminate\\Database\\Eloquent\\Model;\nuse Pterodactyl\\Models\\ActivityLogSubject;\n\ntrait AssertsActivityLogged\n{\n    /**\n     * @param Model|array $subjects\n     */\n    public function assertActivityFor(string $event, ?Model $actor, ...$subjects): void\n    {\n        $this->assertActivityLogged($event);\n        $this->assertActivityActor($event, $actor);\n        $this->assertActivitySubjects($event, ...$subjects);\n    }\n\n    /**\n     * Asserts that the given activity log event was stored in the database.\n     */\n    public function assertActivityLogged(string $event): void\n    {\n        Event::assertDispatched(ActivityLogged::class, fn ($e) => $e->is($event));\n    }\n\n    /**\n     * Asserts that a given activity log event was stored with the subjects being\n     * any of the values provided.\n     */\n    public function assertActivitySubjects(string $event, Model|array $subjects): void\n    {\n        if (is_array($subjects)) {\n            \\Webmozart\\Assert\\Assert::lessThanEq(count(func_get_args()), 2, 'Invalid call to ' . __METHOD__ . ': cannot provide additional arguments if providing an array.');\n        } else {\n            $subjects = array_slice(func_get_args(), 1);\n        }\n\n        Event::assertDispatched(ActivityLogged::class, function (ActivityLogged $e) use ($event, $subjects) {\n            Assert::assertEquals($event, $e->model->event);\n            Assert::assertNotEmpty($e->model->subjects);\n\n            foreach ($subjects as $subject) {\n                $match = $e->model->subjects->first(function (ActivityLogSubject $model) use ($subject) {\n                    return $model->subject_type === $subject->getMorphClass()\n                        && $model->subject_id = $subject->getKey();\n                });\n\n                Assert::assertNotNull(\n                    $match,\n                    sprintf('Failed asserting that event \"%s\" includes a %s[%d] subject', $event, get_class($subject), $subject->getKey())\n                );\n            }\n\n            return true;\n        });\n    }\n\n    /**\n     * Asserts that the provided event was logged into the activity logs with the provided\n     * actor model associated with it.\n     */\n    public function assertActivityActor(string $event, ?Model $actor = null): void\n    {\n        Event::assertDispatched(ActivityLogged::class, function (ActivityLogged $e) use ($event, $actor) {\n            Assert::assertEquals($event, $e->model->event);\n\n            if (is_null($actor)) {\n                Assert::assertNull($e->actor());\n            } else {\n                Assert::assertNotNull($e->actor());\n                Assert::assertTrue($e->actor()->is($actor));\n            }\n\n            return true;\n        });\n    }\n}\n"
  },
  {
    "path": "tests/Assertions/MiddlewareAttributeAssertionsTrait.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Assertions;\n\nuse PHPUnit\\Framework\\Assert;\n\ntrait MiddlewareAttributeAssertionsTrait\n{\n    /**\n     * Assert a request has an attribute assigned to it.\n     */\n    public function assertRequestHasAttribute(string $attribute): void\n    {\n        Assert::assertTrue($this->request->attributes->has($attribute), 'Assert that request mock has ' . $attribute . ' attribute.');\n    }\n\n    /**\n     * Assert a request does not have an attribute assigned to it.\n     */\n    public function assertRequestMissingAttribute(string $attribute): void\n    {\n        Assert::assertFalse($this->request->attributes->has($attribute), 'Assert that request mock does not have ' . $attribute . ' attribute.');\n    }\n\n    /**\n     * Assert a request attribute matches an expected value.\n     */\n    public function assertRequestAttributeEquals(mixed $expected, string $attribute): void\n    {\n        Assert::assertEquals($expected, $this->request->attributes->get($attribute));\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Application/ApplicationApiIntegrationTestCase.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Application;\n\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\User;\nuse PHPUnit\\Framework\\Assert;\nuse Pterodactyl\\Models\\ApiKey;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Illuminate\\Foundation\\Testing\\DatabaseTransactions;\nuse Pterodactyl\\Tests\\Traits\\Integration\\CreatesTestModels;\nuse Pterodactyl\\Transformers\\Api\\Application\\BaseTransformer;\nuse Pterodactyl\\Transformers\\Api\\Client\\BaseClientTransformer;\nuse Pterodactyl\\Tests\\Traits\\Http\\IntegrationJsonRequestAssertions;\n\nabstract class ApplicationApiIntegrationTestCase extends IntegrationTestCase\n{\n    use CreatesTestModels;\n    use DatabaseTransactions;\n    use IntegrationJsonRequestAssertions;\n\n    private ApiKey $key;\n\n    private User $user;\n\n    /**\n     * Bootstrap application API tests. Creates a default admin user and associated API key\n     * and also sets some default headers required for accessing the API.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->user = $this->createApiUser();\n        $this->key = $this->createApiKey($this->user);\n\n        $this\n            ->withHeader('Accept', 'application/vnd.pterodactyl.v1+json')\n            ->withHeader('Authorization', 'Bearer ' . $this->key->identifier . decrypt($this->key->token));\n    }\n\n    public function getApiUser(): User\n    {\n        return $this->user;\n    }\n\n    public function getApiKey(): ApiKey\n    {\n        return $this->key;\n    }\n\n    /**\n     * Creates a new default API key and refreshes the headers using it.\n     */\n    protected function createNewDefaultApiKey(User $user, array $permissions = []): ApiKey\n    {\n        $this->key = $this->createApiKey($user, $permissions);\n\n        $this->withHeader('Authorization', 'Bearer ' . $this->key->identifier . decrypt($this->key->token));\n\n        return $this->key;\n    }\n\n    /**\n     * Create an administrative user.\n     */\n    protected function createApiUser(): User\n    {\n        return User::factory()->create([\n            'root_admin' => true,\n        ]);\n    }\n\n    /**\n     * Create a new application API key for a given user model.\n     */\n    protected function createApiKey(User $user, array $permissions = []): ApiKey\n    {\n        return ApiKey::factory()->create(array_merge([\n            'user_id' => $user->id,\n            'key_type' => ApiKey::TYPE_APPLICATION,\n            'r_servers' => AdminAcl::READ | AdminAcl::WRITE,\n            'r_nodes' => AdminAcl::READ | AdminAcl::WRITE,\n            'r_allocations' => AdminAcl::READ | AdminAcl::WRITE,\n            'r_users' => AdminAcl::READ | AdminAcl::WRITE,\n            'r_locations' => AdminAcl::READ | AdminAcl::WRITE,\n            'r_nests' => AdminAcl::READ | AdminAcl::WRITE,\n            'r_eggs' => AdminAcl::READ | AdminAcl::WRITE,\n            'r_database_hosts' => AdminAcl::READ | AdminAcl::WRITE,\n            'r_server_databases' => AdminAcl::READ | AdminAcl::WRITE,\n        ], $permissions));\n    }\n\n    /**\n     * Return a transformer that can be used for testing purposes.\n     */\n    protected function getTransformer(string $abstract): BaseTransformer\n    {\n        $request = Request::createFromGlobals();\n        $request->setUserResolver(function () {\n            return $this->getApiKey()->user;\n        });\n\n        $transformer = $abstract::fromRequest($request);\n\n        Assert::assertInstanceOf(BaseTransformer::class, $transformer);\n        Assert::assertNotInstanceOf(BaseClientTransformer::class, $transformer);\n\n        return $transformer;\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Application/Location/LocationControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Application\\Location;\n\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Location;\nuse Pterodactyl\\Transformers\\Api\\Application\\NodeTransformer;\nuse Pterodactyl\\Transformers\\Api\\Application\\ServerTransformer;\nuse Pterodactyl\\Transformers\\Api\\Application\\LocationTransformer;\nuse Pterodactyl\\Tests\\Integration\\Api\\Application\\ApplicationApiIntegrationTestCase;\n\nclass LocationControllerTest extends ApplicationApiIntegrationTestCase\n{\n    /**\n     * Test getting all locations through the API.\n     */\n    public function testGetLocations()\n    {\n        $locations = Location::factory()->times(2)->create();\n\n        $response = $this->getJson('/api/application/locations?per_page=60');\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2, 'data');\n        $response->assertJsonStructure([\n            'object',\n            'data' => [\n                ['object', 'attributes' => ['id', 'short', 'long', 'created_at', 'updated_at']],\n                ['object', 'attributes' => ['id', 'short', 'long', 'created_at', 'updated_at']],\n            ],\n            'meta' => ['pagination' => ['total', 'count', 'per_page', 'current_page', 'total_pages']],\n        ]);\n\n        $response\n            ->assertJson([\n                'object' => 'list',\n                'data' => [[], []],\n                'meta' => [\n                    'pagination' => [\n                        'total' => 2,\n                        'count' => 2,\n                        'per_page' => 60,\n                        'current_page' => 1,\n                        'total_pages' => 1,\n                    ],\n                ],\n            ])\n            ->assertJsonFragment([\n                'object' => 'location',\n                'attributes' => [\n                    'id' => $locations[0]->id,\n                    'short' => $locations[0]->short,\n                    'long' => $locations[0]->long,\n                    'created_at' => $this->formatTimestamp($locations[0]->created_at),\n                    'updated_at' => $this->formatTimestamp($locations[0]->updated_at),\n                ],\n            ])->assertJsonFragment([\n                'object' => 'location',\n                'attributes' => [\n                    'id' => $locations[1]->id,\n                    'short' => $locations[1]->short,\n                    'long' => $locations[1]->long,\n                    'created_at' => $this->formatTimestamp($locations[1]->created_at),\n                    'updated_at' => $this->formatTimestamp($locations[1]->updated_at),\n                ],\n            ]);\n    }\n\n    /**\n     * Test getting a single location on the API.\n     */\n    public function testGetSingleLocation()\n    {\n        $location = Location::factory()->create();\n\n        $response = $this->getJson('/api/application/locations/' . $location->id);\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2);\n        $response->assertJsonStructure(['object', 'attributes' => ['id', 'short', 'long', 'created_at', 'updated_at']]);\n        $response->assertJson([\n            'object' => 'location',\n            'attributes' => [\n                'id' => $location->id,\n                'short' => $location->short,\n                'long' => $location->long,\n                'created_at' => $this->formatTimestamp($location->created_at),\n                'updated_at' => $this->formatTimestamp($location->updated_at),\n            ],\n        ], true);\n    }\n\n    /**\n     * Test that a location can be created.\n     */\n    public function testCreateLocation()\n    {\n        $response = $this->postJson('/api/application/locations', [\n            'short' => 'inhouse',\n            'long' => 'This is my inhouse location',\n        ]);\n\n        $response->assertStatus(Response::HTTP_CREATED);\n        $response->assertJsonCount(3);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => ['id', 'short', 'long', 'created_at', 'updated_at'],\n            'meta' => ['resource'],\n        ]);\n\n        $this->assertDatabaseHas('locations', ['short' => 'inhouse', 'long' => 'This is my inhouse location']);\n\n        $location = Location::where('short', 'inhouse')->first();\n        $response->assertJson([\n            'object' => 'location',\n            'attributes' => $this->getTransformer(LocationTransformer::class)->transform($location),\n            'meta' => [\n                'resource' => route('api.application.locations.view', $location->id),\n            ],\n        ], true);\n    }\n\n    /**\n     * Test that a location can be updated.\n     */\n    public function testUpdateLocation()\n    {\n        $location = Location::factory()->create();\n\n        $response = $this->patchJson('/api/application/locations/' . $location->id, [\n            'short' => 'new inhouse',\n            'long' => 'This is my new inhouse location',\n        ]);\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => ['id', 'short', 'long', 'created_at', 'updated_at'],\n        ]);\n\n        $this->assertDatabaseHas('locations', ['short' => 'new inhouse', 'long' => 'This is my new inhouse location']);\n        $location = $location->fresh();\n\n        $response->assertJson([\n            'object' => 'location',\n            'attributes' => $this->getTransformer(LocationTransformer::class)->transform($location),\n        ]);\n    }\n\n    /**\n     * Test that a location can be deleted from the database.\n     */\n    public function testDeleteLocation()\n    {\n        $location = Location::factory()->create();\n        $this->assertDatabaseHas('locations', ['id' => $location->id]);\n\n        $response = $this->delete('/api/application/locations/' . $location->id);\n        $response->assertStatus(Response::HTTP_NO_CONTENT);\n\n        $this->assertDatabaseMissing('locations', ['id' => $location->id]);\n    }\n\n    /**\n     * Test that all the defined relationships for a location can be loaded successfully.\n     */\n    public function testRelationshipsCanBeLoaded()\n    {\n        $location = Location::factory()->create();\n        $server = $this->createServerModel(['user_id' => $this->getApiUser()->id, 'location_id' => $location->id]);\n\n        $response = $this->getJson('/api/application/locations/' . $location->id . '?include=servers,nodes');\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2)->assertJsonCount(2, 'attributes.relationships');\n        $response->assertJsonStructure([\n            'attributes' => [\n                'relationships' => [\n                    'nodes' => ['object', 'data' => [['attributes' => ['id']]]],\n                    'servers' => ['object', 'data' => [['attributes' => ['id']]]],\n                ],\n            ],\n        ]);\n\n        // Just assert that we see the expected relationship IDs in the response.\n        $response->assertJson([\n            'attributes' => [\n                'relationships' => [\n                    'nodes' => [\n                        'object' => 'list',\n                        'data' => [\n                            [\n                                'object' => 'node',\n                                'attributes' => $this->getTransformer(NodeTransformer::class)->transform($server->getRelation('node')),\n                            ],\n                        ],\n                    ],\n                    'servers' => [\n                        'object' => 'list',\n                        'data' => [\n                            [\n                                'object' => 'server',\n                                'attributes' => $this->getTransformer(ServerTransformer::class)->transform($server),\n                            ],\n                        ],\n                    ],\n                ],\n            ],\n        ]);\n    }\n\n    /**\n     * Test that a relationship that an API key does not have permission to access\n     * cannot be loaded onto the model.\n     */\n    public function testKeyWithoutPermissionCannotLoadRelationship()\n    {\n        $this->createNewDefaultApiKey($this->getApiUser(), ['r_nodes' => 0]);\n\n        $location = Location::factory()->create();\n        Node::factory()->create(['location_id' => $location->id]);\n\n        $response = $this->getJson('/api/application/locations/' . $location->id . '?include=nodes');\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2)->assertJsonCount(1, 'attributes.relationships');\n        $response->assertJsonStructure([\n            'attributes' => [\n                'relationships' => [\n                    'nodes' => ['object', 'attributes'],\n                ],\n            ],\n        ]);\n\n        // Just assert that we see the expected relationship IDs in the response.\n        $response->assertJson([\n            'attributes' => [\n                'relationships' => [\n                    'nodes' => [\n                        'object' => 'null_resource',\n                        'attributes' => null,\n                    ],\n                ],\n            ],\n        ]);\n    }\n\n    /**\n     * Test that a missing location returns a 404 error.\n     *\n     * GET /api/application/locations/:id\n     */\n    public function testGetMissingLocation()\n    {\n        $response = $this->getJson('/api/application/locations/nil');\n        $this->assertNotFoundJson($response);\n    }\n\n    /**\n     * Test that an authentication error occurs if a key does not have permission\n     * to access a resource.\n     */\n    public function testErrorReturnedIfNoPermission()\n    {\n        $location = Location::factory()->create();\n        $this->createNewDefaultApiKey($this->getApiUser(), ['r_locations' => 0]);\n\n        $response = $this->getJson('/api/application/locations/' . $location->id);\n        $this->assertAccessDeniedJson($response);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Application/Nests/EggControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Application\\Nests;\n\nuse Illuminate\\Support\\Arr;\nuse Pterodactyl\\Models\\Egg;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Transformers\\Api\\Application\\EggTransformer;\nuse Pterodactyl\\Tests\\Integration\\Api\\Application\\ApplicationApiIntegrationTestCase;\n\nclass EggControllerTest extends ApplicationApiIntegrationTestCase\n{\n    /**\n     * Test that all the eggs belonging to a given nest can be returned.\n     */\n    public function testListAllEggsInNest()\n    {\n        $eggs = Egg::query()->where('nest_id', 1)->get();\n\n        $response = $this->getJson('/api/application/nests/' . $eggs->first()->nest_id . '/eggs');\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(count($eggs), 'data');\n        $response->assertJsonStructure([\n            'object',\n            'data' => [\n                [\n                    'object',\n                    'attributes' => [\n                        'id', 'uuid', 'nest', 'author', 'description', 'docker_image', 'startup', 'created_at', 'updated_at',\n                        'script' => ['privileged', 'install', 'entry', 'container', 'extends'],\n                        'config' => [\n                            'files' => [],\n                            'startup' => ['done'],\n                            'stop',\n                            'logs' => [],\n                            'extends',\n                        ],\n                    ],\n                ],\n            ],\n        ]);\n\n        foreach (array_get($response->json(), 'data') as $datum) {\n            $egg = $eggs->where('id', '=', $datum['attributes']['id'])->first();\n\n            $expected = json_encode(Arr::sortRecursive($datum['attributes']));\n            $actual = json_encode(Arr::sortRecursive($this->getTransformer(EggTransformer::class)->transform($egg)));\n\n            $this->assertSame(\n                $expected,\n                $actual,\n                'Unable to find JSON fragment: ' . PHP_EOL . PHP_EOL . \"[$expected]\" . PHP_EOL . PHP_EOL . 'within' . PHP_EOL . PHP_EOL . \"[$actual].\"\n            );\n        }\n    }\n\n    /**\n     * Test that a single egg can be returned.\n     */\n    public function testReturnSingleEgg()\n    {\n        $egg = Egg::query()->findOrFail(1);\n\n        $response = $this->getJson('/api/application/nests/' . $egg->nest_id . '/eggs/' . $egg->id);\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => [\n                'id', 'uuid', 'nest', 'author', 'description', 'docker_image', 'startup', 'script' => [], 'config' => [], 'created_at', 'updated_at',\n            ],\n        ]);\n\n        $response->assertJson([\n            'object' => 'egg',\n            'attributes' => $this->getTransformer(EggTransformer::class)->transform($egg),\n        ], true);\n    }\n\n    /**\n     * Test that a single egg and all the defined relationships can be returned.\n     */\n    public function testReturnSingleEggWithRelationships()\n    {\n        $egg = Egg::query()->findOrFail(1);\n\n        $response = $this->getJson('/api/application/nests/' . $egg->nest_id . '/eggs/' . $egg->id . '?include=servers,variables,nest');\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => [\n                'relationships' => [\n                    'nest' => ['object', 'attributes'],\n                    'servers' => ['object', 'data' => []],\n                    'variables' => ['object', 'data' => []],\n                ],\n            ],\n        ]);\n    }\n\n    /**\n     * Test that a missing egg returns a 404 error.\n     */\n    public function testGetMissingEgg()\n    {\n        $egg = Egg::query()->findOrFail(1);\n\n        $response = $this->getJson('/api/application/nests/' . $egg->nest_id . '/eggs/nil');\n        $this->assertNotFoundJson($response);\n    }\n\n    /**\n     * Test that an authentication error occurs if a key does not have permission\n     * to access a resource.\n     */\n    public function testErrorReturnedIfNoPermission()\n    {\n        $egg = Egg::query()->findOrFail(1);\n        $this->createNewDefaultApiKey($this->getApiUser(), ['r_eggs' => 0]);\n\n        $response = $this->getJson('/api/application/nests/' . $egg->nest_id . '/eggs');\n        $this->assertAccessDeniedJson($response);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Application/Nests/NestControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Application\\Nests;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Contracts\\Repository\\NestRepositoryInterface;\nuse Pterodactyl\\Transformers\\Api\\Application\\NestTransformer;\nuse Pterodactyl\\Tests\\Integration\\Api\\Application\\ApplicationApiIntegrationTestCase;\n\nclass NestControllerTest extends ApplicationApiIntegrationTestCase\n{\n    private NestRepositoryInterface $repository;\n\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->repository = $this->app->make(NestRepositoryInterface::class);\n    }\n\n    /**\n     * Test that the expected nests are returned by the request.\n     */\n    public function testNestResponse()\n    {\n        /** @var \\Pterodactyl\\Models\\Nest[] $nests */\n        $nests = $this->repository->all();\n\n        $response = $this->getJson('/api/application/nests');\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(count($nests), 'data');\n        $response->assertJsonStructure([\n            'object',\n            'data' => [['object', 'attributes' => ['id', 'uuid', 'author', 'name', 'description', 'created_at', 'updated_at']]],\n            'meta' => ['pagination' => ['total', 'count', 'per_page', 'current_page', 'total_pages']],\n        ]);\n\n        $response->assertJson([\n            'object' => 'list',\n            'data' => [],\n            'meta' => [\n                'pagination' => [\n                    'total' => 4,\n                    'count' => 4,\n                    'per_page' => 50,\n                    'current_page' => 1,\n                    'total_pages' => 1,\n                ],\n            ],\n        ]);\n\n        foreach ($nests as $nest) {\n            $response->assertJsonFragment([\n                'object' => 'nest',\n                'attributes' => $this->getTransformer(NestTransformer::class)->transform($nest),\n            ]);\n        }\n    }\n\n    /**\n     * Test that getting a single nest returns the expected result.\n     */\n    public function testSingleNestResponse()\n    {\n        $nest = $this->repository->find(1);\n\n        $response = $this->getJson('/api/application/nests/' . $nest->id);\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => ['id', 'uuid', 'author', 'name', 'description', 'created_at', 'updated_at'],\n        ]);\n\n        $response->assertJson([\n            'object' => 'nest',\n            'attributes' => $this->getTransformer(NestTransformer::class)->transform($nest),\n        ]);\n    }\n\n    /**\n     * Test that including eggs in the response works as expected.\n     */\n    public function testSingleNestWithEggsIncluded()\n    {\n        $nest = $this->repository->find(1);\n        $nest->loadMissing('eggs');\n\n        $response = $this->getJson('/api/application/nests/' . $nest->id . '?include=servers,eggs');\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => [\n                'relationships' => [\n                    'eggs' => ['object', 'data' => []],\n                    'servers' => ['object', 'data' => []],\n                ],\n            ],\n        ]);\n\n        $response->assertJsonCount(count($nest->getRelation('eggs')), 'attributes.relationships.eggs.data');\n    }\n\n    /**\n     * Test that a missing nest returns a 404 error.\n     */\n    public function testGetMissingNest()\n    {\n        $response = $this->getJson('/api/application/nests/nil');\n        $this->assertNotFoundJson($response);\n    }\n\n    /**\n     * Test that an authentication error occurs if a key does not have permission\n     * to access a resource.\n     */\n    public function testErrorReturnedIfNoPermission()\n    {\n        $nest = $this->repository->find(1);\n        $this->createNewDefaultApiKey($this->getApiUser(), ['r_nests' => 0]);\n\n        $response = $this->getJson('/api/application/nests/' . $nest->id);\n        $this->assertAccessDeniedJson($response);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Application/Nodes/NodeController/UpdateNodeTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Application\\Nodes\\NodeController;\n\nuse Mockery\\MockInterface;\nuse Pterodactyl\\Models\\Node;\nuse GuzzleHttp\\Psr7\\Response;\nuse Pterodactyl\\Models\\Location;\nuse Pterodactyl\\Repositories\\Wings\\DaemonConfigurationRepository;\nuse Pterodactyl\\Tests\\Integration\\Api\\Application\\ApplicationApiIntegrationTestCase;\n\nclass UpdateNodeTest extends ApplicationApiIntegrationTestCase\n{\n    public function testCanUpdateNodeProperties(): void\n    {\n        $node = Node::factory()->for(Location::factory())->create();\n        $location = Location::factory()->create();\n\n        $this->mock(DaemonConfigurationRepository::class, function (MockInterface $mock) use ($node) {\n            $mock->expects('setNode')->with(\\Mockery::on(fn ($value) => $value->is($node)))->andReturnSelf();\n            $mock->expects('update')->withAnyArgs()->andReturn(\n                new Response()\n            );\n        });\n\n        $this->patchJson(route('api.application.nodes.update', ['node' => $node]), [\n            'name' => 'New Name',\n            'description' => 'New Description',\n            'location_id' => $location->id,\n            'fqdn' => 'new.example.com',\n            'scheme' => 'https',\n            'memory' => 100,\n            'memory_overallocate' => 10,\n            'disk' => 200,\n            'disk_overallocate' => 20,\n            'daemon_sftp' => 1101,\n            'daemon_listen' => 1102,\n        ])\n            ->assertOk()\n            ->assertJsonPath('object', 'node')\n            ->assertJsonPath('attributes.name', 'New Name')\n            ->assertJsonPath('attributes.description', 'New Description')\n            ->assertJsonPath('attributes.fqdn', 'new.example.com')\n            ->assertJsonPath('attributes.scheme', 'https')\n            ->assertJsonPath('attributes.memory', 100)\n            ->assertJsonPath('attributes.memory_overallocate', 10)\n            ->assertJsonPath('attributes.disk', 200)\n            ->assertJsonPath('attributes.disk_overallocate', 20)\n            ->assertJsonPath('attributes.daemon_sftp', 1101)\n            ->assertJsonPath('attributes.daemon_listen', 1102);\n\n        $this->assertEquals($location->id, $node->refresh()->location_id);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Application/Users/ExternalUserControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Application\\Users;\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Tests\\Integration\\Api\\Application\\ApplicationApiIntegrationTestCase;\n\nclass ExternalUserControllerTest extends ApplicationApiIntegrationTestCase\n{\n    /**\n     * Test that a user can be retrieved by their external ID.\n     */\n    public function testGetRemoteUser()\n    {\n        $user = User::factory()->create(['external_id' => Str::random()]);\n\n        $response = $this->getJson('/api/application/users/external/' . $user->external_id);\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => [\n                'id', 'external_id', 'uuid', 'username', 'email', 'first_name', 'last_name',\n                'language', 'root_admin', '2fa', 'created_at', 'updated_at',\n            ],\n        ]);\n\n        $response->assertJson([\n            'object' => 'user',\n            'attributes' => [\n                'id' => $user->id,\n                'external_id' => $user->external_id,\n                'uuid' => $user->uuid,\n                'username' => $user->username,\n                'email' => $user->email,\n                'first_name' => $user->name_first,\n                'last_name' => $user->name_last,\n                'language' => $user->language,\n                'root_admin' => (bool) $user->root_admin,\n                '2fa' => (bool) $user->totp_enabled,\n                'created_at' => $this->formatTimestamp($user->created_at),\n                'updated_at' => $this->formatTimestamp($user->updated_at),\n            ],\n        ], true);\n    }\n\n    /**\n     * Test that an invalid external ID returns a 404 error.\n     */\n    public function testGetMissingUser()\n    {\n        $response = $this->getJson('/api/application/users/external/nil');\n        $this->assertNotFoundJson($response);\n    }\n\n    /**\n     * Test that an authentication error occurs if a key does not have permission\n     * to access a resource.\n     */\n    public function testErrorReturnedIfNoPermission()\n    {\n        $user = User::factory()->create(['external_id' => Str::random()]);\n        $this->createNewDefaultApiKey($this->getApiUser(), ['r_users' => 0]);\n\n        $response = $this->getJson('/api/application/users/external/' . $user->external_id);\n        $this->assertAccessDeniedJson($response);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Application/Users/UserControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Application\\Users;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\nuse Pterodactyl\\Transformers\\Api\\Application\\UserTransformer;\nuse Pterodactyl\\Transformers\\Api\\Application\\ServerTransformer;\nuse Pterodactyl\\Tests\\Integration\\Api\\Application\\ApplicationApiIntegrationTestCase;\n\nclass UserControllerTest extends ApplicationApiIntegrationTestCase\n{\n    /**\n     * Test the response when requesting all users on the panel.\n     */\n    public function testGetUsers()\n    {\n        $user = User::factory()->create();\n\n        $response = $this->getJson('/api/application/users?per_page=60');\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2, 'data');\n        $response->assertJsonStructure([\n            'object',\n            'data' => [\n                ['object', 'attributes' => ['id', 'external_id', 'uuid', 'username', 'email', 'first_name', 'last_name', 'language', 'root_admin', '2fa', 'created_at', 'updated_at']],\n                ['object', 'attributes' => ['id', 'external_id', 'uuid', 'username', 'email', 'first_name', 'last_name', 'language', 'root_admin', '2fa', 'created_at', 'updated_at']],\n            ],\n            'meta' => ['pagination' => ['total', 'count', 'per_page', 'current_page', 'total_pages']],\n        ]);\n\n        $response\n            ->assertJson([\n                'object' => 'list',\n                'data' => [[], []],\n                'meta' => [\n                    'pagination' => [\n                        'total' => 2,\n                        'count' => 2,\n                        'per_page' => 60,\n                        'current_page' => 1,\n                        'total_pages' => 1,\n                    ],\n                ],\n            ])\n            ->assertJsonFragment([\n                'object' => 'user',\n                'attributes' => [\n                    'id' => $this->getApiUser()->id,\n                    'external_id' => $this->getApiUser()->external_id,\n                    'uuid' => $this->getApiUser()->uuid,\n                    'username' => $this->getApiUser()->username,\n                    'email' => $this->getApiUser()->email,\n                    'first_name' => $this->getApiUser()->name_first,\n                    'last_name' => $this->getApiUser()->name_last,\n                    'language' => $this->getApiUser()->language,\n                    'root_admin' => $this->getApiUser()->root_admin,\n                    '2fa' => (bool) $this->getApiUser()->totp_enabled,\n                    'created_at' => $this->formatTimestamp($this->getApiUser()->created_at),\n                    'updated_at' => $this->formatTimestamp($this->getApiUser()->updated_at),\n                ],\n            ])\n            ->assertJsonFragment([\n                'object' => 'user',\n                'attributes' => [\n                    'id' => $user->id,\n                    'external_id' => $user->external_id,\n                    'uuid' => $user->uuid,\n                    'username' => $user->username,\n                    'email' => $user->email,\n                    'first_name' => $user->name_first,\n                    'last_name' => $user->name_last,\n                    'language' => $user->language,\n                    'root_admin' => (bool) $user->root_admin,\n                    '2fa' => (bool) $user->totp_enabled,\n                    'created_at' => $this->formatTimestamp($user->created_at),\n                    'updated_at' => $this->formatTimestamp($user->updated_at),\n                ],\n            ]);\n    }\n\n    /**\n     * Test getting a single user.\n     */\n    public function testGetSingleUser()\n    {\n        $user = User::factory()->create();\n\n        $response = $this->getJson('/api/application/users/' . $user->id);\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => ['id', 'external_id', 'uuid', 'username', 'email', 'first_name', 'last_name', 'language', 'root_admin', '2fa', 'created_at', 'updated_at'],\n        ]);\n\n        $response->assertJson([\n            'object' => 'user',\n            'attributes' => [\n                'id' => $user->id,\n                'external_id' => $user->external_id,\n                'uuid' => $user->uuid,\n                'username' => $user->username,\n                'email' => $user->email,\n                'first_name' => $user->name_first,\n                'last_name' => $user->name_last,\n                'language' => $user->language,\n                'root_admin' => (bool) $user->root_admin,\n                '2fa' => (bool) $user->totp_enabled,\n                'created_at' => $this->formatTimestamp($user->created_at),\n                'updated_at' => $this->formatTimestamp($user->updated_at),\n            ],\n        ]);\n    }\n\n    /**\n     * Test that the correct relationships can be loaded.\n     */\n    public function testRelationshipsCanBeLoaded()\n    {\n        $user = User::factory()->create();\n        $server = $this->createServerModel(['user_id' => $user->id]);\n\n        $response = $this->getJson('/api/application/users/' . $user->id . '?include=servers');\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => [\n                'id', 'external_id', 'uuid', 'username', 'email', 'first_name', 'last_name', 'language', 'root_admin', '2fa', 'created_at', 'updated_at',\n                'relationships' => ['servers' => ['object', 'data' => [['object', 'attributes' => []]]]],\n            ],\n        ]);\n\n        $response->assertJsonFragment([\n            'object' => 'list',\n            'data' => [\n                [\n                    'object' => 'server',\n                    'attributes' => $this->getTransformer(ServerTransformer::class)->transform($server),\n                ],\n            ],\n        ]);\n    }\n\n    /**\n     * Test that attempting to load a relationship that the key does not have permission\n     * for returns a null object.\n     */\n    public function testKeyWithoutPermissionCannotLoadRelationship()\n    {\n        $this->createNewDefaultApiKey($this->getApiUser(), ['r_servers' => 0]);\n\n        $user = User::factory()->create();\n        $this->createServerModel(['user_id' => $user->id]);\n\n        $response = $this->getJson('/api/application/users/' . $user->id . '?include=servers');\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2)->assertJsonCount(1, 'attributes.relationships');\n        $response->assertJsonStructure([\n            'attributes' => [\n                'relationships' => [\n                    'servers' => ['object', 'attributes'],\n                ],\n            ],\n        ]);\n\n        // Just assert that we see the expected relationship IDs in the response.\n        $response->assertJson([\n            'attributes' => [\n                'relationships' => [\n                    'servers' => [\n                        'object' => 'null_resource',\n                        'attributes' => null,\n                    ],\n                ],\n            ],\n        ]);\n    }\n\n    /**\n     * Test that an invalid external ID returns a 404 error.\n     */\n    public function testGetMissingUser()\n    {\n        $response = $this->getJson('/api/application/users/nil');\n        $this->assertNotFoundJson($response);\n    }\n\n    /**\n     * Test that an authentication error occurs if a key does not have permission\n     * to access a resource.\n     */\n    public function testErrorReturnedIfNoPermission()\n    {\n        $user = User::factory()->create();\n        $this->createNewDefaultApiKey($this->getApiUser(), ['r_users' => 0]);\n\n        $response = $this->getJson('/api/application/users/' . $user->id);\n        $this->assertAccessDeniedJson($response);\n    }\n\n    /**\n     * Test that a user can be created.\n     */\n    public function testCreateUser()\n    {\n        $response = $this->postJson('/api/application/users', [\n            'username' => 'testuser',\n            'email' => 'test@example.com',\n            'first_name' => 'Test',\n            'last_name' => 'User',\n        ]);\n\n        $response->assertStatus(Response::HTTP_CREATED);\n        $response->assertJsonCount(3);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => ['id', 'external_id', 'uuid', 'username', 'email', 'first_name', 'last_name', 'language', 'root_admin', '2fa', 'created_at', 'updated_at'],\n            'meta' => ['resource'],\n        ]);\n\n        $this->assertDatabaseHas('users', ['username' => 'testuser', 'email' => 'test@example.com']);\n\n        $user = User::where('username', 'testuser')->first();\n        $response->assertJson([\n            'object' => 'user',\n            'attributes' => $this->getTransformer(UserTransformer::class)->transform($user),\n            'meta' => [\n                'resource' => route('api.application.users.view', $user->id),\n            ],\n        ], true);\n    }\n\n    /**\n     * Test that a user can be updated.\n     */\n    public function testUpdateUser()\n    {\n        $user = User::factory()->create();\n\n        $response = $this->patchJson('/api/application/users/' . $user->id, [\n            'username' => 'new.test.name',\n            'email' => 'new@emailtest.com',\n            'first_name' => $user->name_first,\n            'last_name' => $user->name_last,\n        ]);\n        $response->assertStatus(Response::HTTP_OK);\n        $response->assertJsonCount(2);\n        $response->assertJsonStructure([\n            'object',\n            'attributes' => ['id', 'external_id', 'uuid', 'username', 'email', 'first_name', 'last_name', 'language', 'root_admin', '2fa', 'created_at', 'updated_at'],\n        ]);\n\n        $this->assertDatabaseHas('users', ['username' => 'new.test.name', 'email' => 'new@emailtest.com']);\n        $user = $user->fresh();\n\n        $response->assertJson([\n            'object' => 'user',\n            'attributes' => $this->getTransformer(UserTransformer::class)->transform($user),\n        ]);\n    }\n\n    /**\n     * Test that a user can be deleted from the database.\n     */\n    public function testDeleteUser()\n    {\n        $user = User::factory()->create();\n        $this->assertDatabaseHas('users', ['id' => $user->id]);\n\n        $response = $this->delete('/api/application/users/' . $user->id);\n        $response->assertStatus(Response::HTTP_NO_CONTENT);\n\n        $this->assertDatabaseMissing('users', ['id' => $user->id]);\n    }\n\n    /**\n     * Test that an API key without write permissions cannot create, update, or\n     * delete a user model.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('userWriteEndpointsDataProvider')]\n    public function testApiKeyWithoutWritePermissions(string $method, string $url)\n    {\n        $this->createNewDefaultApiKey($this->getApiUser(), ['r_users' => AdminAcl::READ]);\n\n        if (str_contains($url, '{id}')) {\n            $user = User::factory()->create();\n            $url = str_replace('{id}', $user->id, $url);\n        }\n\n        $response = $this->$method($url);\n        $this->assertAccessDeniedJson($response);\n    }\n\n    /**\n     * Endpoints that should return a 403 error when the key does not have write\n     * permissions for user management.\n     */\n    public static function userWriteEndpointsDataProvider(): array\n    {\n        return [\n            ['postJson', '/api/application/users'],\n            ['patchJson', '/api/application/users/{id}'],\n            ['delete', '/api/application/users/{id}'],\n        ];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/AccountControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client;\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Subuser;\nuse Illuminate\\Support\\Facades\\Bus;\nuse Illuminate\\Support\\Facades\\Hash;\nuse Pterodactyl\\Jobs\\RevokeSftpAccessJob;\n\nclass AccountControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that the user's account details are returned from the account endpoint.\n     */\n    public function testAccountDetailsAreReturned()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n\n        $response = $this->actingAs($user)->get('/api/client/account');\n\n        $response->assertOk()->assertJson([\n            'object' => 'user',\n            'attributes' => [\n                'id' => $user->id,\n                'admin' => false,\n                'username' => $user->username,\n                'email' => $user->email,\n                'first_name' => $user->name_first,\n                'last_name' => $user->name_last,\n                'language' => $user->language,\n            ],\n        ]);\n    }\n\n    /**\n     * Test that the user's email address can be updated via the API.\n     */\n    public function testEmailIsUpdated()\n    {\n        $user = User::factory()->create();\n\n        $this->actingAs($user)\n            ->putJson('/api/client/account/email', [\n                'email' => $email = Str::random() . '@example.com',\n                'password' => 'password',\n            ])\n            ->assertNoContent();\n\n        $this->assertActivityFor('user:account.email-changed', $user, $user);\n        $this->assertDatabaseHas('users', ['id' => $user->id, 'email' => $email]);\n    }\n\n    public function testEmailChangeIsThrottled(): void\n    {\n        $users = User::factory()->count(2)->create();\n        $endpoint = route('api:client.account.update-email');\n\n        for ($i = 0; $i < 3; ++$i) {\n            $this->actingAs($users[0])\n                ->putJson($endpoint, ['email' => \"foo+{$i}@example.com\", 'password' => 'password'])\n                ->assertNoContent();\n        }\n\n        $this\n            ->putJson($endpoint, ['email' => 'bar@example.com', 'password' => 'password'])\n            ->assertTooManyRequests();\n\n        // The other user should still be able to update their email because the throttle\n        // is tied to the account, not to the IP address.\n        $this->actingAs($users[1])\n            ->putJson($endpoint, ['email' => 'bar+1@example.com', 'password' => 'password'])\n            ->assertNoContent();\n    }\n\n    /**\n     * Tests that an email is not updated if the password provided in the request is not\n     * valid for the account.\n     */\n    public function testEmailIsNotUpdatedWhenPasswordIsInvalid()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n\n        $response = $this->actingAs($user)->putJson('/api/client/account/email', [\n            'email' => 'hodor@example.com',\n            'password' => 'invalid',\n        ]);\n\n        $response->assertStatus(Response::HTTP_BAD_REQUEST);\n        $response->assertJsonPath('errors.0.code', 'InvalidPasswordProvidedException');\n        $response->assertJsonPath('errors.0.detail', '提供的密码对此帐户无效。');\n    }\n\n    /**\n     * Tests that an email is not updated if an invalid email address is passed through\n     * in the request.\n     */\n    public function testEmailIsNotUpdatedWhenNotValid()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n\n        $response = $this->actingAs($user)->putJson('/api/client/account/email', [\n            'email' => '',\n            'password' => 'password',\n        ]);\n\n        $response->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY);\n        $response->assertJsonPath('errors.0.meta.rule', 'required');\n        $response->assertJsonPath('errors.0.detail', 'email 不能为空。');\n\n        $response = $this->actingAs($user)->putJson('/api/client/account/email', [\n            'email' => 'invalid',\n            'password' => 'password',\n        ]);\n\n        $response->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY);\n        $response->assertJsonPath('errors.0.meta.rule', 'email');\n        $response->assertJsonPath('errors.0.detail', 'email 不是一个合法的邮箱。');\n    }\n\n    /**\n     * Test that the password for an account can be successfully updated.\n     */\n    public function testPasswordIsUpdated()\n    {\n        $user = User::factory()->create();\n\n        // Assign the user to two servers, one as the owner the other as a subuser, both\n        // on different nodes to ensure our logic fires off correctly and the user has their\n        // credentials revoked on both nodes.\n        $server = $this->createServerModel(['owner_id' => $user->id]);\n        $server2 = $this->createServerModel();\n        Subuser::factory()->for($server2)->for($user)->create();\n\n        $initialHash = $user->password;\n\n        Bus::fake([RevokeSftpAccessJob::class]);\n\n        $this->actingAs($user)\n            ->putJson('/api/client/account/password', [\n                'current_password' => 'password',\n                'password' => 'New_Password1',\n                'password_confirmation' => 'New_Password1',\n            ])\n            ->assertNoContent();\n\n        $user = $user->refresh();\n\n        $this->assertNotEquals($user->password, $initialHash);\n        $this->assertTrue(Hash::check('New_Password1', $user->password));\n        $this->assertFalse(Hash::check('password', $user->password));\n\n        $this->assertActivityFor('user:account.password-changed', $user, $user);\n        $this->assertNotEquals($server->node_id, $server2->node_id);\n\n        Bus::assertDispatchedTimes(RevokeSftpAccessJob::class, 2);\n        Bus::assertDispatched(fn (RevokeSftpAccessJob $job) => $job->user === $user->uuid && $job->target->is($server->node));\n        Bus::assertDispatched(fn (RevokeSftpAccessJob $job) => $job->user === $user->uuid && $job->target->is($server2->node));\n    }\n\n    /**\n     * Test that the password for an account is not updated if the current password is not\n     * provided correctly.\n     */\n    public function testPasswordIsNotUpdatedIfCurrentPasswordIsInvalid()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n\n        $response = $this->actingAs($user)->putJson('/api/client/account/password', [\n            'current_password' => 'invalid',\n            'password' => 'New_Password1',\n            'password_confirmation' => 'New_Password1',\n        ]);\n\n        $response->assertStatus(Response::HTTP_BAD_REQUEST);\n        $response->assertJsonPath('errors.0.code', 'InvalidPasswordProvidedException');\n        $response->assertJsonPath('errors.0.detail', '提供的密码对此帐户无效。');\n    }\n\n    /**\n     * Test that a validation error is returned to the user if no password is provided or if\n     * the password is below the minimum password length.\n     */\n    public function testErrorIsReturnedForInvalidRequestData()\n    {\n        $user = User::factory()->create();\n\n        $this->actingAs($user)->putJson('/api/client/account/password', [\n            'current_password' => 'password',\n        ])\n            ->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY)\n            ->assertJsonPath('errors.0.meta.rule', 'required');\n\n        $this->actingAs($user)->putJson('/api/client/account/password', [\n            'current_password' => 'password',\n            'password' => 'pass',\n            'password_confirmation' => 'pass',\n        ])\n            ->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY)\n            ->assertJsonPath('errors.0.meta.rule', 'min');\n    }\n\n    /**\n     * Test that a validation error is returned if the password passed in the request\n     * does not have a confirmation, or the confirmation is not the same as the password.\n     */\n    public function testErrorIsReturnedIfPasswordIsNotConfirmed()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n\n        $response = $this->actingAs($user)->putJson('/api/client/account/password', [\n            'current_password' => 'password',\n            'password' => 'New_Password1',\n            'password_confirmation' => 'Invalid_New_Password',\n        ]);\n\n        $response->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY);\n        $response->assertJsonPath('errors.0.meta.rule', 'confirmed');\n        $response->assertJsonPath('errors.0.detail', 'password 两次输入不一致。');\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/ApiKeyControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\ApiKey;\nuse Illuminate\\Support\\Facades\\Event;\nuse Pterodactyl\\Events\\ActivityLogged;\n\nclass ApiKeyControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Cleanup after tests.\n     */\n    protected function tearDown(): void\n    {\n        ApiKey::query()->forceDelete();\n\n        parent::tearDown();\n    }\n\n    /**\n     * Test that the client's API key can be returned successfully.\n     */\n    public function testApiKeysAreReturned()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n        /** @var ApiKey $key */\n        $key = ApiKey::factory()->for($user)->create([\n            'key_type' => ApiKey::TYPE_ACCOUNT,\n        ]);\n\n        $response = $this->actingAs($user)->get('/api/client/account/api-keys')\n            ->assertOk()\n            ->assertJsonPath('object', 'list')\n            ->assertJsonPath('data.0.object', ApiKey::RESOURCE_NAME);\n\n        $this->assertJsonTransformedWith($response->json('data.0.attributes'), $key);\n    }\n\n    /**\n     * Test that an API key can be created for the client account. This also checks that the\n     * API key secret is returned as metadata in the response since it will not be returned\n     * after that point.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('validIPAddressDataProvider')]\n    public function testApiKeyCanBeCreatedForAccount(array $data)\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n\n        // Small subtest to ensure we're always comparing the  number of keys to the\n        // specific logged in account, and not just the total number of keys stored in\n        // the database.\n        ApiKey::factory()->times(10)->create([\n            'user_id' => User::factory()->create()->id,\n            'key_type' => ApiKey::TYPE_ACCOUNT,\n        ]);\n\n        $response = $this->actingAs($user)->postJson('/api/client/account/api-keys', [\n            'description' => 'Test Description',\n            'allowed_ips' => $data,\n        ])\n            ->assertOk()\n            ->assertJsonPath('object', ApiKey::RESOURCE_NAME);\n\n        /** @var ApiKey $key */\n        $key = ApiKey::query()->where('identifier', $response->json('attributes.identifier'))->firstOrFail();\n\n        $this->assertJsonTransformedWith($response->json('attributes'), $key);\n        $response->assertJsonPath('meta.secret_token', decrypt($key->token));\n\n        $this->assertActivityFor('user:api-key.create', $user, [$key, $user]);\n    }\n\n    /**\n     * Block requests to create an API key specifying more than 50 IP addresses.\n     */\n    public function testApiKeyCannotSpecifyMoreThanFiftyIps()\n    {\n        $ips = [];\n        for ($i = 0; $i < 100; ++$i) {\n            $ips[] = '127.0.0.' . $i;\n        }\n\n        $this->actingAs(User::factory()->create())\n            ->postJson('/api/client/account/api-keys', [\n                'description' => 'Test Data',\n                'allowed_ips' => $ips,\n            ])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.detail', 'allowed ips 最多只有 50 个单元。');\n    }\n\n    /**\n     * Test that no more than 25 API keys can exist at any one time for an account. This prevents\n     * a DoS attack vector against the panel.\n     *\n     * @see https://github.com/pterodactyl/panel/security/advisories/GHSA-pjmh-7xfm-r4x9\n     * @see https://github.com/pterodactyl/panel/issues/4394\n     */\n    public function testApiKeyLimitIsApplied()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n        ApiKey::factory()->times(25)->for($user)->create([\n            'key_type' => ApiKey::TYPE_ACCOUNT,\n        ]);\n\n        $this->actingAs($user)->postJson('/api/client/account/api-keys', [\n            'description' => 'Test Description',\n            'allowed_ips' => ['127.0.0.1'],\n        ])\n            ->assertStatus(Response::HTTP_BAD_REQUEST)\n            ->assertJsonPath('errors.0.code', 'DisplayException')\n            ->assertJsonPath('errors.0.detail', '您的帐户已达到 API 密钥数量限制。');\n    }\n\n    /**\n     * Test that a bad request results in a validation error being returned by the API.\n     *\n     * @see https://github.com/pterodactyl/panel/issues/2457\n     */\n    public function testValidationErrorIsReturnedForBadRequests()\n    {\n        $this->actingAs(User::factory()->create());\n\n        $this->postJson('/api/client/account/api-keys', [\n            'description' => '',\n            'allowed_ips' => ['127.0.0.1'],\n        ])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.meta.rule', 'required')\n            ->assertJsonPath('errors.0.detail', 'description 不能为空。');\n\n        $this->postJson('/api/client/account/api-keys', [\n            'description' => str_repeat('a', 501),\n            'allowed_ips' => ['127.0.0.1'],\n        ])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.meta.rule', 'max')\n            ->assertJsonPath('errors.0.detail', 'description 不能大于 500 个字符。');\n\n        $this->postJson('/api/client/account/api-keys', [\n            'description' => 'Foobar',\n            'allowed_ips' => ['hodor', '127.0.0.1', 'hodor/24'],\n        ])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.detail', '\"hodor\" is not a valid IP address or CIDR range.')\n            ->assertJsonPath('errors.0.meta.source_field', 'allowed_ips.0')\n            ->assertJsonPath('errors.1.detail', '\"hodor/24\" is not a valid IP address or CIDR range.')\n            ->assertJsonPath('errors.1.meta.source_field', 'allowed_ips.2');\n    }\n\n    /**\n     * Tests that an API key can be deleted from the account.\n     */\n    public function testApiKeyCanBeDeleted()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n        /** @var ApiKey $key */\n        $key = ApiKey::factory()->for($user)->create([\n            'key_type' => ApiKey::TYPE_ACCOUNT,\n        ]);\n\n        $response = $this->actingAs($user)->delete('/api/client/account/api-keys/' . $key->identifier);\n        $response->assertStatus(Response::HTTP_NO_CONTENT);\n\n        $this->assertDatabaseMissing('api_keys', ['id' => $key->id]);\n        $this->assertActivityFor('user:api-key.delete', $user, $user);\n    }\n\n    /**\n     * Test that trying to delete an API key that does not exist results in a 404.\n     */\n    public function testNonExistentApiKeyDeletionReturns404Error()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n        /** @var ApiKey $key */\n        $key = ApiKey::factory()->create([\n            'user_id' => $user->id,\n            'key_type' => ApiKey::TYPE_ACCOUNT,\n        ]);\n\n        $response = $this->actingAs($user)->delete('/api/client/account/api-keys/1234');\n        $response->assertNotFound();\n\n        $this->assertDatabaseHas('api_keys', ['id' => $key->id]);\n        Event::assertNotDispatched(ActivityLogged::class);\n    }\n\n    /**\n     * Test that an API key that exists on the system cannot be deleted if the user\n     * who created it is not the authenticated user.\n     */\n    public function testApiKeyBelongingToAnotherUserCannotBeDeleted()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n        /** @var User $user2 */\n        $user2 = User::factory()->create();\n        /** @var ApiKey $key */\n        $key = ApiKey::factory()->for($user2)->create([\n            'key_type' => ApiKey::TYPE_ACCOUNT,\n        ]);\n\n        $this->actingAs($user)\n            ->deleteJson('/api/client/account/api-keys/' . $key->identifier)\n            ->assertNotFound();\n\n        $this->assertDatabaseHas('api_keys', ['id' => $key->id]);\n        Event::assertNotDispatched(ActivityLogged::class);\n    }\n\n    /**\n     * Tests that an application API key also belonging to the logged-in user cannot be\n     * deleted through this endpoint if it exists.\n     */\n    public function testApplicationApiKeyCannotBeDeleted()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n        /** @var ApiKey $key */\n        $key = ApiKey::factory()->for($user)->create([\n            'key_type' => ApiKey::TYPE_APPLICATION,\n        ]);\n\n        $this->actingAs($user)\n            ->deleteJson('/api/client/account/api-keys/' . $key->identifier)\n            ->assertNotFound();\n\n        $this->assertDatabaseHas('api_keys', ['id' => $key->id]);\n    }\n\n    /**\n     * Provides some different IP address combinations that can be used when\n     * testing that we accept the expected IP values.\n     */\n    public static function validIPAddressDataProvider(): array\n    {\n        return [\n            [[]],\n            [['127.0.0.1']],\n            [['127.0.0.1', '::1']],\n            [['::ffff:7f00:1']],\n            [['127.0.0.1', '192.168.1.100', '192.168.10.10/28']],\n            [['127.0.0.1/32', '192.168.100.100/27', '::1', '::1/128']],\n        ];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/ClientApiIntegrationTestCase.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client;\n\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\Task;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Model;\nuse Pterodactyl\\Models\\Backup;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\Location;\nuse Pterodactyl\\Models\\Schedule;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Pterodactyl\\Tests\\Integration\\TestResponse;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Illuminate\\Database\\Eloquent\\Model as EloquentModel;\nuse Pterodactyl\\Transformers\\Api\\Client\\BaseClientTransformer;\n\nabstract class ClientApiIntegrationTestCase extends IntegrationTestCase\n{\n    /**\n     * Cleanup after running tests.\n     */\n    protected function tearDown(): void\n    {\n        Database::query()->forceDelete();\n        DatabaseHost::query()->forceDelete();\n        Backup::query()->forceDelete();\n        Server::query()->forceDelete();\n        Node::query()->forceDelete();\n        Location::query()->forceDelete();\n        User::query()->forceDelete();\n\n        parent::tearDown();\n    }\n\n    /**\n     * Override the default createTestResponse from Illuminate so that we can\n     * just dump 500-level errors to the screen in the tests without having\n     * to keep re-assigning variables.\n     *\n     * @param \\Illuminate\\Http\\Response $response\n     * @param \\Illuminate\\Http\\Request $request\n     *\n     * @return \\Illuminate\\Testing\\TestResponse\n     */\n    protected function createTestResponse($response, $request)\n    {\n        return TestResponse::fromBaseResponse($response, $request);\n    }\n\n    /**\n     * Returns a link to the specific resource using the client API.\n     */\n    protected function link(mixed $model, ?string $append = null): string\n    {\n        switch (get_class($model)) {\n            case Server::class:\n                $link = \"/api/client/servers/$model->uuid\";\n                break;\n            case Schedule::class:\n                $link = \"/api/client/servers/{$model->server->uuid}/schedules/$model->id\";\n                break;\n            case Task::class:\n                $link = \"/api/client/servers/{$model->schedule->server->uuid}/schedules/{$model->schedule->id}/tasks/$model->id\";\n                break;\n            case Allocation::class:\n                $link = \"/api/client/servers/{$model->server->uuid}/network/allocations/$model->id\";\n                break;\n            case Backup::class:\n                $link = \"/api/client/servers/{$model->server->uuid}/backups/$model->uuid\";\n                break;\n            default:\n                throw new \\InvalidArgumentException(sprintf('Cannot create link for Model of type %s', class_basename($model)));\n        }\n\n        return $link . ($append ? '/' . ltrim($append, '/') : '');\n    }\n\n    /**\n     * Asserts that the data passed through matches the output of the data from the transformer. This\n     * will remove the \"relationships\" key when performing the comparison.\n     */\n    protected function assertJsonTransformedWith(array $data, Model|EloquentModel $model)\n    {\n        $reflect = new \\ReflectionClass($model);\n        $transformer = sprintf('\\\\Pterodactyl\\\\Transformers\\\\Api\\\\Client\\\\%sTransformer', $reflect->getShortName());\n\n        $transformer = new $transformer();\n        $this->assertInstanceOf(BaseClientTransformer::class, $transformer);\n\n        $this->assertSame(\n            $transformer->transform($model),\n            Collection::make($data)->except(['relationships'])->toArray()\n        );\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/ClientControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Models\\Permission;\n\nclass ClientControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that only the servers a logged-in user is assigned to are returned by the\n     * API endpoint. Obviously there are cases such as being an administrator or being\n     * a subuser, but for this test we just want to test a basic scenario and pretend\n     * subusers do not exist at all.\n     */\n    public function testOnlyLoggedInUsersServersAreReturned()\n    {\n        /** @var \\Pterodactyl\\Models\\User[] $users */\n        $users = User::factory()->times(3)->create();\n\n        /** @var \\Pterodactyl\\Models\\Server[] $servers */\n        $servers = [\n            $this->createServerModel(['user_id' => $users[0]->id]),\n            $this->createServerModel(['user_id' => $users[1]->id]),\n            $this->createServerModel(['user_id' => $users[2]->id]),\n        ];\n\n        $response = $this->actingAs($users[0])->getJson('/api/client');\n\n        $response->assertOk();\n        $response->assertJsonPath('object', 'list');\n        $response->assertJsonPath('data.0.object', Server::RESOURCE_NAME);\n        $response->assertJsonPath('data.0.attributes.identifier', $servers[0]->uuidShort);\n        $response->assertJsonPath('data.0.attributes.server_owner', true);\n        $response->assertJsonPath('meta.pagination.total', 1);\n        $response->assertJsonPath('meta.pagination.per_page', 50);\n    }\n\n    /**\n     * Test that using ?filter[*]=name|uuid returns any server matching that name or UUID\n     * with the search filters.\n     */\n    public function testServersAreFilteredUsingNameAndUuidInformation()\n    {\n        /** @var \\Pterodactyl\\Models\\User[] $users */\n        $users = User::factory()->times(2)->create();\n        $users[0]->update(['root_admin' => true]);\n\n        /** @var \\Pterodactyl\\Models\\Server[] $servers */\n        $servers = [\n            $this->createServerModel(['user_id' => $users[0]->id, 'name' => 'Julia']),\n            $this->createServerModel(['user_id' => $users[1]->id, 'uuidShort' => '12121212', 'name' => 'Janice']),\n            $this->createServerModel(['user_id' => $users[1]->id, 'uuid' => Uuid::uuid4()->toString(), 'external_id' => 'ext123', 'name' => 'Julia']),\n            $this->createServerModel(['user_id' => $users[1]->id, 'uuid' => Uuid::uuid4()->toString(), 'name' => 'Jennifer']),\n        ];\n\n        $this->actingAs($users[1])->getJson('/api/client?filter[*]=Julia')\n            ->assertOk()\n            ->assertJsonCount(1, 'data')\n            ->assertJsonPath('data.0.attributes.identifier', $servers[2]->uuidShort);\n\n        $this->actingAs($users[1])->getJson('/api/client?filter[*]=ext123')\n            ->assertOk()\n            ->assertJsonCount(1, 'data')\n            ->assertJsonPath('data.0.attributes.identifier', $servers[2]->uuidShort);\n\n        $this->actingAs($users[1])->getJson('/api/client?filter[*]=ext123')\n            ->assertOk()\n            ->assertJsonCount(1, 'data')\n            ->assertJsonPath('data.0.attributes.identifier', $servers[2]->uuidShort);\n\n        $this->actingAs($users[1])->getJson('/api/client?filter[*]=12121212')\n            ->assertOk()\n            ->assertJsonCount(1, 'data')\n            ->assertJsonPath('data.0.attributes.identifier', $servers[1]->uuidShort);\n\n        $this->actingAs($users[1])->getJson(\"/api/client?filter[*]={$servers[2]->uuidShort}\")\n            ->assertOk()\n            ->assertJsonCount(1, 'data')\n            ->assertJsonPath('data.0.attributes.identifier', $servers[2]->uuidShort);\n\n        $this->actingAs($users[1])->getJson('/api/client?filter[*]=88788878-abcd')\n            ->assertOk()\n            ->assertJsonCount(0, 'data');\n\n        $this->actingAs($users[0])->getJson('/api/client?filter[*]=Julia&type=admin-all')\n            ->assertOk()\n            ->assertJsonCount(2, 'data')\n            ->assertJsonPath('data.0.attributes.identifier', $servers[0]->uuidShort)\n            ->assertJsonPath('data.1.attributes.identifier', $servers[2]->uuidShort);\n    }\n\n    /**\n     * Test that using ?filter[*]=:25565 or ?filter[*]=192.168.1.1:25565 returns only those servers\n     * with the same allocation for the given user.\n     */\n    public function testServersAreFilteredUsingAllocationInformation()\n    {\n        /** @var User $user */\n        /** @var Server $server */\n        [$user, $server] = $this->generateTestAccount();\n        $server2 = $this->createServerModel(['user_id' => $user->id, 'node_id' => $server->node_id]);\n\n        $allocation = Allocation::factory()->create(['node_id' => $server->node_id, 'server_id' => $server->id, 'ip' => '192.168.1.1', 'port' => 25565]);\n        $allocation2 = Allocation::factory()->create(['node_id' => $server->node_id, 'server_id' => $server2->id, 'ip' => '192.168.1.1', 'port' => 25570]);\n\n        $server->update(['allocation_id' => $allocation->id]);\n        $server2->update(['allocation_id' => $allocation2->id]);\n\n        $server->refresh();\n        $server2->refresh();\n\n        $this->actingAs($user)->getJson('/api/client?filter[*]=192.168.1.1')\n            ->assertOk()\n            ->assertJsonCount(2, 'data')\n            ->assertJsonPath('data.0.attributes.identifier', $server->uuidShort)\n            ->assertJsonPath('data.1.attributes.identifier', $server2->uuidShort);\n\n        $this->actingAs($user)->getJson('/api/client?filter[*]=192.168.1.1:25565')\n            ->assertOk()\n            ->assertJsonCount(1, 'data')\n            ->assertJsonPath('data.0.attributes.identifier', $server->uuidShort);\n\n        $this->actingAs($user)->getJson('/api/client?filter[*]=:25570')\n            ->assertOk()\n            ->assertJsonCount(1, 'data')\n            ->assertJsonPath('data.0.attributes.identifier', $server2->uuidShort);\n\n        $this->actingAs($user)->getJson('/api/client?filter[*]=:255')\n            ->assertOk()\n            ->assertJsonCount(2, 'data')\n            ->assertJsonPath('data.0.attributes.identifier', $server->uuidShort)\n            ->assertJsonPath('data.1.attributes.identifier', $server2->uuidShort);\n    }\n\n    /**\n     * Test that servers where the user is a subuser are returned by default in the API call.\n     */\n    public function testServersUserIsASubuserOfAreReturned()\n    {\n        /** @var \\Pterodactyl\\Models\\User[] $users */\n        $users = User::factory()->times(3)->create();\n        $servers = [\n            $this->createServerModel(['user_id' => $users[0]->id]),\n            $this->createServerModel(['user_id' => $users[1]->id]),\n            $this->createServerModel(['user_id' => $users[2]->id]),\n        ];\n\n        // Set user 0 as a subuser of server 1. Thus, we should get two servers\n        // back in the response when making the API call as user 0.\n        Subuser::query()->create([\n            'user_id' => $users[0]->id,\n            'server_id' => $servers[1]->id,\n            'permissions' => [Permission::ACTION_WEBSOCKET_CONNECT],\n        ]);\n\n        $response = $this->actingAs($users[0])->getJson('/api/client');\n\n        $response->assertOk();\n        $response->assertJsonCount(2, 'data');\n        $response->assertJsonPath('data.0.attributes.server_owner', true);\n        $response->assertJsonPath('data.0.attributes.identifier', $servers[0]->uuidShort);\n        $response->assertJsonPath('data.1.attributes.server_owner', false);\n        $response->assertJsonPath('data.1.attributes.identifier', $servers[1]->uuidShort);\n    }\n\n    /**\n     * Returns only servers that the user owns, not servers they are a subuser of.\n     */\n    public function testFilterOnlyOwnerServers()\n    {\n        /** @var \\Pterodactyl\\Models\\User[] $users */\n        $users = User::factory()->times(3)->create();\n        $servers = [\n            $this->createServerModel(['user_id' => $users[0]->id]),\n            $this->createServerModel(['user_id' => $users[1]->id]),\n            $this->createServerModel(['user_id' => $users[2]->id]),\n        ];\n\n        // Set user 0 as a subuser of server 1. Thus, we should get two servers\n        // back in the response when making the API call as user 0.\n        Subuser::query()->create([\n            'user_id' => $users[0]->id,\n            'server_id' => $servers[1]->id,\n            'permissions' => [Permission::ACTION_WEBSOCKET_CONNECT],\n        ]);\n\n        $response = $this->actingAs($users[0])->getJson('/api/client?type=owner');\n\n        $response->assertOk();\n        $response->assertJsonCount(1, 'data');\n        $response->assertJsonPath('data.0.attributes.server_owner', true);\n        $response->assertJsonPath('data.0.attributes.identifier', $servers[0]->uuidShort);\n    }\n\n    /**\n     * Tests that the permissions from the Panel are returned correctly.\n     */\n    public function testPermissionsAreReturned()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n\n        $this->actingAs($user)\n            ->getJson('/api/client/permissions')\n            ->assertOk()\n            ->assertJson([\n                'object' => 'system_permissions',\n                'attributes' => [\n                    'permissions' => Permission::permissions()->toArray(),\n                ],\n            ]);\n    }\n\n    /**\n     * Test that only servers a user can access because they are an administrator are returned. This\n     * will always exclude any servers they can see because they're the owner or a subuser of the server.\n     */\n    public function testOnlyAdminLevelServersAreReturned()\n    {\n        /** @var \\Pterodactyl\\Models\\User[] $users */\n        $users = User::factory()->times(4)->create();\n        $users[0]->update(['root_admin' => true]);\n\n        $servers = [\n            $this->createServerModel(['user_id' => $users[0]->id]),\n            $this->createServerModel(['user_id' => $users[1]->id]),\n            $this->createServerModel(['user_id' => $users[2]->id]),\n            $this->createServerModel(['user_id' => $users[3]->id]),\n        ];\n\n        Subuser::query()->create([\n            'user_id' => $users[0]->id,\n            'server_id' => $servers[1]->id,\n            'permissions' => [Permission::ACTION_WEBSOCKET_CONNECT],\n        ]);\n\n        // Only servers 2 & 3 (0 indexed) should be returned by the API at this point. The user making\n        // the request is the owner of server 0, and a subuser of server 1, so they should be excluded.\n        $response = $this->actingAs($users[0])->getJson('/api/client?type=admin');\n\n        $response->assertOk();\n        $response->assertJsonCount(2, 'data');\n\n        $response->assertJsonPath('data.0.attributes.server_owner', false);\n        $response->assertJsonPath('data.0.attributes.identifier', $servers[2]->uuidShort);\n        $response->assertJsonPath('data.1.attributes.server_owner', false);\n        $response->assertJsonPath('data.1.attributes.identifier', $servers[3]->uuidShort);\n    }\n\n    /**\n     * Test that all servers a user can access as an admin are returned if using ?filter=admin-all.\n     */\n    public function testAllServersAreReturnedToAdmin()\n    {\n        /** @var \\Pterodactyl\\Models\\User[] $users */\n        $users = User::factory()->times(4)->create();\n        $users[0]->update(['root_admin' => true]);\n\n        $servers = [\n            $this->createServerModel(['user_id' => $users[0]->id]),\n            $this->createServerModel(['user_id' => $users[1]->id]),\n            $this->createServerModel(['user_id' => $users[2]->id]),\n            $this->createServerModel(['user_id' => $users[3]->id]),\n        ];\n\n        Subuser::query()->create([\n            'user_id' => $users[0]->id,\n            'server_id' => $servers[1]->id,\n            'permissions' => [Permission::ACTION_WEBSOCKET_CONNECT],\n        ]);\n\n        // All servers should be returned.\n        $response = $this->actingAs($users[0])->getJson('/api/client?type=admin-all');\n\n        $response->assertOk();\n        $response->assertJsonCount(4, 'data');\n    }\n\n    /**\n     * Test that no servers get returned if the user requests all admin level servers by using\n     * ?type=admin or ?type=admin-all in the request.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('filterTypeDataProvider')]\n    public function testNoServersAreReturnedIfAdminFilterIsPassedByRegularUser(string $type)\n    {\n        /** @var \\Pterodactyl\\Models\\User[] $users */\n        $users = User::factory()->times(3)->create();\n\n        $this->createServerModel(['user_id' => $users[0]->id]);\n        $this->createServerModel(['user_id' => $users[1]->id]);\n        $this->createServerModel(['user_id' => $users[2]->id]);\n\n        $response = $this->actingAs($users[0])->getJson('/api/client?type=' . $type);\n\n        $response->assertOk();\n        $response->assertJsonCount(0, 'data');\n    }\n\n    /**\n     * Test that a subuser without the allocation.read permission is only able to see the primary\n     * allocation for the server.\n     */\n    public function testOnlyPrimaryAllocationIsReturnedToSubuser()\n    {\n        /** @var Server $server */\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_WEBSOCKET_CONNECT]);\n        $server->allocation->notes = 'Test notes';\n        $server->allocation->save();\n\n        Allocation::factory()->times(2)->create([\n            'node_id' => $server->node_id,\n            'server_id' => $server->id,\n        ]);\n\n        $server->refresh();\n        $response = $this->actingAs($user)->getJson('/api/client');\n\n        $response->assertOk();\n        $response->assertJsonCount(1, 'data');\n        $response->assertJsonPath('data.0.attributes.server_owner', false);\n        $response->assertJsonPath('data.0.attributes.uuid', $server->uuid);\n        $response->assertJsonCount(1, 'data.0.attributes.relationships.allocations.data');\n        $response->assertJsonPath('data.0.attributes.relationships.allocations.data.0.attributes.id', $server->allocation->id);\n        $response->assertJsonPath('data.0.attributes.relationships.allocations.data.0.attributes.notes', null);\n    }\n\n    public static function filterTypeDataProvider(): array\n    {\n        return [['admin'], ['admin-all']];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/SSHKeyControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client;\n\nuse phpseclib3\\Crypt\\EC;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\UserSSHKey;\n\nclass SSHKeyControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that only the SSH keys for the authenticated user are returned.\n     */\n    public function testSSHKeysAreReturned()\n    {\n        $user = User::factory()->create();\n        $user2 = User::factory()->create();\n\n        $key = UserSSHKey::factory()->for($user)->create();\n        UserSSHKey::factory()->for($user2)->rsa()->create();\n\n        $this->actingAs($user);\n        $response = $this->getJson('/api/client/account/ssh-keys')\n            ->assertOk()\n            ->assertJsonPath('object', 'list')\n            ->assertJsonPath('data.0.object', UserSSHKey::RESOURCE_NAME);\n\n        $this->assertJsonTransformedWith($response->json('data.0.attributes'), $key);\n    }\n\n    /**\n     * Test that a user's SSH key can be deleted, and that passing the fingerprint\n     * of another user's SSH key won't delete that key.\n     */\n    public function testSSHKeyCanBeDeleted()\n    {\n        $user = User::factory()->create();\n        $user2 = User::factory()->create();\n\n        $key = UserSSHKey::factory()->for($user)->create();\n        $key2 = UserSSHKey::factory()->for($user2)->create();\n\n        $endpoint = '/api/client/account/ssh-keys/remove';\n\n        $this->actingAs($user);\n        $this->postJson($endpoint)\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.meta', ['source_field' => 'fingerprint', 'rule' => 'required']);\n\n        $this->postJson($endpoint, ['fingerprint' => $key->fingerprint])->assertNoContent();\n\n        $this->assertSoftDeleted($key);\n        $this->assertNotSoftDeleted($key2);\n\n        $this->postJson($endpoint, ['fingerprint' => $key->fingerprint])->assertNoContent();\n        $this->postJson($endpoint, ['fingerprint' => $key2->fingerprint])->assertNoContent();\n\n        $this->assertNotSoftDeleted($key2);\n    }\n\n    public function testDSAKeyIsRejected()\n    {\n        $user = User::factory()->create();\n        $key = UserSSHKey::factory()->dsa()->make();\n\n        $this->actingAs($user)->postJson('/api/client/account/ssh-keys', [\n            'name' => 'Name',\n            'public_key' => $key->public_key,\n        ])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.detail', 'DSA keys are not supported.');\n\n        $this->assertEquals(0, $user->sshKeys()->count());\n    }\n\n    public function testWeakRSAKeyIsRejected()\n    {\n        $user = User::factory()->create();\n        $key = UserSSHKey::factory()->rsa(true)->make();\n\n        $this->actingAs($user)->postJson('/api/client/account/ssh-keys', [\n            'name' => 'Name',\n            'public_key' => $key->public_key,\n        ])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.detail', 'RSA keys must be at least 2048 bytes in length.');\n\n        $this->assertEquals(0, $user->sshKeys()->count());\n    }\n\n    public function testInvalidOrPrivateKeyIsRejected()\n    {\n        $user = User::factory()->create();\n\n        $this->actingAs($user)->postJson('/api/client/account/ssh-keys', [\n            'name' => 'Name',\n            'public_key' => 'invalid',\n        ])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.detail', 'The public key provided is not valid.');\n\n        $this->assertEquals(0, $user->sshKeys()->count());\n\n        $key = EC::createKey('Ed25519');\n        $this->actingAs($user)->postJson('/api/client/account/ssh-keys', [\n            'name' => 'Name',\n            'public_key' => $key->toString('PKCS8'),\n        ])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.detail', 'The public key provided is not valid.');\n    }\n\n    public function testPublicKeyCanBeStored()\n    {\n        $user = User::factory()->create();\n        $key = UserSSHKey::factory()->make();\n\n        $this->actingAs($user)->postJson('/api/client/account/ssh-keys', [\n            'name' => 'Name',\n            'public_key' => $key->public_key,\n        ])\n            ->assertOk()\n            ->assertJsonPath('object', UserSSHKey::RESOURCE_NAME)\n            ->assertJsonPath('attributes.public_key', $key->public_key);\n\n        $this->assertCount(1, $user->sshKeys);\n        $this->assertEquals($key->public_key, $user->sshKeys[0]->public_key);\n    }\n\n    public function testPublicKeyThatAlreadyExistsCannotBeAddedASecondTime()\n    {\n        $user = User::factory()->create();\n        $key = UserSSHKey::factory()->for($user)->create();\n\n        $this->actingAs($user)->postJson('/api/client/account/ssh-keys', [\n            'name' => 'Name',\n            'public_key' => $key->public_key,\n        ])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.detail', 'The public key provided already exists on your account.');\n\n        $this->assertEquals(1, $user->sshKeys()->count());\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Allocation/AllocationAuthorizationTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Allocation;\n\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass AllocationAuthorizationTest extends ClientApiIntegrationTestCase\n{\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('methodDataProvider')]\n    public function testAccessToAServersAllocationsIsRestrictedProperly(string $method, string $endpoint)\n    {\n        // The API $user is the owner of $server1.\n        [$user, $server1] = $this->generateTestAccount();\n        // Will be a subuser of $server2.\n        $server2 = $this->createServerModel();\n        // And as no access to $server3.\n        $server3 = $this->createServerModel();\n\n        // Set the API $user as a subuser of server 2, but with no permissions\n        // to do anything with the allocations for that server.\n        Subuser::factory()->create(['server_id' => $server2->id, 'user_id' => $user->id]);\n\n        $allocation1 = Allocation::factory()->create(['server_id' => $server1->id, 'node_id' => $server1->node_id]);\n        $allocation2 = Allocation::factory()->create(['server_id' => $server2->id, 'node_id' => $server2->node_id]);\n        $allocation3 = Allocation::factory()->create(['server_id' => $server3->id, 'node_id' => $server3->node_id]);\n\n        // This is the only valid call for this test, accessing the allocation for the same\n        // server that the API user is the owner of.\n        $response = $this->actingAs($user)->json($method, $this->link($server1, '/network/allocations/' . $allocation1->id . $endpoint));\n        $this->assertTrue($response->status() <= 204 || $response->status() === 400 || $response->status() === 422);\n\n        // This request fails because the allocation is valid for that server but the user\n        // making the request is not authorized to perform that action.\n        $this->actingAs($user)->json($method, $this->link($server2, '/network/allocations/' . $allocation2->id . $endpoint))->assertForbidden();\n\n        // Both of these should report a 404 error due to the allocations being linked to\n        // servers that are not the same as the server in the request, or are assigned\n        // to a server for which the user making the request has no access to.\n        $this->actingAs($user)->json($method, $this->link($server1, '/network/allocations/' . $allocation2->id . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server1, '/network/allocations/' . $allocation3->id . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server2, '/network/allocations/' . $allocation3->id . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server3, '/network/allocations/' . $allocation3->id . $endpoint))->assertNotFound();\n    }\n\n    public static function methodDataProvider(): array\n    {\n        return [\n            ['POST', ''],\n            ['DELETE', ''],\n            ['POST', '/primary'],\n        ];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Allocation/CreateNewAllocationTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Allocation;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass CreateNewAllocationTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        config()->set('pterodactyl.client_features.allocations.enabled', true);\n        config()->set('pterodactyl.client_features.allocations.range_start', 5000);\n        config()->set('pterodactyl.client_features.allocations.range_end', 5050);\n    }\n\n    /**\n     * Tests that a new allocation can be properly assigned to a server.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionDataProvider')]\n    public function testNewAllocationCanBeAssignedToServer(array $permission)\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount($permission);\n        $server->update(['allocation_limit' => 2]);\n\n        $response = $this->actingAs($user)->postJson($this->link($server, '/network/allocations'));\n        $response->assertJsonPath('object', Allocation::RESOURCE_NAME);\n\n        $matched = Allocation::query()->findOrFail($response->json('attributes.id'));\n\n        $this->assertSame($server->id, $matched->server_id);\n        $this->assertJsonTransformedWith($response->json('attributes'), $matched);\n    }\n\n    /**\n     * Test that a user without the required permissions cannot create an allocation for\n     * the server instance.\n     */\n    public function testAllocationCannotBeCreatedIfUserDoesNotHavePermission()\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_ALLOCATION_UPDATE]);\n        $server->update(['allocation_limit' => 2]);\n\n        $this->actingAs($user)->postJson($this->link($server, '/network/allocations'))->assertForbidden();\n    }\n\n    /**\n     * Test that an error is returned to the user if this feature is not enabled on the system.\n     */\n    public function testAllocationCannotBeCreatedIfNotEnabled()\n    {\n        config()->set('pterodactyl.client_features.allocations.enabled', false);\n\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount();\n        $server->update(['allocation_limit' => 2]);\n\n        $this->actingAs($user)->postJson($this->link($server, '/network/allocations'))\n            ->assertStatus(Response::HTTP_BAD_REQUEST)\n            ->assertJsonPath('errors.0.code', 'AutoAllocationNotEnabledException')\n            ->assertJsonPath('errors.0.detail', '此实例未启用服务器自动分配功能。');\n    }\n\n    /**\n     * Test that an allocation cannot be created if the server has reached its allocation limit.\n     */\n    public function testAllocationCannotBeCreatedIfServerIsAtLimit()\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount();\n        $server->update(['allocation_limit' => 1]);\n\n        $this->actingAs($user)->postJson($this->link($server, '/network/allocations'))\n            ->assertStatus(Response::HTTP_BAD_REQUEST)\n            ->assertJsonPath('errors.0.code', 'DisplayException')\n            ->assertJsonPath('errors.0.detail', '无法为此服务器分配更多端口：已达到分配限制。');\n    }\n\n    public static function permissionDataProvider(): array\n    {\n        return [[[Permission::ACTION_ALLOCATION_CREATE]], [[]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Allocation/DeleteAllocationTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Allocation;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass DeleteAllocationTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that an allocation is deleted from the server and the notes are properly reset\n     * to an empty value on assignment.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionDataProvider')]\n    public function testAllocationCanBeDeletedFromServer(array $permission)\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount($permission);\n        $server->update(['allocation_limit' => 2]);\n\n        /** @var Allocation $allocation */\n        $allocation = Allocation::factory()->create([\n            'server_id' => $server->id,\n            'node_id' => $server->node_id,\n            'notes' => 'hodor',\n        ]);\n\n        $this->actingAs($user)->deleteJson($this->link($allocation))->assertStatus(Response::HTTP_NO_CONTENT);\n\n        $this->assertDatabaseHas('allocations', ['id' => $allocation->id, 'server_id' => null, 'notes' => null]);\n    }\n\n    /**\n     * Test that an error is returned if the user does not have permissiont to delete an allocation.\n     */\n    public function testErrorIsReturnedIfUserDoesNotHavePermission()\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_ALLOCATION_CREATE]);\n\n        /** @var Allocation $allocation */\n        $allocation = Allocation::factory()->create([\n            'server_id' => $server->id,\n            'node_id' => $server->node_id,\n            'notes' => 'hodor',\n        ]);\n\n        $this->actingAs($user)->deleteJson($this->link($allocation))->assertForbidden();\n\n        $this->assertDatabaseHas('allocations', ['id' => $allocation->id, 'server_id' => $server->id]);\n    }\n\n    /**\n     * Test that an allocation is not deleted if it is currently marked as the primary allocation\n     * for the server.\n     */\n    public function testErrorIsReturnedIfAllocationIsPrimary()\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount();\n        $server->update(['allocation_limit' => 2]);\n\n        $this->actingAs($user)->deleteJson($this->link($server->allocation))\n            ->assertStatus(Response::HTTP_BAD_REQUEST)\n            ->assertJsonPath('errors.0.code', 'DisplayException')\n            ->assertJsonPath('errors.0.detail', '您不能删除此服务器的首选分配。');\n    }\n\n    public function testAllocationCannotBeDeletedIfServerLimitIsNotDefined()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        /** @var Allocation $allocation */\n        $allocation = Allocation::factory()->forServer($server)->create(['notes' => 'Test notes']);\n\n        $this->actingAs($user)->deleteJson($this->link($allocation))\n            ->assertStatus(400)\n            ->assertJsonPath('errors.0.detail', '您无法删除此服务器的网络分配：未设置分配限制。');\n\n        $allocation->refresh();\n        $this->assertNotNull($allocation->notes);\n        $this->assertEquals($server->id, $allocation->server_id);\n    }\n\n    /**\n     * Test that an allocation cannot be deleted if it does not belong to the server instance.\n     */\n    public function testErrorIsReturnedIfAllocationDoesNotBelongToServer()\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount();\n        [, $server2] = $this->generateTestAccount();\n\n        $this->actingAs($user)->deleteJson($this->link($server2->allocation))->assertNotFound();\n        $this->actingAs($user)->deleteJson($this->link($server, \"/network/allocations/{$server2->allocation_id}\"))->assertNotFound();\n    }\n\n    public static function permissionDataProvider(): array\n    {\n        return [[[Permission::ACTION_ALLOCATION_DELETE]], [[]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Backup/BackupAuthorizationTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Backup;\n\nuse Carbon\\CarbonImmutable;\nuse Pterodactyl\\Models\\Backup;\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Services\\Backups\\DeleteBackupService;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass BackupAuthorizationTest extends ClientApiIntegrationTestCase\n{\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('methodDataProvider')]\n    public function testAccessToAServersBackupIsRestrictedProperly(string $method, string $endpoint)\n    {\n        // The API $user is the owner of $server1.\n        [$user, $server1] = $this->generateTestAccount();\n        // Will be a subuser of $server2.\n        $server2 = $this->createServerModel();\n        // And as no access to $server3.\n        $server3 = $this->createServerModel();\n\n        // Set the API $user as a subuser of server 2, but with no permissions\n        // to do anything with the backups for that server.\n        Subuser::factory()->create(['server_id' => $server2->id, 'user_id' => $user->id]);\n\n        $backup1 = Backup::factory()->create(['server_id' => $server1->id, 'completed_at' => CarbonImmutable::now()]);\n        $backup2 = Backup::factory()->create(['server_id' => $server2->id, 'completed_at' => CarbonImmutable::now()]);\n        $backup3 = Backup::factory()->create(['server_id' => $server3->id, 'completed_at' => CarbonImmutable::now()]);\n\n        $this->instance(DeleteBackupService::class, $mock = \\Mockery::mock(DeleteBackupService::class));\n\n        if ($method === 'DELETE') {\n            $mock->expects('handle')->andReturnUndefined();\n        }\n\n        // This is the only valid call for this test, accessing the backup for the same\n        // server that the API user is the owner of.\n        $this->actingAs($user)->json($method, $this->link($server1, '/backups/' . $backup1->uuid . $endpoint))\n            ->assertStatus($method === 'DELETE' ? 204 : 200);\n\n        // This request fails because the backup is valid for that server but the user\n        // making the request is not authorized to perform that action.\n        $this->actingAs($user)->json($method, $this->link($server2, '/backups/' . $backup2->uuid . $endpoint))->assertForbidden();\n\n        // Both of these should report a 404 error due to the backup being linked to\n        // servers that are not the same as the server in the request, or are assigned\n        // to a server for which the user making the request has no access to.\n        $this->actingAs($user)->json($method, $this->link($server1, '/backups/' . $backup2->uuid . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server1, '/backups/' . $backup3->uuid . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server2, '/backups/' . $backup3->uuid . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server3, '/backups/' . $backup3->uuid . $endpoint))->assertNotFound();\n    }\n\n    public static function methodDataProvider(): array\n    {\n        return [\n            ['GET', ''],\n            ['GET', '/download'],\n            ['DELETE', ''],\n        ];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Backup/DeleteBackupTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Backup;\n\nuse Mockery\\MockInterface;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Backup;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Support\\Facades\\Event;\nuse Pterodactyl\\Events\\ActivityLogged;\nuse Pterodactyl\\Repositories\\Wings\\DaemonBackupRepository;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass DeleteBackupTest extends ClientApiIntegrationTestCase\n{\n    private MockInterface $repository;\n\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->repository = $this->mock(DaemonBackupRepository::class);\n    }\n\n    public function testUserWithoutPermissionCannotDeleteBackup()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_BACKUP_CREATE]);\n\n        $backup = Backup::factory()->create(['server_id' => $server->id]);\n\n        $this->actingAs($user)->deleteJson($this->link($backup))\n            ->assertStatus(Response::HTTP_FORBIDDEN);\n    }\n\n    /**\n     * Tests that a backup can be deleted for a server and that it is properly updated\n     * in the database. Once deleted there should also be a corresponding record in the\n     * activity logs table for this API call.\n     */\n    public function testBackupCanBeDeleted()\n    {\n        Event::fake([ActivityLogged::class]);\n\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_BACKUP_DELETE]);\n\n        /** @var Backup $backup */\n        $backup = Backup::factory()->create(['server_id' => $server->id]);\n\n        $this->repository->expects('setServer->delete')->with(\n            \\Mockery::on(function ($value) use ($backup) {\n                return $value instanceof Backup && $value->uuid === $backup->uuid;\n            })\n        )->andReturn(new Response());\n\n        $this->actingAs($user)->deleteJson($this->link($backup))->assertStatus(Response::HTTP_NO_CONTENT);\n\n        $backup->refresh();\n        $this->assertSoftDeleted($backup);\n\n        $this->assertActivityFor('server:backup.delete', $user, [$backup, $backup->server]);\n\n        $this->actingAs($user)->deleteJson($this->link($backup))->assertStatus(Response::HTTP_NOT_FOUND);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/CommandControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server;\n\nuse GuzzleHttp\\Psr7\\Request;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Permission;\nuse GuzzleHttp\\Exception\\BadResponseException;\nuse GuzzleHttp\\Psr7\\Response as GuzzleResponse;\nuse Pterodactyl\\Repositories\\Wings\\DaemonCommandRepository;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass CommandControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that a validation error is returned if there is no command present in the\n     * request.\n     */\n    public function testValidationErrorIsReturnedIfNoCommandIsPresent()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        $response = $this->actingAs($user)->postJson(\"/api/client/servers/$server->uuid/command\", [\n            'command' => '',\n        ]);\n\n        $response->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY);\n        $response->assertJsonPath('errors.0.meta.rule', 'required');\n    }\n\n    /**\n     * Test that a subuser without the required permission receives an error when trying to\n     * execute the command.\n     */\n    public function testSubuserWithoutPermissionReceivesError()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_WEBSOCKET_CONNECT]);\n\n        $response = $this->actingAs($user)->postJson(\"/api/client/servers/$server->uuid/command\", [\n            'command' => 'say Test',\n        ]);\n\n        $response->assertStatus(Response::HTTP_FORBIDDEN);\n    }\n\n    /**\n     * Test that a command can be sent to the server.\n     */\n    public function testCommandCanSendToServer()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_CONTROL_CONSOLE]);\n\n        $mock = $this->mock(DaemonCommandRepository::class);\n        $mock->expects('setServer')\n            ->with(\\Mockery::on(fn (Server $value) => $value->is($server)))\n            ->andReturnSelf();\n\n        $mock->expects('send')->with('say Test')->andReturn(new GuzzleResponse());\n\n        $response = $this->actingAs($user)->postJson(\"/api/client/servers/$server->uuid/command\", [\n            'command' => 'say Test',\n        ]);\n\n        $response->assertStatus(Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Test that an error is returned when the server is offline that is more specific than the\n     * regular daemon connection error.\n     */\n    public function testErrorIsReturnedWhenServerIsOffline()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        $mock = $this->mock(DaemonCommandRepository::class);\n        $mock->expects('setServer->send')->andThrows(\n            new DaemonConnectionException(\n                new BadResponseException('', new Request('GET', 'test'), new GuzzleResponse(Response::HTTP_BAD_GATEWAY))\n            )\n        );\n\n        $response = $this->actingAs($user)->postJson(\"/api/client/servers/$server->uuid/command\", [\n            'command' => 'say Test',\n        ]);\n\n        $response->assertStatus(Response::HTTP_BAD_GATEWAY);\n        $response->assertJsonPath('errors.0.code', 'HttpException');\n        $response->assertJsonPath('errors.0.detail', '服务器必须在线才能发送命令。');\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Database/DatabaseAuthorizationTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Database;\n\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Pterodactyl\\Contracts\\Extensions\\HashidsInterface;\nuse Pterodactyl\\Services\\Databases\\DatabasePasswordService;\nuse Pterodactyl\\Services\\Databases\\DatabaseManagementService;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass DatabaseAuthorizationTest extends ClientApiIntegrationTestCase\n{\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('methodDataProvider')]\n    public function testAccessToAServersDatabasesIsRestrictedProperly(string $method, string $endpoint)\n    {\n        // The API $user is the owner of $server1.\n        [$user, $server1] = $this->generateTestAccount();\n        // Will be a subuser of $server2.\n        $server2 = $this->createServerModel();\n        // And as no access to $server3.\n        $server3 = $this->createServerModel();\n\n        $host = DatabaseHost::factory()->create([]);\n\n        // Set the API $user as a subuser of server 2, but with no permissions\n        // to do anything with the databases for that server.\n        Subuser::factory()->create(['server_id' => $server2->id, 'user_id' => $user->id]);\n\n        $database1 = Database::factory()->create(['server_id' => $server1->id, 'database_host_id' => $host->id]);\n        $database2 = Database::factory()->create(['server_id' => $server2->id, 'database_host_id' => $host->id]);\n        $database3 = Database::factory()->create(['server_id' => $server3->id, 'database_host_id' => $host->id]);\n\n        $this\n            ->mock($method === 'POST' ? DatabasePasswordService::class : DatabaseManagementService::class)\n            ->expects($method === 'POST' ? 'handle' : 'delete')\n            ->andReturn($method === 'POST' ? 'foo' : null);\n\n        $hashids = $this->app->make(HashidsInterface::class);\n        // This is the only valid call for this test, accessing the database for the same\n        // server that the API user is the owner of.\n        $this->actingAs($user)->json($method, $this->link($server1, '/databases/' . $hashids->encode($database1->id) . $endpoint))\n            ->assertStatus($method === 'DELETE' ? 204 : 200);\n\n        // This request fails because the database is valid for that server but the user\n        // making the request is not authorized to perform that action.\n        $this->actingAs($user)->json($method, $this->link($server2, '/databases/' . $hashids->encode($database2->id) . $endpoint))->assertForbidden();\n\n        // Both of these should report a 404 error due to the database being linked to\n        // servers that are not the same as the server in the request, or are assigned\n        // to a server for which the user making the request has no access to.\n        $this->actingAs($user)->json($method, $this->link($server1, '/databases/' . $hashids->encode($database2->id) . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server1, '/databases/' . $hashids->encode($database3->id) . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server2, '/databases/' . $hashids->encode($database3->id) . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server3, '/databases/' . $hashids->encode($database3->id) . $endpoint))->assertNotFound();\n    }\n\n    public static function methodDataProvider(): array\n    {\n        return [\n            ['POST', '/rotate-password'],\n            ['DELETE', ''],\n        ];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Files/CompressFilesTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Files;\n\nuse Mockery\\MockInterface;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Repositories\\Wings\\DaemonFileRepository;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass CompressFilesTest extends ClientApiIntegrationTestCase\n{\n    public function testEndpointRequiresAuthorization(): void\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_CONTROL_CONSOLE]);\n\n        $this->postJson($this->link($server, '/files/compress'))->assertUnauthorized();\n\n        $this->actingAs($user)\n            ->postJson($this->link($server, '/files/compress'))\n            ->assertForbidden();\n    }\n\n    public function testEndpointTriggersWingsCall(): void\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_FILE_ARCHIVE]);\n\n        $this->mock(DaemonFileRepository::class, function (MockInterface $mock) {\n            $mock->expects('setServer->compressFiles')->with('/', ['test.txt'])->andReturn([\n                'name' => 'test.tar.gz',\n                'mime' => 'application/gzip',\n            ]);\n        });\n\n        $this->actingAs($user)\n            ->postJson($endpoint = $this->link($server, '/files/compress'), [])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.meta', ['source_field' => 'files', 'rule' => 'required']);\n\n        $this->postJson($endpoint, ['root' => '/', 'files' => ['test.txt']])\n            ->assertOk()\n            ->assertJsonPath('object', 'file_object')\n            ->assertJsonPath('attributes.name', 'test.tar.gz')\n            ->assertJsonPath('attributes.mimetype', 'application/gzip');\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/NetworkAllocationControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass NetworkAllocationControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that a servers allocations are returned in the expected format.\n     */\n    public function testServerAllocationsAreReturned()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        $response = $this->actingAs($user)->getJson($this->link($server, '/network/allocations'));\n\n        $response->assertOk();\n        $response->assertJsonPath('object', 'list');\n        $response->assertJsonCount(1, 'data');\n\n        $this->assertJsonTransformedWith($response->json('data.0.attributes'), $server->allocation);\n    }\n\n    /**\n     * Test that allocations cannot be returned without the required user permissions.\n     */\n    public function testServerAllocationsAreNotReturnedWithoutPermission()\n    {\n        [$user, $server] = $this->generateTestAccount();\n        $user2 = User::factory()->create();\n\n        $server->owner_id = $user2->id;\n        $server->save();\n\n        $this->actingAs($user)->getJson($this->link($server, '/network/allocations'))\n            ->assertNotFound();\n\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_ALLOCATION_CREATE]);\n\n        $this->actingAs($user)->getJson($this->link($server, '/network/allocations'))\n            ->assertForbidden();\n    }\n\n    /**\n     * Tests that notes on an allocation can be set correctly.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('updatePermissionsDataProvider')]\n    public function testAllocationNotesCanBeUpdated(array $permissions)\n    {\n        [$user, $server] = $this->generateTestAccount($permissions);\n        $allocation = $server->allocation;\n\n        $this->assertNull($allocation->notes);\n\n        $this->actingAs($user)->postJson($this->link($allocation), [])\n            ->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY)\n            ->assertJsonPath('errors.0.meta.rule', 'present');\n\n        $this->actingAs($user)->postJson($this->link($allocation), ['notes' => 'Test notes'])\n            ->assertOk()\n            ->assertJsonPath('object', Allocation::RESOURCE_NAME)\n            ->assertJsonPath('attributes.notes', 'Test notes');\n\n        $allocation = $allocation->refresh();\n\n        $this->assertSame('Test notes', $allocation->notes);\n\n        $this->actingAs($user)->postJson($this->link($allocation), ['notes' => null])\n            ->assertOk()\n            ->assertJsonPath('object', Allocation::RESOURCE_NAME)\n            ->assertJsonPath('attributes.notes', null);\n\n        $allocation = $allocation->refresh();\n\n        $this->assertNull($allocation->notes);\n    }\n\n    public function testAllocationNotesCannotBeUpdatedByInvalidUsers()\n    {\n        [$user, $server] = $this->generateTestAccount();\n        $user2 = User::factory()->create();\n\n        $server->owner_id = $user2->id;\n        $server->save();\n\n        $this->actingAs($user)->postJson($this->link($server->allocation))->assertNotFound();\n\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_ALLOCATION_CREATE]);\n\n        $this->actingAs($user)->postJson($this->link($server->allocation))->assertForbidden();\n    }\n\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('updatePermissionsDataProvider')]\n    public function testPrimaryAllocationCanBeModified(array $permissions)\n    {\n        [$user, $server] = $this->generateTestAccount($permissions);\n        $allocation = $server->allocation;\n        $allocation2 = Allocation::factory()->create(['node_id' => $server->node_id, 'server_id' => $server->id]);\n\n        $server->allocation_id = $allocation->id;\n        $server->save();\n\n        $this->actingAs($user)->postJson($this->link($allocation2, '/primary'))\n            ->assertOk();\n\n        $server = $server->refresh();\n\n        $this->assertSame($allocation2->id, $server->allocation_id);\n    }\n\n    public function testPrimaryAllocationCannotBeModifiedByInvalidUser()\n    {\n        [$user, $server] = $this->generateTestAccount();\n        $user2 = User::factory()->create();\n\n        $server->owner_id = $user2->id;\n        $server->save();\n\n        $this->actingAs($user)->postJson($this->link($server->allocation, '/primary'))\n            ->assertNotFound();\n\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_ALLOCATION_CREATE]);\n\n        $this->actingAs($user)->postJson($this->link($server->allocation, '/primary'))\n            ->assertForbidden();\n    }\n\n    public static function updatePermissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_ALLOCATION_UPDATE]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/PowerControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Repositories\\Wings\\DaemonPowerRepository;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass PowerControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that a subuser without permission to send a command to the server receives\n     * an error in response. This checks against the specific permission needed to send\n     * the command to the server.\n     *\n     * @param string[] $permissions\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('invalidPermissionDataProvider')]\n    public function testSubuserWithoutPermissionsReceivesError(string $action, array $permissions)\n    {\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/power\", ['signal' => $action])\n            ->assertStatus(Response::HTTP_FORBIDDEN);\n    }\n\n    /**\n     * Test that sending an invalid power signal returns an error.\n     */\n    public function testInvalidPowerSignalResultsInError()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        $response = $this->actingAs($user)->postJson(\"/api/client/servers/$server->uuid/power\", [\n            'signal' => 'invalid',\n        ]);\n\n        $response->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY);\n        $response->assertJsonPath('errors.0.meta.rule', 'in');\n        $response->assertJsonPath('errors.0.detail', '已选的属性 signal 无效。');\n    }\n\n    /**\n     * Test that sending a valid power actions works.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('validPowerActionDataProvider')]\n    public function testActionCanBeSentToServer(string $action, string $permission)\n    {\n        $service = \\Mockery::mock(DaemonPowerRepository::class);\n        $this->app->instance(DaemonPowerRepository::class, $service);\n\n        [$user, $server] = $this->generateTestAccount([$permission]);\n\n        $service->expects('setServer')\n            ->with(\\Mockery::on(function ($value) use ($server) {\n                return $server->uuid === $value->uuid;\n            }))\n            ->andReturnSelf()\n            ->getMock()\n            ->expects('send')\n            ->with(trim($action));\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/power\", ['signal' => $action])\n            ->assertStatus(Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Returns invalid permission combinations for a given power action.\n     */\n    public static function invalidPermissionDataProvider(): array\n    {\n        return [\n            ['start', [Permission::ACTION_CONTROL_STOP, Permission::ACTION_CONTROL_RESTART]],\n            ['stop', [Permission::ACTION_CONTROL_START]],\n            ['kill', [Permission::ACTION_CONTROL_START, Permission::ACTION_CONTROL_RESTART]],\n            ['restart', [Permission::ACTION_CONTROL_STOP, Permission::ACTION_CONTROL_START]],\n            ['random', [Permission::ACTION_CONTROL_START]],\n        ];\n    }\n\n    public static function validPowerActionDataProvider(): array\n    {\n        return [\n            ['start', Permission::ACTION_CONTROL_START],\n            ['stop', Permission::ACTION_CONTROL_STOP],\n            ['restart', Permission::ACTION_CONTROL_RESTART],\n            ['kill', Permission::ACTION_CONTROL_STOP],\n            // Yes, these spaces are intentional. You should be able to send values with or without\n            // a space on the start/end since we should be trimming the values.\n            [' restart', Permission::ACTION_CONTROL_RESTART],\n            ['kill ', Permission::ACTION_CONTROL_STOP],\n        ];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/ResourceUtilizationControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server;\n\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass ResourceUtilizationControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that the resource utilization for a server is returned in the expected format.\n     */\n    public function testServerResourceUtilizationIsReturned()\n    {\n        $service = \\Mockery::mock(DaemonServerRepository::class);\n        $this->app->instance(DaemonServerRepository::class, $service);\n\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_WEBSOCKET_CONNECT]);\n\n        $service->expects('setServer')->with(\\Mockery::on(function ($value) use ($server) {\n            return $server->uuid === $value->uuid;\n        }))->andReturnSelf()->getMock()->expects('getDetails')->andReturns([]);\n\n        $response = $this->actingAs($user)->getJson(\"/api/client/servers/$server->uuid/resources\");\n\n        $response->assertOk();\n        $response->assertJson([\n            'object' => 'stats',\n            'attributes' => [\n                'current_state' => 'stopped',\n                'is_suspended' => false,\n                'resources' => [\n                    'memory_bytes' => 0,\n                    'cpu_absolute' => 0,\n                    'disk_bytes' => 0,\n                    'network_rx_bytes' => 0,\n                    'network_tx_bytes' => 0,\n                ],\n            ],\n        ]);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Schedule/CreateServerScheduleTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Schedule;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass CreateServerScheduleTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that a schedule can be created for the server.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testScheduleCanBeCreatedForServer(array $permissions)\n    {\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        $response = $this->actingAs($user)->postJson(\"/api/client/servers/$server->uuid/schedules\", [\n            'name' => 'Test Schedule',\n            'is_active' => false,\n            'minute' => '0',\n            'hour' => '*/2',\n            'day_of_week' => '2',\n            'month' => '1',\n            'day_of_month' => '*',\n        ]);\n\n        $response->assertOk();\n\n        $this->assertNotNull($id = $response->json('attributes.id'));\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::query()->findOrFail($id);\n        $this->assertFalse($schedule->is_active);\n        $this->assertFalse($schedule->is_processing);\n        $this->assertSame('0', $schedule->cron_minute);\n        $this->assertSame('*/2', $schedule->cron_hour);\n        $this->assertSame('2', $schedule->cron_day_of_week);\n        $this->assertSame('1', $schedule->cron_month);\n        $this->assertSame('*', $schedule->cron_day_of_month);\n        $this->assertSame('Test Schedule', $schedule->name);\n\n        $this->assertJsonTransformedWith($response->json('attributes'), $schedule);\n        $response->assertJsonCount(0, 'attributes.relationships.tasks.data');\n    }\n\n    /**\n     * Test that the validation rules for scheduling work as expected.\n     */\n    public function testScheduleValidationRules()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        $response = $this->actingAs($user)->postJson(\"/api/client/servers/$server->uuid/schedules\", []);\n\n        $response->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY);\n        foreach (['name', 'minute', 'hour', 'day_of_month', 'day_of_week'] as $i => $field) {\n            $response->assertJsonPath(\"errors.$i.code\", 'ValidationException');\n            $response->assertJsonPath(\"errors.$i.meta.rule\", 'required');\n            $response->assertJsonPath(\"errors.$i.meta.source_field\", $field);\n        }\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/schedules\", [\n                'name' => 'Testing',\n                'is_active' => 'no',\n                'minute' => '*',\n                'hour' => '*',\n                'day_of_month' => '*',\n                'month' => '*',\n                'day_of_week' => '*',\n            ])\n            ->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY)\n            ->assertJsonPath('errors.0.meta.rule', 'boolean');\n    }\n\n    /**\n     * Test that a subuser without required permissions cannot create a schedule.\n     */\n    public function testSubuserCannotCreateScheduleWithoutPermissions()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_SCHEDULE_UPDATE]);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/schedules\", [])\n            ->assertForbidden();\n    }\n\n    public static function permissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_SCHEDULE_CREATE]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Schedule/DeleteServerScheduleTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Schedule;\n\nuse Pterodactyl\\Models\\Task;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass DeleteServerScheduleTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that a schedule can be deleted from the system.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testScheduleCanBeDeleted(array $permissions)\n    {\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n        $task = Task::factory()->create(['schedule_id' => $schedule->id]);\n\n        $this->actingAs($user)\n            ->deleteJson(\"/api/client/servers/$server->uuid/schedules/$schedule->id\")\n            ->assertStatus(Response::HTTP_NO_CONTENT);\n\n        $this->assertDatabaseMissing('schedules', ['id' => $schedule->id]);\n        $this->assertDatabaseMissing('tasks', ['id' => $task->id]);\n    }\n\n    /**\n     * Test that no error is returned if the schedule does not exist on the system at all.\n     */\n    public function testNotFoundErrorIsReturnedIfScheduleDoesNotExistAtAll()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        $this->actingAs($user)\n            ->deleteJson(\"/api/client/servers/$server->uuid/schedules/123456789\")\n            ->assertStatus(Response::HTTP_NOT_FOUND);\n    }\n\n    /**\n     * Ensure that a schedule belonging to another server cannot be deleted and its presence is not\n     * revealed to the user.\n     */\n    public function testNotFoundErrorIsReturnedIfScheduleDoesNotBelongToServer()\n    {\n        [$user, $server] = $this->generateTestAccount();\n        $server2 = $this->createServerModel(['owner_id' => $user->id]);\n\n        $schedule = Schedule::factory()->create(['server_id' => $server2->id]);\n\n        $this->actingAs($user)\n            ->deleteJson(\"/api/client/servers/$server->uuid/schedules/$schedule->id\")\n            ->assertStatus(Response::HTTP_NOT_FOUND);\n\n        $this->assertDatabaseHas('schedules', ['id' => $schedule->id]);\n    }\n\n    /**\n     * Test that an error is returned if the subuser does not have the required permissions to\n     * delete the schedule from the server.\n     */\n    public function testErrorIsReturnedIfSubuserDoesNotHaveRequiredPermissions()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_SCHEDULE_UPDATE]);\n\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n\n        $this->actingAs($user)\n            ->deleteJson(\"/api/client/servers/$server->uuid/schedules/$schedule->id\")\n            ->assertStatus(Response::HTTP_FORBIDDEN);\n\n        $this->assertDatabaseHas('schedules', ['id' => $schedule->id]);\n    }\n\n    public static function permissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_SCHEDULE_DELETE]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Schedule/ExecuteScheduleTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Schedule;\n\nuse Pterodactyl\\Models\\Task;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Support\\Facades\\Bus;\nuse Pterodactyl\\Jobs\\Schedule\\RunTaskJob;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass ExecuteScheduleTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that a schedule can be executed and is updated in the database correctly.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testScheduleIsExecutedRightAway(array $permissions)\n    {\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        Bus::fake();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create([\n            'server_id' => $server->id,\n        ]);\n\n        $response = $this->actingAs($user)->postJson($this->link($schedule, '/execute'));\n        $response->assertStatus(Response::HTTP_BAD_REQUEST);\n        $response->assertJsonPath('errors.0.code', 'DisplayException');\n        $response->assertJsonPath('errors.0.detail', 'Cannot process schedule for task execution: no tasks are registered.');\n\n        /** @var Task $task */\n        $task = Task::factory()->create([\n            'schedule_id' => $schedule->id,\n            'sequence_id' => 1,\n            'time_offset' => 2,\n        ]);\n\n        $this->actingAs($user)->postJson($this->link($schedule, '/execute'))->assertStatus(Response::HTTP_ACCEPTED);\n\n        Bus::assertDispatched(function (RunTaskJob $job) use ($task) {\n            // A task executed right now should not have any job delay associated with it.\n            $this->assertNull($job->delay);\n            $this->assertSame($task->id, $job->task->id);\n\n            return true;\n        });\n    }\n\n    /**\n     * Test that a user without the schedule update permission cannot execute it.\n     */\n    public function testUserWithoutScheduleUpdatePermissionCannotExecute()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_SCHEDULE_CREATE]);\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n\n        $this->actingAs($user)->postJson($this->link($schedule, '/execute'))->assertForbidden();\n    }\n\n    public static function permissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_SCHEDULE_UPDATE]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Schedule/GetServerSchedulesTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Schedule;\n\nuse Pterodactyl\\Models\\Task;\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass GetServerSchedulesTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Cleanup after tests run.\n     */\n    protected function tearDown(): void\n    {\n        Task::query()->forceDelete();\n        Schedule::query()->forceDelete();\n\n        parent::tearDown();\n    }\n\n    /**\n     * Test that schedules for a server are returned.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testServerSchedulesAreReturned(array $permissions, bool $individual)\n    {\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n        /** @var Task $task */\n        $task = Task::factory()->create(['schedule_id' => $schedule->id, 'sequence_id' => 1, 'time_offset' => 0]);\n\n        $response = $this->actingAs($user)\n            ->getJson(\n                $individual\n                    ? \"/api/client/servers/$server->uuid/schedules/$schedule->id\"\n                    : \"/api/client/servers/$server->uuid/schedules\"\n            )\n            ->assertOk();\n\n        $prefix = $individual ? '' : 'data.0.';\n        if (!$individual) {\n            $response->assertJsonCount(1, 'data');\n        }\n\n        $response->assertJsonCount(1, $prefix . 'attributes.relationships.tasks.data');\n\n        $response->assertJsonPath($prefix . 'object', Schedule::RESOURCE_NAME);\n        $response->assertJsonPath($prefix . 'attributes.relationships.tasks.data.0.object', Task::RESOURCE_NAME);\n\n        $this->assertJsonTransformedWith($response->json($prefix . 'attributes'), $schedule);\n        $this->assertJsonTransformedWith($response->json($prefix . 'attributes.relationships.tasks.data.0.attributes'), $task);\n    }\n\n    /**\n     * Test that a schedule belonging to another server cannot be viewed.\n     */\n    public function testScheduleBelongingToAnotherServerCannotBeViewed()\n    {\n        [$user, $server] = $this->generateTestAccount();\n        $server2 = $this->createServerModel(['owner_id' => $user->id]);\n\n        $schedule = Schedule::factory()->create(['server_id' => $server2->id]);\n\n        $this->actingAs($user)\n            ->getJson(\"/api/client/servers/$server->uuid/schedules/$schedule->id\")\n            ->assertNotFound();\n    }\n\n    /**\n     * Test that a subuser without the required permissions is unable to access the schedules endpoint.\n     */\n    public function testUserWithoutPermissionCannotViewSchedules()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_WEBSOCKET_CONNECT]);\n\n        $this->actingAs($user)\n            ->getJson(\"/api/client/servers/$server->uuid/schedules\")\n            ->assertForbidden();\n\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n\n        $this->actingAs($user)\n            ->getJson(\"/api/client/servers/$server->uuid/schedules/$schedule->id\")\n            ->assertForbidden();\n    }\n\n    public static function permissionsDataProvider(): array\n    {\n        return [\n            [[], false],\n            [[], true],\n            [[Permission::ACTION_SCHEDULE_READ], false],\n            [[Permission::ACTION_SCHEDULE_READ], true],\n        ];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Schedule/ScheduleAuthorizationTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Schedule;\n\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass ScheduleAuthorizationTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Tests that a subuser with access to two servers cannot improperly access a resource\n     * on Server A when providing a URL that points to Server B. This prevents a regression\n     * in the code where controllers didn't properly validate that a resource was assigned\n     * to the server that was also present in the URL.\n     *\n     * The comments within the test code itself are better at explaining exactly what is\n     * being tested and protected against.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('methodDataProvider')]\n    public function testAccessToAServersSchedulesIsRestrictedProperly(string $method, string $endpoint)\n    {\n        // The API $user is the owner of $server1.\n        [$user, $server1] = $this->generateTestAccount();\n        // Will be a subuser of $server2.\n        $server2 = $this->createServerModel();\n        // And as no access to $server3.\n        $server3 = $this->createServerModel();\n\n        // Set the API $user as a subuser of server 2, but with no permissions\n        // to do anything with the schedules for that server.\n        Subuser::factory()->create(['server_id' => $server2->id, 'user_id' => $user->id]);\n\n        $schedule1 = Schedule::factory()->create(['server_id' => $server1->id]);\n        $schedule2 = Schedule::factory()->create(['server_id' => $server2->id]);\n        $schedule3 = Schedule::factory()->create(['server_id' => $server3->id]);\n\n        // This is the only valid call for this test, accessing the schedule for the same\n        // server that the API user is the owner of.\n        $response = $this->actingAs($user)->json($method, $this->link($server1, '/schedules/' . $schedule1->id . $endpoint));\n        $this->assertTrue($response->status() <= 204 || $response->status() === 400 || $response->status() === 422);\n\n        // This request fails because the schedule is valid for that server but the user\n        // making the request is not authorized to perform that action.\n        $this->actingAs($user)->json($method, $this->link($server2, '/schedules/' . $schedule2->id . $endpoint))->assertForbidden();\n\n        // Both of these should report a 404 error due to the schedules being linked to\n        // servers that are not the same as the server in the request, or are assigned\n        // to a server for which the user making the request has no access to.\n        $this->actingAs($user)->json($method, $this->link($server1, '/schedules/' . $schedule2->id . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server1, '/schedules/' . $schedule3->id . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server2, '/schedules/' . $schedule3->id . $endpoint))->assertNotFound();\n        $this->actingAs($user)->json($method, $this->link($server3, '/schedules/' . $schedule3->id . $endpoint))->assertNotFound();\n    }\n\n    public static function methodDataProvider(): array\n    {\n        return [\n            ['GET', ''],\n            ['POST', ''],\n            ['DELETE', ''],\n            ['POST', '/execute'],\n            ['POST', '/tasks'],\n        ];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Schedule/UpdateServerScheduleTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Schedule;\n\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Helpers\\Utilities;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass UpdateServerScheduleTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * The data to use when updating a schedule.\n     */\n    private array $updateData = [\n        'name' => 'Updated Schedule Name',\n        'minute' => '5',\n        'hour' => '*',\n        'day_of_week' => '*',\n        'month' => '*',\n        'day_of_month' => '*',\n        'is_active' => false,\n    ];\n\n    /**\n     * Test that a schedule can be updated.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testScheduleCanBeUpdated(array $permissions)\n    {\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n        $expected = Utilities::getScheduleNextRunDate('5', '*', '*', '*', '*');\n\n        $response = $this->actingAs($user)\n            ->postJson(\"/api/client/servers/{$server->uuid}/schedules/{$schedule->id}\", $this->updateData);\n\n        $schedule = $schedule->refresh();\n\n        $response->assertOk();\n        $this->assertSame('Updated Schedule Name', $schedule->name);\n        $this->assertFalse($schedule->is_active);\n        $this->assertJsonTransformedWith($response->json('attributes'), $schedule);\n\n        $this->assertSame($expected->toAtomString(), $schedule->next_run_at->toAtomString());\n    }\n\n    /**\n     * Test that an error is returned if the schedule exists but does not belong to this\n     * specific server instance.\n     */\n    public function testErrorIsReturnedIfScheduleDoesNotBelongToServer()\n    {\n        [$user, $server] = $this->generateTestAccount();\n        $server2 = $this->createServerModel(['owner_id' => $user->id]);\n\n        $schedule = Schedule::factory()->create(['server_id' => $server2->id]);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/{$server->uuid}/schedules/{$schedule->id}\")\n            ->assertNotFound();\n    }\n\n    /**\n     * Test that an error is returned if the subuser does not have permission to modify a\n     * server schedule.\n     */\n    public function testErrorIsReturnedIfSubuserDoesNotHavePermissionToModifySchedule()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_SCHEDULE_CREATE]);\n\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/{$server->uuid}/schedules/{$schedule->id}\")\n            ->assertForbidden();\n    }\n\n    /**\n     * Test that the \"is_processing\" field gets reset to false when the schedule is enabled\n     * or disabled so that an invalid state can be more easily fixed.\n     *\n     * @see https://github.com/pterodactyl/panel/issues/2425\n     */\n    public function testScheduleIsProcessingIsSetToFalseWhenActiveStateChanges()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create([\n            'server_id' => $server->id,\n            'is_active' => true,\n            'is_processing' => true,\n        ]);\n\n        $this->assertTrue($schedule->is_active);\n        $this->assertTrue($schedule->is_processing);\n\n        $response = $this->actingAs($user)\n            ->postJson(\"/api/client/servers/{$server->uuid}/schedules/{$schedule->id}\", $this->updateData);\n\n        $schedule = $schedule->refresh();\n\n        $response->assertOk();\n        $this->assertFalse($schedule->is_active);\n        $this->assertFalse($schedule->is_processing);\n    }\n\n    public static function permissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_SCHEDULE_UPDATE]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/ScheduleTask/CreateServerScheduleTaskTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\ScheduleTask;\n\nuse Pterodactyl\\Models\\Task;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass CreateServerScheduleTaskTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that a task can be created.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testTaskCanBeCreated(array $permissions)\n    {\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n        $this->assertEmpty($schedule->tasks);\n\n        $response = $this->actingAs($user)->postJson($this->link($schedule, '/tasks'), [\n            'action' => 'command',\n            'payload' => 'say Test',\n            'time_offset' => 10,\n            'sequence_id' => 1,\n        ]);\n\n        $response->assertOk();\n        /** @var Task $task */\n        $task = Task::query()->findOrFail($response->json('attributes.id'));\n\n        $this->assertSame($schedule->id, $task->schedule_id);\n        $this->assertSame(1, $task->sequence_id);\n        $this->assertSame('command', $task->action);\n        $this->assertSame('say Test', $task->payload);\n        $this->assertSame(10, $task->time_offset);\n        $this->assertJsonTransformedWith($response->json('attributes'), $task);\n    }\n\n    /**\n     * Test that validation errors are returned correctly if bad data is passed into the API.\n     */\n    public function testValidationErrorsAreReturned()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n\n        $response = $this->actingAs($user)->postJson($this->link($schedule, '/tasks'))->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY);\n\n        foreach (['action', 'payload', 'time_offset'] as $i => $field) {\n            $response->assertJsonPath(\"errors.$i.meta.rule\", $field === 'payload' ? 'required_unless' : 'required');\n            $response->assertJsonPath(\"errors.$i.meta.source_field\", $field);\n        }\n\n        $this->actingAs($user)->postJson($this->link($schedule, '/tasks'), [\n            'action' => 'hodor',\n            'payload' => 'say Test',\n            'time_offset' => 0,\n        ])\n            ->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY)\n            ->assertJsonPath('errors.0.meta.rule', 'in')\n            ->assertJsonPath('errors.0.meta.source_field', 'action');\n\n        $this->actingAs($user)->postJson($this->link($schedule, '/tasks'), [\n            'action' => 'command',\n            'time_offset' => 0,\n        ])\n            ->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY)\n            ->assertJsonPath('errors.0.meta.rule', 'required_unless')\n            ->assertJsonPath('errors.0.meta.source_field', 'payload');\n\n        $this->actingAs($user)->postJson($this->link($schedule, '/tasks'), [\n            'action' => 'command',\n            'payload' => 'say Test',\n            'time_offset' => 0,\n            'sequence_id' => 'hodor',\n        ])\n            ->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY)\n            ->assertJsonPath('errors.0.meta.rule', 'numeric')\n            ->assertJsonPath('errors.0.meta.source_field', 'sequence_id');\n    }\n\n    /**\n     * Test that backups can not be tasked when the backup limit is 0.\n     */\n    public function testBackupsCanNotBeTaskedIfLimit0()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n\n        $this->actingAs($user)->postJson($this->link($schedule, '/tasks'), [\n            'action' => 'backup',\n            'time_offset' => 0,\n        ])\n            ->assertStatus(Response::HTTP_FORBIDDEN)\n            ->assertJsonPath('errors.0.detail', '当服务器的备份限制设置为 0 时，则不能创建备份任务。');\n\n        $this->actingAs($user)->postJson($this->link($schedule, '/tasks'), [\n            'action' => 'backup',\n            'payload' => \"file.txt\\nfile2.log\",\n            'time_offset' => 0,\n        ])\n            ->assertStatus(Response::HTTP_FORBIDDEN)\n            ->assertJsonPath('errors.0.detail', '当服务器的备份限制设置为 0 时，则不能创建备份任务。');\n    }\n\n    /**\n     * Test that an error is returned if the user attempts to create an additional task that\n     * would put the schedule over the task limit.\n     */\n    public function testErrorIsReturnedIfTooManyTasksExistForSchedule()\n    {\n        config()->set('pterodactyl.client_features.schedules.per_schedule_task_limit', 2);\n\n        [$user, $server] = $this->generateTestAccount();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n        Task::factory()->times(2)->create(['schedule_id' => $schedule->id]);\n\n        $this->actingAs($user)->postJson($this->link($schedule, '/tasks'), [\n            'action' => 'command',\n            'payload' => 'say test',\n            'time_offset' => 0,\n        ])\n            ->assertStatus(Response::HTTP_BAD_REQUEST)\n            ->assertJsonPath('errors.0.code', 'ServiceLimitExceededException')\n            ->assertJsonPath('errors.0.detail', 'Schedules may not have more than 2 tasks associated with them. Creating this task would put this schedule over the limit.');\n    }\n\n    /**\n     * Test that an error is returned if the targeted schedule does not belong to the server\n     * in the request.\n     */\n    public function testErrorIsReturnedIfScheduleDoesNotBelongToServer()\n    {\n        [$user, $server] = $this->generateTestAccount();\n        $server2 = $this->createServerModel(['owner_id' => $user->id]);\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server2->id]);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/schedules/$schedule->id/tasks\")\n            ->assertNotFound();\n    }\n\n    /**\n     * Test that an error is returned if the subuser making the request does not have permission\n     * to update a schedule.\n     */\n    public function testErrorIsReturnedIfSubuserDoesNotHaveScheduleUpdatePermissions()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_SCHEDULE_CREATE]);\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n\n        $this->actingAs($user)\n            ->postJson($this->link($schedule, '/tasks'))\n            ->assertForbidden();\n    }\n\n    public static function permissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_SCHEDULE_UPDATE]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/ScheduleTask/DeleteScheduleTaskTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\ScheduleTask;\n\nuse Pterodactyl\\Models\\Task;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Schedule;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass DeleteScheduleTaskTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that an error is returned if the schedule does not belong to the server.\n     */\n    public function testScheduleNotBelongingToServerReturnsError()\n    {\n        $server2 = $this->createServerModel();\n        [$user] = $this->generateTestAccount();\n\n        $schedule = Schedule::factory()->create(['server_id' => $server2->id]);\n        $task = Task::factory()->create(['schedule_id' => $schedule->id]);\n\n        $this->actingAs($user)->deleteJson($this->link($task))->assertNotFound();\n    }\n\n    /**\n     * Test that an error is returned if the task and schedule in the URL do not line up\n     * with each other.\n     */\n    public function testTaskBelongingToDifferentScheduleReturnsError()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n        $schedule2 = Schedule::factory()->create(['server_id' => $server->id]);\n        $task = Task::factory()->create(['schedule_id' => $schedule->id]);\n\n        $this->actingAs($user)->deleteJson(\"/api/client/servers/$server->uuid/schedules/$schedule2->id/tasks/$task->id\")->assertNotFound();\n    }\n\n    /**\n     * Test that a user without the required permissions returns an error.\n     */\n    public function testUserWithoutPermissionReturnsError()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_SCHEDULE_CREATE]);\n\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n        $task = Task::factory()->create(['schedule_id' => $schedule->id]);\n\n        $this->actingAs($user)->deleteJson($this->link($task))->assertForbidden();\n\n        $user2 = User::factory()->create();\n\n        $this->actingAs($user2)->deleteJson($this->link($task))->assertNotFound();\n    }\n\n    /**\n     * Test that a schedule task is deleted and items with a higher sequence ID are decremented\n     * properly in the database.\n     */\n    public function testScheduleTaskIsDeletedAndSubsequentTasksAreUpdated()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n        $tasks = [\n            Task::factory()->create(['schedule_id' => $schedule->id, 'sequence_id' => 1]),\n            Task::factory()->create(['schedule_id' => $schedule->id, 'sequence_id' => 2]),\n            Task::factory()->create(['schedule_id' => $schedule->id, 'sequence_id' => 3]),\n            Task::factory()->create(['schedule_id' => $schedule->id, 'sequence_id' => 4]),\n        ];\n\n        $response = $this->actingAs($user)->deleteJson($this->link($tasks[1]));\n        $response->assertStatus(Response::HTTP_NO_CONTENT);\n\n        $this->assertDatabaseHas('tasks', ['id' => $tasks[0]->id, 'sequence_id' => 1]);\n        $this->assertDatabaseHas('tasks', ['id' => $tasks[2]->id, 'sequence_id' => 2]);\n        $this->assertDatabaseHas('tasks', ['id' => $tasks[3]->id, 'sequence_id' => 3]);\n        $this->assertDatabaseMissing('tasks', ['id' => $tasks[1]->id]);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/SettingsControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server;\n\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass SettingsControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that the server's name can be changed.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('renamePermissionsDataProvider')]\n    public function testServerNameCanBeChanged(array $permissions)\n    {\n        /** @var Server $server */\n        [$user, $server] = $this->generateTestAccount($permissions);\n        $originalName = $server->name;\n        $originalDescription = $server->description;\n\n        $response = $this->actingAs($user)->postJson(\"/api/client/servers/$server->uuid/settings/rename\", [\n            'name' => '',\n            'description' => '',\n        ]);\n\n        $response->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY);\n        $response->assertJsonPath('errors.0.meta.rule', 'required');\n\n        $server = $server->refresh();\n        $this->assertSame($originalName, $server->name);\n        $this->assertSame($originalDescription, $server->description);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/settings/rename\", [\n                'name' => 'Test Server Name',\n                'description' => 'This is a test server.',\n            ])\n            ->assertStatus(Response::HTTP_NO_CONTENT);\n\n        $server = $server->refresh();\n        $this->assertSame('Test Server Name', $server->name);\n        $this->assertSame('This is a test server.', $server->description);\n    }\n\n    /**\n     * Test that a subuser receives a permissions error if they do not have the required permission\n     * and attempt to change the name.\n     */\n    public function testSubuserCannotChangeServerNameWithoutPermission()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_WEBSOCKET_CONNECT]);\n        $originalName = $server->name;\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/settings/rename\", [\n                'name' => 'Test Server Name',\n            ])\n            ->assertStatus(Response::HTTP_FORBIDDEN);\n\n        $server = $server->refresh();\n        $this->assertSame($originalName, $server->name);\n    }\n\n    /**\n     * Test that a server can be reinstalled. Honestly this test doesn't do much of anything other\n     * than make sure the endpoint works since.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('reinstallPermissionsDataProvider')]\n    public function testServerCanBeReinstalled(array $permissions)\n    {\n        /** @var Server $server */\n        [$user, $server] = $this->generateTestAccount($permissions);\n        $this->assertTrue($server->isInstalled());\n\n        $service = \\Mockery::mock(DaemonServerRepository::class);\n        $this->app->instance(DaemonServerRepository::class, $service);\n\n        $service->expects('setServer')\n            ->with(\\Mockery::on(function ($value) use ($server) {\n                return $value->uuid === $server->uuid;\n            }))\n            ->andReturnSelf()\n            ->getMock()\n            ->expects('reinstall')\n            ->andReturnUndefined();\n\n        $this->actingAs($user)->postJson(\"/api/client/servers/$server->uuid/settings/reinstall\")\n            ->assertStatus(Response::HTTP_ACCEPTED);\n\n        $server = $server->refresh();\n        $this->assertSame(Server::STATUS_INSTALLING, $server->status);\n    }\n\n    /**\n     * Test that a subuser receives a permissions error if they do not have the required permission\n     * and attempt to reinstall a server.\n     */\n    public function testSubuserCannotReinstallServerWithoutPermission()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_WEBSOCKET_CONNECT]);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/settings/reinstall\")\n            ->assertStatus(Response::HTTP_FORBIDDEN);\n\n        $server = $server->refresh();\n        $this->assertTrue($server->isInstalled());\n    }\n\n    public static function renamePermissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_SETTINGS_RENAME]]];\n    }\n\n    public static function reinstallPermissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_SETTINGS_REINSTALL]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Startup/GetStartupAndVariablesTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Startup;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Models\\EggVariable;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass GetStartupAndVariablesTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that the startup command and variables are returned for a server, but only the variables\n     * that can be viewed by a user (e.g. user_viewable=true).\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testStartupVariablesAreReturnedForServer(array $permissions)\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        $egg = $this->cloneEggAndVariables($server->egg);\n        // BUNGEE_VERSION should never be returned to the user in this API call, either in\n        // the array of variables, or revealed in the startup command.\n        $egg->variables()->first()->update([\n            'user_viewable' => false,\n        ]);\n\n        $server->fill([\n            'egg_id' => $egg->id,\n            'startup' => 'java {{SERVER_JARFILE}} --version {{BUNGEE_VERSION}}',\n        ])->save();\n        $server = $server->refresh();\n\n        $response = $this->actingAs($user)->getJson($this->link($server) . '/startup');\n\n        $response->assertOk();\n        $response->assertJsonPath('meta.startup_command', 'java bungeecord.jar --version [hidden]');\n        $response->assertJsonPath('meta.raw_startup_command', $server->startup);\n\n        $response->assertJsonPath('object', 'list');\n        $response->assertJsonCount(1, 'data');\n        $response->assertJsonPath('data.0.object', EggVariable::RESOURCE_NAME);\n        $this->assertJsonTransformedWith($response->json('data.0.attributes'), $egg->variables[1]);\n    }\n\n    /**\n     * Test that a user without the required permission, or who does not have any permission to\n     * access the server cannot get the startup information for it.\n     */\n    public function testStartupDataIsNotReturnedWithoutPermission()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_WEBSOCKET_CONNECT]);\n        $this->actingAs($user)->getJson($this->link($server) . '/startup')->assertForbidden();\n\n        $user2 = User::factory()->create();\n        $this->actingAs($user2)->getJson($this->link($server) . '/startup')->assertNotFound();\n    }\n\n    public static function permissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_STARTUP_READ]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Startup/UpdateStartupVariableTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Startup;\n\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Models\\EggVariable;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass UpdateStartupVariableTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that a startup variable can be edited successfully for a server.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testStartupVariableCanBeUpdated(array $permissions)\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount($permissions);\n        $server->fill([\n            'startup' => 'java {{SERVER_JARFILE}} --version {{BUNGEE_VERSION}}',\n        ])->save();\n\n        $response = $this->actingAs($user)->putJson($this->link($server) . '/startup/variable', [\n            'key' => 'BUNGEE_VERSION',\n            'value' => '1.2.3',\n        ]);\n\n        $response->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY);\n        $response->assertJsonPath('errors.0.code', 'ValidationException');\n        $response->assertJsonPath('errors.0.detail', 'value 只能由字母和数字组成。');\n\n        $response = $this->actingAs($user)->putJson($this->link($server) . '/startup/variable', [\n            'key' => 'BUNGEE_VERSION',\n            'value' => '123',\n        ]);\n\n        $response->assertOk();\n        $response->assertJsonPath('object', EggVariable::RESOURCE_NAME);\n        $this->assertJsonTransformedWith($response->json('attributes'), $server->variables[0]);\n        $response->assertJsonPath('meta.startup_command', 'java bungeecord.jar --version 123');\n        $response->assertJsonPath('meta.raw_startup_command', $server->startup);\n    }\n\n    /**\n     * Test that variables that are either not user_viewable, or not user_editable, cannot be\n     * updated via this endpoint.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testStartupVariableCannotBeUpdatedIfNotUserViewableOrEditable(array $permissions)\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        $egg = $this->cloneEggAndVariables($server->egg);\n        $egg->variables()->where('env_variable', 'BUNGEE_VERSION')->update(['user_viewable' => false]);\n        $egg->variables()->where('env_variable', 'SERVER_JARFILE')->update(['user_editable' => false]);\n\n        $server->fill(['egg_id' => $egg->id])->save();\n        $server->refresh();\n\n        $response = $this->actingAs($user)->putJson($this->link($server) . '/startup/variable', [\n            'key' => 'BUNGEE_VERSION',\n            'value' => '123',\n        ]);\n\n        $response->assertStatus(Response::HTTP_BAD_REQUEST);\n        $response->assertJsonPath('errors.0.code', 'BadRequestHttpException');\n        $response->assertJsonPath('errors.0.detail', '您试图编辑不存在的环境变量。');\n\n        $response = $this->actingAs($user)->putJson($this->link($server) . '/startup/variable', [\n            'key' => 'SERVER_JARFILE',\n            'value' => 'server2.jar',\n        ]);\n\n        $response->assertStatus(Response::HTTP_BAD_REQUEST);\n        $response->assertJsonPath('errors.0.code', 'BadRequestHttpException');\n        $response->assertJsonPath('errors.0.detail', '您试图编辑的环境变量是只读的。');\n    }\n\n    /**\n     * Test that a hidden variable is not included in the startup_command output for the server if\n     * a different variable is updated.\n     */\n    public function testHiddenVariablesAreNotReturnedInStartupCommandWhenUpdatingVariable()\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount();\n\n        $egg = $this->cloneEggAndVariables($server->egg);\n        $egg->variables()->first()->update(['user_viewable' => false]);\n\n        $server->fill([\n            'egg_id' => $egg->id,\n            'startup' => 'java {{SERVER_JARFILE}} --version {{BUNGEE_VERSION}}',\n        ])->save();\n\n        $server->refresh();\n\n        $response = $this->actingAs($user)->putJson($this->link($server) . '/startup/variable', [\n            'key' => 'SERVER_JARFILE',\n            'value' => 'server2.jar',\n        ]);\n\n        $response->assertOk();\n        $response->assertJsonPath('meta.startup_command', 'java server2.jar --version [hidden]');\n        $response->assertJsonPath('meta.raw_startup_command', $server->startup);\n    }\n\n    /**\n     * Test that an egg variable with a validation rule of 'nullable|string' works if no value\n     * is passed through in the request.\n     *\n     * @see https://github.com/pterodactyl/panel/issues/2433\n     */\n    public function testEggVariableWithNullableStringIsNotRequired()\n    {\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount();\n\n        $egg = $this->cloneEggAndVariables($server->egg);\n        $egg->variables()->first()->update(['rules' => 'nullable|string']);\n\n        $server->fill(['egg_id' => $egg->id])->save();\n        $server->refresh();\n\n        $response = $this->actingAs($user)->putJson($this->link($server) . '/startup/variable', [\n            'key' => 'BUNGEE_VERSION',\n            'value' => '',\n        ]);\n\n        $response->assertOk();\n        $response->assertJsonPath('attributes.server_value', null);\n    }\n\n    /**\n     * Test that a variable cannot be updated if the user does not have permission to perform\n     * that action, or they aren't assigned at all to the server.\n     */\n    public function testStartupVariableCannotBeUpdatedIfNotUserViewable()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_WEBSOCKET_CONNECT]);\n        $this->actingAs($user)->putJson($this->link($server) . '/startup/variable')->assertForbidden();\n\n        $user2 = User::factory()->create();\n        $this->actingAs($user2)->putJson($this->link($server) . '/startup/variable')->assertNotFound();\n    }\n\n    public static function permissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_STARTUP_UPDATE]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Subuser/CreateServerSubuserTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Subuser;\n\nuse Illuminate\\Support\\Str;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Foundation\\Testing\\WithFaker;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass CreateServerSubuserTest extends ClientApiIntegrationTestCase\n{\n    use WithFaker;\n\n    /**\n     * Test that a subuser can be created for a server.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testSubuserCanBeCreated(array $permissions)\n    {\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        $response = $this->actingAs($user)->postJson($this->link($server) . '/users', [\n            'email' => $email = $this->faker->email,\n            'permissions' => [\n                Permission::ACTION_USER_CREATE,\n            ],\n        ]);\n\n        $response->assertOk();\n\n        /** @var User $subuser */\n        $subuser = User::query()->where('email', $email)->firstOrFail();\n\n        $response->assertJsonPath('object', Subuser::RESOURCE_NAME);\n        $response->assertJsonPath('attributes.uuid', $subuser->uuid);\n        $response->assertJsonPath('attributes.permissions', [\n            Permission::ACTION_USER_CREATE,\n            Permission::ACTION_WEBSOCKET_CONNECT,\n        ]);\n\n        $expected = $response->json('attributes');\n        unset($expected['permissions']);\n\n        $this->assertJsonTransformedWith($expected, $subuser);\n    }\n\n    /**\n     * Tests that an error is returned if a subuser attempts to create a new subuser and assign\n     * permissions that their account does not also possess.\n     */\n    public function testErrorIsReturnedIfAssigningPermissionsNotAssignedToSelf()\n    {\n        [$user, $server] = $this->generateTestAccount([\n            Permission::ACTION_USER_CREATE,\n            Permission::ACTION_USER_READ,\n            Permission::ACTION_CONTROL_CONSOLE,\n        ]);\n\n        $response = $this->actingAs($user)->postJson($this->link($server) . '/users', [\n            'email' => $this->faker->email,\n            'permissions' => [\n                Permission::ACTION_USER_CREATE,\n                Permission::ACTION_USER_UPDATE, // This permission is not assigned to the subuser.\n            ],\n        ]);\n\n        $response->assertForbidden();\n        $response->assertJsonPath('errors.0.code', 'HttpForbiddenException');\n        $response->assertJsonPath('errors.0.detail', 'Cannot assign permissions to a subuser that your account does not actively possess.');\n    }\n\n    /**\n     * Throws some bad data at the API and ensures that a subuser cannot be created.\n     */\n    public function testSubuserWithExcessivelyLongEmailCannotBeCreated()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        $email = str_repeat(Str::random(20), 9) . '1@gmail.com'; // 191 is the hard limit for the column in MySQL.\n\n        $response = $this->actingAs($user)->postJson($this->link($server) . '/users', [\n            'email' => $email,\n            'permissions' => [\n                Permission::ACTION_USER_CREATE,\n            ],\n        ]);\n\n        $response->assertOk();\n\n        $response = $this->actingAs($user)->postJson($this->link($server) . '/users', [\n            'email' => $email . '.au',\n            'permissions' => [\n                Permission::ACTION_USER_CREATE,\n            ],\n        ]);\n\n        $response->assertStatus(Response::HTTP_UNPROCESSABLE_ENTITY);\n        $response->assertJsonPath('errors.0.detail', 'email 必须介于 1 - 191 个字符之间。');\n        $response->assertJsonPath('errors.0.meta.source_field', 'email');\n    }\n\n    /**\n     * Test that creating a subuser when there is already an account with that email runs\n     * as expected and does not create a new account.\n     */\n    public function testCreatingSubuserWithSameEmailAsExistingUserWorks()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        /** @var User $existing */\n        $existing = User::factory()->create(['email' => $this->faker->email]);\n\n        $response = $this->actingAs($user)->postJson($this->link($server) . '/users', [\n            'email' => $existing->email,\n            'permissions' => [\n                Permission::ACTION_USER_CREATE,\n            ],\n        ]);\n\n        $response->assertOk();\n        $response->assertJsonPath('object', Subuser::RESOURCE_NAME);\n        $response->assertJsonPath('attributes.uuid', $existing->uuid);\n    }\n\n    /**\n     * Test that an error is returned if the account associated with an email address is already\n     * associated with the server instance.\n     */\n    public function testAddingSubuserThatAlreadyIsAssignedReturnsError()\n    {\n        [$user, $server] = $this->generateTestAccount();\n\n        $response = $this->actingAs($user)->postJson($this->link($server) . '/users', [\n            'email' => $email = $this->faker->email,\n            'permissions' => [\n                Permission::ACTION_USER_CREATE,\n            ],\n        ]);\n\n        $response->assertOk();\n\n        $response = $this->actingAs($user)->postJson($this->link($server) . '/users', [\n            'email' => $email,\n            'permissions' => [\n                Permission::ACTION_USER_CREATE,\n            ],\n        ]);\n\n        $response->assertStatus(Response::HTTP_BAD_REQUEST);\n        $response->assertJsonPath('errors.0.code', 'ServerSubuserExistsException');\n        $response->assertJsonPath('errors.0.detail', '具有该电子邮箱地址的用户已被指定为该服务器的子用户。');\n    }\n\n    public static function permissionsDataProvider(): array\n    {\n        return [[[]], [[Permission::ACTION_USER_CREATE]]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Subuser/DeleteSubuserTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Subuser;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Support\\Facades\\Bus;\nuse Pterodactyl\\Jobs\\RevokeSftpAccessJob;\nuse PHPUnit\\Framework\\Attributes\\TestWith;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass DeleteSubuserTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Guards against PHP's exciting behavior where a string can be cast to an int and only\n     * the first numeric digits are returned. This causes UUIDs to be returned as an int when\n     * looking up users, thus returning the wrong subusers (or no subuser at all).\n     *\n     * For example, 12aaaaaa-bbbb-cccc-ddddeeeeffff would be cast to \"12\" if you tried to cast\n     * it to an integer. Then, in the deep API middlewares you would end up trying to load a user\n     * with an ID of 12, which may or may not exist and be wrongly assigned to the model object.\n     *\n     * @see https://github.com/pterodactyl/panel/issues/2359\n     */\n    #[TestWith([null])]\n    #[TestWith(['18180000'])]\n    public function testCorrectSubuserIsDeletedFromServer(?string $prefix)\n    {\n        Bus::fake([RevokeSftpAccessJob::class]);\n\n        [$user, $server] = $this->generateTestAccount();\n\n        /** @var User $differentUser */\n        $differentUser = User::factory()->create();\n\n        $real = Uuid::uuid4()->toString();\n        // Generate a UUID that lines up with a user in the database if it were to be cast to an int.\n        $uuid = ($prefix ?: $differentUser->id) . substr($real, strlen($prefix ?: (string) $differentUser->id));\n\n        /** @var User $subuser */\n        $subuser = User::factory()->create(['uuid' => $uuid]);\n\n        Subuser::query()->forceCreate([\n            'user_id' => $subuser->id,\n            'server_id' => $server->id,\n            'permissions' => [Permission::ACTION_WEBSOCKET_CONNECT],\n        ]);\n\n        $this->withoutExceptionHandling()\n            ->actingAs($user)\n            ->deleteJson($this->link($server) . \"/users/$subuser->uuid\")->assertNoContent();\n\n        Bus::assertDispatchedTimes(function (RevokeSftpAccessJob $job) use ($subuser, $server) {\n            return $job->user === $subuser->uuid && $job->target->is($server);\n        });\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Subuser/SubuserAuthorizationTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Subuser;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Subuser;\nuse Illuminate\\Support\\Facades\\Bus;\nuse Pterodactyl\\Jobs\\RevokeSftpAccessJob;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass SubuserAuthorizationTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that mismatched subusers are not accessible to a server.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('methodDataProvider')]\n    public function testUserCannotAccessResourceBelongingToOtherServers(string $method)\n    {\n        Bus::fake([RevokeSftpAccessJob::class]);\n\n        // Generic subuser, the specific resource we're trying to access.\n        /** @var User $internal */\n        $internal = User::factory()->create();\n\n        // The API $user is the owner of $server1.\n        [$user, $server1] = $this->generateTestAccount();\n        // Will be a subuser of $server2.\n        $server2 = $this->createServerModel();\n        // And as no access to $server3.\n        $server3 = $this->createServerModel();\n\n        // Set the API $user as a subuser of server 2, but with no permissions\n        // to do anything with the subusers for that server.\n        Subuser::factory()->create(['server_id' => $server2->id, 'user_id' => $user->id]);\n\n        Subuser::factory()->create(['server_id' => $server1->id, 'user_id' => $internal->id]);\n        Subuser::factory()->create(['server_id' => $server2->id, 'user_id' => $internal->id]);\n        Subuser::factory()->create(['server_id' => $server3->id, 'user_id' => $internal->id]);\n\n        // This route is acceptable since they're accessing a subuser on their own server.\n        $this->actingAs($user)->json($method, $this->link($server1, '/users/' . $internal->uuid))->assertStatus($method === 'POST' ? 422 : ($method === 'DELETE' ? 204 : 200));\n\n        // This route can be revealed since the subuser belongs to the correct server, but\n        // errors out with a 403 since $user does not have the right permissions for this.\n        $this->actingAs($user)->json($method, $this->link($server2, '/users/' . $internal->uuid))->assertForbidden();\n        $this->actingAs($user)->json($method, $this->link($server3, '/users/' . $internal->uuid))->assertNotFound();\n\n        if ($method === 'DELETE') {\n            Bus::assertDispatchedTimes(function (RevokeSftpAccessJob $job) use ($server1, $internal) {\n                return $job->user === $internal->uuid && $job->target->is($server1);\n            });\n        } else {\n            Bus::assertNotDispatched(RevokeSftpAccessJob::class);\n        }\n    }\n\n    public static function methodDataProvider(): array\n    {\n        return [['GET'], ['POST'], ['DELETE']];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/Subuser/UpdateSubuserTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server\\Subuser;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Permission;\nuse Illuminate\\Support\\Facades\\Bus;\nuse Pterodactyl\\Jobs\\RevokeSftpAccessJob;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass UpdateSubuserTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that the correct permissions are applied to the account when making updates\n     * to a subusers permissions.\n     */\n    public function testCorrectPermissionsAreRequiredForUpdating()\n    {\n        Bus::fake([RevokeSftpAccessJob::class]);\n\n        [$user, $server] = $this->generateTestAccount(['user.read']);\n\n        $subuser = Subuser::factory()\n            ->for(User::factory()->create())\n            ->for($server)\n            ->create([\n                'permissions' => ['control.start'],\n            ]);\n\n        $this->postJson(\n            $endpoint = \"/api/client/servers/$server->uuid/users/{$subuser->user->uuid}\",\n            $data = [\n                'permissions' => [\n                    'control.start',\n                    'control.stop',\n                ],\n            ]\n        )\n            ->assertUnauthorized();\n\n        $this->actingAs($subuser->user)->postJson($endpoint, $data)->assertForbidden();\n        $this->actingAs($user)->postJson($endpoint, $data)->assertForbidden();\n\n        $server->subusers()->where('user_id', $user->id)->update([\n            'permissions' => [\n                Permission::ACTION_USER_UPDATE,\n                Permission::ACTION_CONTROL_START,\n                Permission::ACTION_CONTROL_STOP,\n            ],\n        ]);\n\n        $this->postJson($endpoint, $data)->assertOk();\n\n        Bus::assertDispatchedTimes(function (RevokeSftpAccessJob $job) use ($server, $subuser) {\n            return $job->user === $subuser->user->uuid && $job->target->is($server);\n        });\n    }\n\n    /**\n     * Tests that permissions for the account are updated and any extraneous values\n     * we don't know about are removed.\n     */\n    public function testPermissionsAreSavedToAccount()\n    {\n        Bus::fake([RevokeSftpAccessJob::class]);\n\n        [$user, $server] = $this->generateTestAccount();\n\n        /** @var Subuser $subuser */\n        $subuser = Subuser::factory()\n            ->for(User::factory()->create())\n            ->for($server)\n            ->create([\n                'permissions' => ['control.restart', 'websocket.connect', 'foo.bar'],\n            ]);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/users/{$subuser->user->uuid}\", [\n                'permissions' => [\n                    'control.start',\n                    'control.stop',\n                    'control.stop',\n                    'foo.bar',\n                    'power.fake',\n                ],\n            ])\n            ->assertOk();\n\n        $subuser->refresh();\n        $this->assertEqualsCanonicalizing(\n            ['control.start', 'control.stop', 'websocket.connect'],\n            $subuser->permissions\n        );\n\n        Bus::assertDispatchedTimes(function (RevokeSftpAccessJob $job) use ($server, $subuser) {\n            return $job->user === $subuser->user->uuid && $job->target->is($server);\n        });\n    }\n\n    /**\n     * Ensure a subuser cannot assign permissions to an account that they do not have\n     * themselves.\n     */\n    public function testUserCannotAssignPermissionsTheyDoNotHave()\n    {\n        Bus::fake([RevokeSftpAccessJob::class]);\n\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_USER_READ, Permission::ACTION_USER_UPDATE]);\n\n        $subuser = Subuser::factory()\n            ->for(User::factory()->create())\n            ->for($server)\n            ->create(['permissions' => ['foo.bar']]);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/users/{$subuser->user->uuid}\", [\n                'permissions' => [Permission::ACTION_USER_READ, Permission::ACTION_CONTROL_CONSOLE],\n            ])\n            ->assertForbidden();\n\n        $this->assertEqualsCanonicalizing(['foo.bar'], $subuser->refresh()->permissions);\n\n        Bus::assertNothingDispatched();\n    }\n\n    /**\n     * Test that a user cannot update thyself.\n     */\n    public function testUserCannotUpdateSelf()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_USER_READ, Permission::ACTION_USER_UPDATE]);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/users/$user->uuid\", [])\n            ->assertForbidden();\n    }\n\n    /**\n     * Test that an error is returned if you attempt to update a subuser on a different account.\n     */\n    public function testCannotUpdateSubuserForDifferentServer()\n    {\n        [$user, $server] = $this->generateTestAccount();\n        [$user2] = $this->generateTestAccount(['foo.bar']);\n\n        $this->actingAs($user)\n            ->postJson(\"/api/client/servers/$server->uuid/users/$user2->uuid\", [])\n            ->assertNotFound();\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/Server/WebsocketControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client\\Server;\n\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Http\\Response;\nuse Lcobucci\\JWT\\Configuration;\nuse Pterodactyl\\Models\\Permission;\nuse Lcobucci\\JWT\\Signer\\Hmac\\Sha256;\nuse Lcobucci\\JWT\\Signer\\Key\\InMemory;\nuse Lcobucci\\JWT\\Validation\\Constraint\\SignedWith;\nuse Pterodactyl\\Tests\\Integration\\Api\\Client\\ClientApiIntegrationTestCase;\n\nclass WebsocketControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that a subuser attempting to connect to the websocket receives an error if they\n     * do not explicitly have the permission.\n     */\n    public function testSubuserWithoutWebsocketPermissionReceivesError()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_CONTROL_RESTART]);\n\n        $this->actingAs($user)->getJson(\"/api/client/servers/$server->uuid/websocket\")\n            ->assertStatus(Response::HTTP_FORBIDDEN)\n            ->assertJsonPath('errors.0.code', 'HttpForbiddenException')\n            ->assertJsonPath('errors.0.detail', '您无权连接到此服务器的 websocket。');\n    }\n\n    /**\n     * Confirm users cannot access the websocket for another user's server.\n     */\n    public function testUserWithoutPermissionForServerReceivesError()\n    {\n        [, $server] = $this->generateTestAccount([Permission::ACTION_WEBSOCKET_CONNECT]);\n        [$user] = $this->generateTestAccount([Permission::ACTION_WEBSOCKET_CONNECT]);\n\n        $this->actingAs($user)->getJson(\"/api/client/servers/$server->uuid/websocket\")\n            ->assertStatus(Response::HTTP_NOT_FOUND);\n    }\n\n    /**\n     * Test that the expected permissions are returned for the server owner and that the JWT is\n     * configured correctly.\n     */\n    public function testJwtAndWebsocketUrlAreReturnedForServerOwner()\n    {\n        /** @var \\Pterodactyl\\Models\\User $user */\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount();\n\n        // Force the node to HTTPS since we want to confirm it gets transformed to wss:// in the URL.\n        $server->node->scheme = 'https';\n        $server->node->save();\n\n        $response = $this->actingAs($user)->getJson(\"/api/client/servers/$server->uuid/websocket\");\n\n        $response->assertOk();\n        $response->assertJsonStructure(['data' => ['token', 'socket']]);\n\n        $connection = $response->json('data.socket');\n        $this->assertStringStartsWith('wss://', $connection, 'Failed asserting that websocket connection address has expected \"wss://\" prefix.');\n        $this->assertStringEndsWith(\"/api/servers/$server->uuid/ws\", $connection, 'Failed asserting that websocket connection address uses expected Wings endpoint.');\n\n        $config = Configuration::forSymmetricSigner(new Sha256(), $key = InMemory::plainText($server->node->getDecryptedKey()));\n        $config->setValidationConstraints(new SignedWith(new Sha256(), $key));\n        /** @var \\Lcobucci\\JWT\\Token\\Plain $token */\n        $token = $config->parser()->parse($response->json('data.token'));\n\n        $this->assertTrue(\n            $config->validator()->validate($token, ...$config->validationConstraints()),\n            'Failed to validate that the JWT data returned was signed using the Node\\'s secret key.'\n        );\n\n        // The way we generate times for the JWT will truncate the microseconds from the\n        // time, but CarbonImmutable::now() will include them, thus causing test failures.\n        //\n        // This little chunk of logic just strips those out by generating a new CarbonImmutable\n        // instance from the current timestamp, which is how the JWT works. We also need to\n        // switch to UTC here for consistency.\n        $expect = CarbonImmutable::createFromTimestamp(CarbonImmutable::now()->getTimestamp())->timezone('UTC');\n\n        // Check that the claims are generated correctly.\n        $this->assertTrue($token->hasBeenIssuedBy(config('app.url')));\n        $this->assertTrue($token->isPermittedFor($server->node->getConnectionAddress()));\n        $this->assertEquals($expect, $token->claims()->get('iat'));\n        $this->assertEquals($expect->subMinutes(5), $token->claims()->get('nbf'));\n        $this->assertEquals($expect->addMinutes(10), $token->claims()->get('exp'));\n        $this->assertSame($user->id, $token->claims()->get('user_id'));\n        $this->assertSame($server->uuid, $token->claims()->get('server_uuid'));\n        $this->assertSame(['*'], $token->claims()->get('permissions'));\n    }\n\n    /**\n     * Test that the subuser's permissions are passed along correctly in the generated JWT.\n     */\n    public function testJwtIsConfiguredCorrectlyForServerSubuser()\n    {\n        $permissions = [Permission::ACTION_WEBSOCKET_CONNECT, Permission::ACTION_CONTROL_CONSOLE];\n\n        /** @var \\Pterodactyl\\Models\\User $user */\n        /** @var \\Pterodactyl\\Models\\Server $server */\n        [$user, $server] = $this->generateTestAccount($permissions);\n\n        $response = $this->actingAs($user)->getJson(\"/api/client/servers/$server->uuid/websocket\");\n\n        $response->assertOk();\n        $response->assertJsonStructure(['data' => ['token', 'socket']]);\n\n        $config = Configuration::forSymmetricSigner(new Sha256(), $key = InMemory::plainText($server->node->getDecryptedKey()));\n        $config->setValidationConstraints(new SignedWith(new Sha256(), $key));\n        /** @var \\Lcobucci\\JWT\\Token\\Plain $token */\n        $token = $config->parser()->parse($response->json('data.token'));\n\n        $this->assertTrue(\n            $config->validator()->validate($token, ...$config->validationConstraints()),\n            'Failed to validate that the JWT data returned was signed using the Node\\'s secret key.'\n        );\n\n        // Check that the claims are generated correctly.\n        $this->assertSame($permissions, $token->claims()->get('permissions'));\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Client/TwoFactorControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Client;\n\nuse Carbon\\Carbon;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Http\\Response;\nuse PragmaRX\\Google2FA\\Google2FA;\nuse Pterodactyl\\Models\\RecoveryToken;\nuse PHPUnit\\Framework\\ExpectationFailedException;\n\nclass TwoFactorControllerTest extends ClientApiIntegrationTestCase\n{\n    /**\n     * Test that image data for enabling 2FA is returned by the endpoint and that the user\n     * record in the database is updated as expected.\n     */\n    public function testTwoFactorImageDataIsReturned()\n    {\n        /** @var User $user */\n        $user = User::factory()->create(['use_totp' => false]);\n\n        $this->assertFalse($user->use_totp);\n        $this->assertEmpty($user->totp_secret);\n        $this->assertEmpty($user->totp_authenticated_at);\n\n        $response = $this->actingAs($user)->getJson('/api/client/account/two-factor');\n\n        $response->assertOk();\n        $response->assertJsonStructure(['data' => ['image_url_data']]);\n\n        $user = $user->refresh();\n\n        $this->assertFalse($user->use_totp);\n        $this->assertNotEmpty($user->totp_secret);\n        $this->assertEmpty($user->totp_authenticated_at);\n    }\n\n    /**\n     * Test that an error is returned if the user's account already has 2FA enabled on it.\n     */\n    public function testErrorIsReturnedWhenTwoFactorIsAlreadyEnabled()\n    {\n        /** @var User $user */\n        $user = User::factory()->create(['use_totp' => true]);\n\n        $response = $this->actingAs($user)->getJson('/api/client/account/two-factor');\n\n        $response->assertStatus(Response::HTTP_BAD_REQUEST);\n        $response->assertJsonPath('errors.0.code', 'BadRequestHttpException');\n        $response->assertJsonPath('errors.0.detail', '此帐户已启用动态口令认证。');\n    }\n\n    /**\n     * Test that a validation error is thrown if invalid data is passed to the 2FA endpoint.\n     */\n    public function testValidationErrorIsReturnedIfInvalidDataIsPassedToEnabled2FA()\n    {\n        /** @var User $user */\n        $user = User::factory()->create(['use_totp' => false]);\n\n        $this->actingAs($user)\n            ->postJson('/api/client/account/two-factor', ['code' => ''])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.meta.rule', 'required')\n            ->assertJsonPath('errors.0.meta.source_field', 'code')\n            ->assertJsonPath('errors.1.meta.rule', 'required')\n            ->assertJsonPath('errors.1.meta.source_field', 'password');\n    }\n\n    /**\n     * Tests that 2FA can be enabled on an account for the user.\n     */\n    public function testTwoFactorCanBeEnabledOnAccount()\n    {\n        /** @var User $user */\n        $user = User::factory()->create(['use_totp' => false]);\n\n        // Make the initial call to get the account setup for 2FA.\n        $this->actingAs($user)->getJson('/api/client/account/two-factor')->assertOk();\n\n        $user = $user->refresh();\n        $this->assertNotNull($user->totp_secret);\n\n        /** @var Google2FA $service */\n        $service = $this->app->make(Google2FA::class);\n\n        $secret = decrypt($user->totp_secret);\n        $token = $service->getCurrentOtp($secret);\n\n        $response = $this->actingAs($user)->postJson('/api/client/account/two-factor', [\n            'code' => $token,\n            'password' => 'password',\n        ]);\n\n        $response->assertOk();\n        $response->assertJsonPath('object', 'recovery_tokens');\n\n        $user = $user->refresh();\n        $this->assertTrue($user->use_totp);\n\n        $tokens = RecoveryToken::query()->where('user_id', $user->id)->get();\n        $this->assertCount(10, $tokens);\n        $this->assertStringStartsWith('$2y$10$', $tokens[0]->token);\n        // Ensure the recovery tokens that were created include a \"created_at\" timestamp\n        // value on them.\n        //\n        // @see https://github.com/pterodactyl/panel/issues/3163\n        $this->assertNotNull($tokens[0]->created_at);\n\n        $tokens = $tokens->pluck('token')->toArray();\n\n        foreach ($response->json('attributes.tokens') as $raw) {\n            foreach ($tokens as $hashed) {\n                if (password_verify($raw, $hashed)) {\n                    continue 2;\n                }\n            }\n\n            throw new ExpectationFailedException(sprintf('无法断言令牌 [%s] 作为 recovery_tokens 表中的哈希值存在。', $raw));\n        }\n    }\n\n    /**\n     * Test that two-factor authentication can be disabled on an account as long as the password\n     * provided is valid for the account.\n     */\n    public function testTwoFactorCanBeDisabledOnAccount()\n    {\n        Carbon::setTestNow(Carbon::now());\n\n        /** @var User $user */\n        $user = User::factory()->create(['use_totp' => true]);\n\n        $response = $this->actingAs($user)->postJson('/api/client/account/two-factor/disable', [\n            'password' => 'invalid',\n        ]);\n\n        $response->assertStatus(Response::HTTP_BAD_REQUEST);\n        $response->assertJsonPath('errors.0.code', 'BadRequestHttpException');\n        $response->assertJsonPath('errors.0.detail', '提供的密码无效。');\n\n        $response = $this->actingAs($user)->postJson('/api/client/account/two-factor/disable', [\n            'password' => 'password',\n        ]);\n\n        $response->assertStatus(Response::HTTP_NO_CONTENT);\n\n        $user = $user->refresh();\n        $this->assertFalse($user->use_totp);\n        $this->assertNotNull($user->totp_authenticated_at);\n        $this->assertSame(Carbon::now()->toAtomString(), $user->totp_authenticated_at->toAtomString());\n    }\n\n    /**\n     * Test that no error is returned when trying to disabled two factor on an account where it\n     * was not enabled in the first place.\n     */\n    public function testNoErrorIsReturnedIfTwoFactorIsNotEnabled()\n    {\n        Carbon::setTestNow(Carbon::now());\n\n        /** @var User $user */\n        $user = User::factory()->create(['use_totp' => false]);\n\n        $response = $this->actingAs($user)->postJson('/api/client/account/two-factor/disable', [\n            'password' => 'password',\n        ]);\n\n        $response->assertStatus(Response::HTTP_NO_CONTENT);\n    }\n\n    /**\n     * Test that a valid account password is required when enabling two-factor.\n     */\n    public function testEnablingTwoFactorRequiresValidPassword()\n    {\n        $user = User::factory()->create(['use_totp' => false]);\n\n        $this->actingAs($user)\n            ->postJson('/api/client/account/two-factor', [\n                'code' => '123456',\n                'password' => 'foo',\n            ])\n            ->assertStatus(Response::HTTP_BAD_REQUEST)\n            ->assertJsonPath('errors.0.detail', '提供的密码无效。');\n\n        $this->assertFalse($user->refresh()->use_totp);\n    }\n\n    /**\n     * Test that a valid account password is required when disabling two-factor.\n     */\n    public function testDisablingTwoFactorRequiresValidPassword()\n    {\n        $user = User::factory()->create(['use_totp' => true]);\n\n        $this->actingAs($user)\n            ->postJson('/api/client/account/two-factor/disable', [\n                'password' => 'foo',\n            ])\n            ->assertStatus(Response::HTTP_BAD_REQUEST)\n            ->assertJsonPath('errors.0.detail', '提供的密码无效。');\n\n        $this->assertTrue($user->refresh()->use_totp);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Remote/ServerTransferControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Remote;\n\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\Location;\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Models\\ServerTransfer;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\n\nclass ServerTransferControllerTest extends IntegrationTestCase\n{\n    protected ServerTransfer $transfer;\n\n    public function setup(): void\n    {\n        parent::setUp();\n\n        $server = $this->createServerModel();\n\n        $new = Node::factory()\n            ->for(Location::factory())\n            ->has(Allocation::factory())\n            ->create();\n\n        $this->transfer = ServerTransfer::factory()->for($server)->create([\n            'old_allocation' => $server->allocation_id,\n            'new_allocation' => $new->allocations->first()->id,\n            'new_node' => $new->id,\n            'old_node' => $server->node_id,\n        ]);\n    }\n\n    public function testSuccessStatusUpdateCanBeSentFromNewNode(): void\n    {\n        $server = $this->transfer->server;\n        $newNode = $this->transfer->newNode;\n\n        $this\n            ->withHeader('Authorization', \"Bearer $newNode->daemon_token_id.\" . $newNode->getDecryptedKey())\n            ->postJson(\"/api/remote/servers/{$server->uuid}/transfer/success\")\n            ->assertNoContent();\n\n        $this->assertTrue($this->transfer->refresh()->successful);\n    }\n\n    public function testFailureStatusUpdateCanBeSentFromOldNode(): void\n    {\n        $server = $this->transfer->server;\n        $oldNode = $this->transfer->oldNode;\n\n        $this->withHeader('Authorization', \"Bearer $oldNode->daemon_token_id.\" . $oldNode->getDecryptedKey())\n            ->postJson(\"/api/remote/servers/{$server->uuid}/transfer/failure\")\n            ->assertNoContent();\n\n        $this->assertFalse($this->transfer->refresh()->successful);\n    }\n\n    public function testFailureStatusUpdateCanBeSentFromNewNode(): void\n    {\n        $server = $this->transfer->server;\n        $newNode = $this->transfer->newNode;\n\n        $this->withHeader('Authorization', \"Bearer $newNode->daemon_token_id.\" . $newNode->getDecryptedKey())\n            ->postJson(\"/api/remote/servers/{$server->uuid}/transfer/failure\")\n            ->assertNoContent();\n\n        $this->assertFalse($this->transfer->refresh()->successful);\n    }\n\n    public function testSuccessStatusUpdateCannotBeSentFromOldNode(): void\n    {\n        $server = $this->transfer->server;\n        $oldNode = $this->transfer->oldNode;\n\n        $this->withHeader('Authorization', \"Bearer $oldNode->daemon_token_id.\" . $oldNode->getDecryptedKey())\n            ->postJson(\"/api/remote/servers/{$server->uuid}/transfer/success\")\n            ->assertForbidden()\n            ->assertJsonPath('errors.0.code', 'HttpForbiddenException')\n            ->assertJsonPath('errors.0.detail', 'Requesting node does not have permission to access this server.');\n\n        $this->assertNull($this->transfer->refresh()->successful);\n    }\n\n    public function testSuccessStatusUpdateCannotBeSentFromUnauthorizedNode(): void\n    {\n        $server = $this->transfer->server;\n        $node = Node::factory()->for(Location::factory())->create();\n\n        $this->withHeader('Authorization', \"Bearer $node->daemon_token_id.\" . $node->getDecryptedKey())\n            ->postJson(\"/api/remote/servers/$server->uuid/transfer/success\")\n            ->assertForbidden()\n            ->assertJsonPath('errors.0.code', 'HttpForbiddenException')\n            ->assertJsonPath('errors.0.detail', 'Requesting node does not have permission to access this server.');\n\n        $this->assertNull($this->transfer->refresh()->successful);\n    }\n\n    public function testFailureStatusUpdateCannotBeSentFromUnauthorizedNode(): void\n    {\n        $server = $this->transfer->server;\n        $node = Node::factory()->for(Location::factory())->create();\n\n        $this->withHeader('Authorization', \"Bearer $node->daemon_token_id.\" . $node->getDecryptedKey())\n            ->postJson(\"/api/remote/servers/$server->uuid/transfer/failure\")->assertForbidden()\n            ->assertJsonPath('errors.0.code', 'HttpForbiddenException')\n            ->assertJsonPath('errors.0.detail', 'Requesting node does not have permission to access this server.');\n\n        $this->assertNull($this->transfer->refresh()->successful);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Api/Remote/SftpAuthenticationControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Api\\Remote;\n\nuse phpseclib3\\Crypt\\EC;\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Permission;\nuse Pterodactyl\\Models\\UserSSHKey;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\n\nclass SftpAuthenticationControllerTest extends IntegrationTestCase\n{\n    protected User $user;\n\n    protected Server $server;\n\n    /**\n     * Sets up the tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        [$user, $server] = $this->generateTestAccount();\n\n        $user->update(['password' => password_hash('foobar', PASSWORD_DEFAULT)]);\n\n        $this->user = $user;\n        $this->server = $server;\n\n        $this->setAuthorization();\n    }\n\n    /**\n     * Test that a public key is validated correctly.\n     */\n    public function testPublicKeyIsValidatedCorrectly()\n    {\n        $key = UserSSHKey::factory()->for($this->user)->create();\n\n        $this->postJson('/api/remote/sftp/auth', [])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.meta.source_field', 'username')\n            ->assertJsonPath('errors.0.meta.rule', 'required')\n            ->assertJsonPath('errors.1.meta.source_field', 'password')\n            ->assertJsonPath('errors.1.meta.rule', 'required');\n\n        $data = [\n            'type' => 'public_key',\n            'username' => $this->getUsername(),\n            'password' => $key->public_key,\n        ];\n\n        $this->postJson('/api/remote/sftp/auth', $data)\n            ->assertOk()\n            ->assertJsonPath('server', $this->server->uuid)\n            ->assertJsonPath('permissions', ['*']);\n\n        $key->delete();\n        $this->postJson('/api/remote/sftp/auth', $data)->assertForbidden();\n        $this->postJson('/api/remote/sftp/auth', array_merge($data, ['type' => null]))->assertForbidden();\n    }\n\n    /**\n     * Test that an account password is validated correctly.\n     */\n    public function testPasswordIsValidatedCorrectly()\n    {\n        $this->postJson('/api/remote/sftp/auth', [\n            'username' => $this->getUsername(),\n            'password' => '',\n        ])\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.meta.source_field', 'password')\n            ->assertJsonPath('errors.0.meta.rule', 'required');\n\n        $this->postJson('/api/remote/sftp/auth', [\n            'username' => $this->getUsername(),\n            'password' => 'wrong password',\n        ])\n            ->assertForbidden();\n\n        $this->user->update(['password' => password_hash('foobar', PASSWORD_DEFAULT)]);\n\n        $this->postJson('/api/remote/sftp/auth', [\n            'username' => $this->getUsername(),\n            'password' => 'foobar',\n        ])\n            ->assertOk();\n    }\n\n    /**\n     * Test that providing an invalid key and/or invalid username triggers the throttle on\n     * the endpoint.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('authorizationTypeDataProvider')]\n    public function testUserIsThrottledIfInvalidCredentialsAreProvided()\n    {\n        for ($i = 0; $i <= 10; ++$i) {\n            $this->postJson('/api/remote/sftp/auth', [\n                'type' => 'public_key',\n                'username' => $i % 2 === 0 ? $this->user->username : $this->getUsername(),\n                'password' => 'invalid key',\n            ])\n                ->assertStatus($i === 10 ? 429 : 403);\n        }\n    }\n\n    /**\n     * Test that the user is not throttled so long as a valid public key is provided, even\n     * if it doesn't actually exist in the database for the user.\n     */\n    public function testUserIsNotThrottledIfNoPublicKeyMatches()\n    {\n        for ($i = 0; $i <= 10; ++$i) {\n            $this->postJson('/api/remote/sftp/auth', [\n                'type' => 'public_key',\n                'username' => $this->getUsername(),\n                'password' => EC::createKey('Ed25519')->getPublicKey()->toString('OpenSSH'),\n            ])\n                ->assertForbidden();\n        }\n    }\n\n    /**\n     * Test that a request is rejected if the credentials are valid but the username indicates\n     * a server on a different node.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('authorizationTypeDataProvider')]\n    public function testRequestIsRejectedIfServerBelongsToDifferentNode(string $type)\n    {\n        $node2 = $this->createServerModel()->node;\n\n        $this->setAuthorization($node2);\n\n        $password = $type === 'public_key'\n            ? UserSSHKey::factory()->for($this->user)->create()->public_key\n            : 'foobar';\n\n        $this->postJson('/api/remote/sftp/auth', [\n            'type' => 'public_key',\n            'username' => $this->getUsername(),\n            'password' => $password,\n        ])\n            ->assertForbidden();\n    }\n\n    public function testRequestIsDeniedIfUserLacksSftpPermission()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_FILE_READ]);\n\n        $user->update(['password' => password_hash('foobar', PASSWORD_DEFAULT)]);\n\n        $this->setAuthorization($server->node);\n\n        $this->postJson('/api/remote/sftp/auth', [\n            'username' => $user->username . '.' . $server->uuidShort,\n            'password' => 'foobar',\n        ])\n            ->assertForbidden()\n            ->assertJsonPath('errors.0.detail', '您无权访问此服务器的 SFTP。');\n    }\n\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('serverStateDataProvider')]\n    public function testInvalidServerStateReturnsConflictError(string $status)\n    {\n        $this->server->update(['status' => $status]);\n\n        $this->postJson('/api/remote/sftp/auth', ['username' => $this->getUsername(), 'password' => 'foobar'])\n            ->assertStatus(409);\n    }\n\n    /**\n     * Test that permissions are returned for the user account correctly.\n     */\n    public function testUserPermissionsAreReturnedCorrectly()\n    {\n        [$user, $server] = $this->generateTestAccount([Permission::ACTION_FILE_READ, Permission::ACTION_FILE_SFTP]);\n\n        $user->update(['password' => password_hash('foobar', PASSWORD_DEFAULT)]);\n\n        $this->setAuthorization($server->node);\n\n        $data = [\n            'username' => $user->username . '.' . $server->uuidShort,\n            'password' => 'foobar',\n        ];\n\n        $this->postJson('/api/remote/sftp/auth', $data)\n            ->assertOk()\n            ->assertJsonPath('permissions', [Permission::ACTION_FILE_READ, Permission::ACTION_FILE_SFTP]);\n\n        $user->update(['root_admin' => true]);\n\n        $this->postJson('/api/remote/sftp/auth', $data)\n            ->assertOk()\n            ->assertJsonPath('permissions.0', '*');\n\n        $this->setAuthorization();\n        $data['username'] = $user->username . '.' . $this->server->uuidShort;\n\n        $this->post('/api/remote/sftp/auth', $data)\n            ->assertOk()\n            ->assertJsonPath('permissions.0', '*');\n\n        $user->update(['root_admin' => false]);\n        $this->post('/api/remote/sftp/auth', $data)->assertForbidden();\n    }\n\n    public static function authorizationTypeDataProvider(): array\n    {\n        return [\n            'password auth' => ['password'],\n            'public key auth' => ['public_key'],\n        ];\n    }\n\n    public static function serverStateDataProvider(): array\n    {\n        return [\n            'installing' => [Server::STATUS_INSTALLING],\n            'suspended' => [Server::STATUS_SUSPENDED],\n            'restoring a backup' => [Server::STATUS_RESTORING_BACKUP],\n        ];\n    }\n\n    /**\n     * Returns the username for connecting to SFTP.\n     */\n    protected function getUsername(bool $long = false): string\n    {\n        return $this->user->username . '.' . ($long ? $this->server->uuid : $this->server->uuidShort);\n    }\n\n    /**\n     * Sets the authorization header for the rest of the test.\n     */\n    protected function setAuthorization(?Node $node = null): void\n    {\n        $node = $node ?? $this->server->node;\n\n        $this->withHeader('Authorization', 'Bearer ' . $node->daemon_token_id . '.' . decrypt($node->daemon_token));\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Http/Controllers/Admin/UserController/DeleteUserTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Http\\Controllers\\Admin\\UserController;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Tests\\Integration\\Http\\HttpTestCase;\n\nclass DeleteUserTest extends HttpTestCase\n{\n    public function testNonAdminCannotAccessEndpoint(): void\n    {\n        $this->actingAs(User::factory()->create())\n            ->delete(route('admin.users.delete', ['user' => User::factory()->create()]))\n            ->assertForbidden();\n    }\n\n    public function testCannotDeleteSelf(): void\n    {\n        $this->actingAs($user = User::factory()->admin()->create())\n            ->delete(route('admin.users.delete', ['user' => $user]))\n            ->assertBadRequest()\n            ->assertJsonPath('errors.0.detail', __('admin/user.exceptions.delete_self'));\n\n        $this->assertModelExists($user);\n    }\n\n    public function testUserIsDeleted(): void\n    {\n        $user = User::factory()->create();\n\n        $this->actingAs(User::factory()->admin()->create())\n            ->delete(route('admin.users.delete', ['user' => $user]))\n            ->assertRedirectToRoute('admin.users');\n\n        $this->assertModelMissing($user);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Http/Controllers/Auth/LoginCheckpointControllerTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Http\\Controllers\\Auth;\n\nuse Carbon\\Carbon;\nuse Pterodactyl\\Models\\User;\nuse PragmaRX\\Google2FA\\Google2FA;\nuse Illuminate\\Auth\\Events\\Failed;\nuse Illuminate\\Support\\Facades\\Event;\nuse Illuminate\\Support\\Facades\\Session;\nuse Pterodactyl\\Events\\Auth\\DirectLogin;\nuse PHPUnit\\Framework\\Attributes\\TestWith;\nuse Pterodactyl\\Tests\\Integration\\Http\\HttpTestCase;\nuse Pterodactyl\\Events\\Auth\\ProvidedAuthenticationToken;\n\nclass LoginCheckpointControllerTest extends HttpTestCase\n{\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        Event::fake([Failed::class, DirectLogin::class, ProvidedAuthenticationToken::class]);\n    }\n\n    /**\n     * Basic test that a user can be signed in using their TOTP token and that\n     * the `totp_authenticated_at` field in the database is updated to the login\n     * verification time.\n     */\n    #[TestWith([null])]\n    #[TestWith([-31])]\n    #[TestWith([-60])]\n    public function testUserCanSignInUsingTotpToken(?int $ts): void\n    {\n        $user = User::factory()->create([\n            'use_totp' => true,\n            'totp_secret' => encrypt(str_repeat('a', 16)),\n            'totp_authenticated_at' => is_null($ts) ? null : Carbon::now()->addSeconds($ts),\n        ]);\n\n        Session::put('auth_confirmation_token', [\n            'user_id' => $user->id,\n            'token_value' => 'token',\n            'expires_at' => now()->addMinutes(5),\n        ]);\n\n        $totp = $this->app->make(Google2FA::class)->getCurrentOtp(str_repeat('a', 16));\n\n        $this->withoutExceptionHandling()->postJson(route('auth.login-checkpoint', [\n            'confirmation_token' => 'token',\n            'authentication_code' => $totp,\n        ]))\n            ->assertOk()\n            ->assertSessionMissing('auth_confirmation_token')\n            ->assertJsonPath('data.complete', true)\n            ->assertJsonPath('data.intended', '/')\n            ->assertJsonPath('data.user.uuid', $user->uuid);\n\n        $this->assertEquals(now(), $user->refresh()->totp_authenticated_at);\n\n        $this->assertAuthenticatedAs($user);\n\n        Event::assertDispatched(fn (DirectLogin $event) => $event->user->is($user) && $event->remember);\n        Event::assertDispatched(fn (ProvidedAuthenticationToken $event) => $event->user->is($user));\n    }\n\n    /**\n     * Test that a TOTP token cannot be reused by verifying that the OTP verification\n     * logic fails if the token's timestamp is before the `totp_authenticated_at`\n     * column value.\n     *\n     * @see https://github.com/pterodactyl/panel/security/advisories/GHSA-rgmp-4873-r683\n     */\n    #[TestWith([1])]\n    #[TestWith([30])]\n    #[TestWith([80])]\n    public function testTotpTokenCannotBeReused(int $seconds): void\n    {\n        $user = User::factory()->create([\n            'use_totp' => true,\n            'totp_secret' => encrypt(str_repeat('a', 16)),\n            'totp_authenticated_at' => now()->addSeconds($seconds),\n        ]);\n\n        Session::put('auth_confirmation_token', [\n            'user_id' => $user->id,\n            'token_value' => 'token',\n            'expires_at' => now()->addMinutes(5),\n        ]);\n\n        $totp = $this->app->make(Google2FA::class)->getCurrentOtp(str_repeat('a', 16));\n\n        $this->postJson(route('auth.login-checkpoint', [\n            'confirmation_token' => 'token',\n            'authentication_code' => $totp,\n        ]))\n            ->assertBadRequest()\n            ->assertJsonPath('errors.0.detail', '动态口令无效。');\n\n        $this->assertGuest();\n        $this->assertEquals(now()->addSeconds($seconds), $user->refresh()->totp_authenticated_at);\n\n        Event::assertDispatched(fn (Failed $event) => $event->guard === 'auth' && $event->user->is($user));\n    }\n\n    public function testEndpointReturnsErrorIfSessionMissing(): void\n    {\n        $this->postJson(route('auth.login-checkpoint'))\n            ->assertUnprocessable()\n            ->assertJsonPath('errors.0.meta.source_field', 'confirmation_token')\n            ->assertJsonPath('errors.1.meta.source_field', 'authentication_code')\n            ->assertJsonPath('errors.2.meta.source_field', 'recovery_token');\n\n        $this->postJson(route('auth.login-checkpoint', [\n            'confirmation_token' => 'token',\n            'authentication_code' => '123456',\n        ]))\n            ->assertBadRequest()\n            ->assertJsonPath('errors.0.detail', '提供的动态口令已过期，请刷新页面重试。');\n\n        $this->assertGuest();\n\n        Event::assertDispatched(fn (Failed $event) => $event->guard === 'auth');\n    }\n\n    public function testEndpointAppliesThrottling(): void\n    {\n        for ($i = 0; $i < 5; ++$i) {\n            $this->postJson(route('auth.login-checkpoint', ['confirmation_token' => 'token', 'authentication_code' => '123456']))\n                ->assertBadRequest();\n        }\n\n        $this->postJson(route('auth.login-checkpoint', ['confirmation_token' => 'token', 'authentication_code' => '123456']))\n            ->assertTooManyRequests();\n    }\n\n    public function testEndpointBlocksSessionDataMismatch(): void\n    {\n        $user = User::factory()->create([\n            'use_totp' => true,\n            'totp_secret' => str_repeat('a', 16),\n        ]);\n\n        Session::put('auth_confirmation_token', [\n            'user_id' => $user->id,\n            'token_value' => 'token',\n            'expires_at' => now()->addMinutes(5),\n        ]);\n\n        $this->postJson(route('auth.login-checkpoint', [\n            'confirmation_token' => 'wrong-token',\n            'authentication_code' => $this->app->make(Google2FA::class)->getCurrentOtp(str_repeat('a', 16)),\n        ]))\n            ->assertBadRequest();\n\n        $this->assertGuest();\n\n        Event::assertDispatched(Failed::class);\n    }\n\n    public function testEndpointReturnsErrorIfUserDoesNotExist(): void\n    {\n        Session::put('auth_confirmation_token', [\n            'user_id' => 0,\n            'token_value' => 'token',\n            'expires_at' => now()->addMinutes(5),\n        ]);\n\n        $this->postJson(route('auth.login-checkpoint', [\n            'confirmation_token' => 'token',\n            'authentication_code' => '123456',\n        ]))\n            ->assertBadRequest()\n            ->assertJsonPath('errors.0.detail', '提供的动态口令已过期，请刷新页面重试。');\n    }\n\n    public function testEndpointAllowsRecoveryToken(): void\n    {\n        $user = User::factory()->create();\n        $token = $user->recoveryTokens()->forceCreate(['token' => password_hash('recovery', PASSWORD_DEFAULT)]);\n\n        Session::put('auth_confirmation_token', [\n            'user_id' => $user->id,\n            'token_value' => 'token',\n            'expires_at' => now()->addMinutes(5),\n        ]);\n\n        $this->postJson(route('auth.login-checkpoint', [\n            'confirmation_token' => 'token',\n            'recovery_token' => 'invalid',\n        ]))\n            ->assertBadRequest()\n            ->assertJsonPath('errors.0.detail', '提供的恢复口令无效。');\n\n        $this->assertGuest();\n\n        $this->postJson(route('auth.login-checkpoint', [\n            'confirmation_token' => 'token',\n            'recovery_token' => 'recovery',\n        ]))\n            ->assertOk()\n            ->assertSessionMissing('auth_confirmation_token');\n\n        Event::assertDispatched(ProvidedAuthenticationToken::class);\n        Event::assertDispatched(DirectLogin::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Http/HttpTestCase.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Http;\n\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\n\nabstract class HttpTestCase extends IntegrationTestCase\n{\n}\n"
  },
  {
    "path": "tests/Integration/IntegrationTestCase.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration;\n\nuse Carbon\\CarbonImmutable;\nuse Carbon\\CarbonInterface;\nuse Pterodactyl\\Tests\\TestCase;\nuse Illuminate\\Support\\Facades\\Event;\nuse Pterodactyl\\Events\\ActivityLogged;\nuse Pterodactyl\\Tests\\Assertions\\AssertsActivityLogged;\nuse Pterodactyl\\Tests\\Traits\\Integration\\CreatesTestModels;\nuse Pterodactyl\\Transformers\\Api\\Application\\BaseTransformer;\n\nabstract class IntegrationTestCase extends TestCase\n{\n    use CreatesTestModels;\n    use AssertsActivityLogged;\n\n    protected array $connectionsToTransact = ['mysql'];\n\n    protected $defaultHeaders = [\n        'Accept' => 'application/json',\n    ];\n\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        Event::fake(ActivityLogged::class);\n    }\n\n    /**\n     * Return an ISO-8601 formatted timestamp to use in the API response.\n     */\n    protected function formatTimestamp(string $timestamp): string\n    {\n        return CarbonImmutable::createFromFormat(CarbonInterface::DEFAULT_TO_STRING_FORMAT, $timestamp)\n            ->setTimezone(BaseTransformer::RESPONSE_TIMEZONE)\n            ->toAtomString();\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Jobs/RevokeSftpAccessJobTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Jobs;\n\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Jobs\\RevokeSftpAccessJob;\nuse PHPUnit\\Framework\\Attributes\\TestWith;\nuse GuzzleHttp\\Exception\\TransferException;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Repositories\\Wings\\DaemonRevocationRepository;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass RevokeSftpAccessJobTest extends IntegrationTestCase\n{\n    #[TestWith([Server::class, 'server'])]\n    #[TestWith([Node::class, 'node'])]\n    public function testUniqueIdBasedOnModelType(string $class, string $key): void\n    {\n        $model = $class::factory()->make(['uuid' => 'uuid-1234']);\n\n        $job = new RevokeSftpAccessJob('user-1', $model);\n\n        $this->assertEquals(\n            \"revoke-sftp:user-1:{$key}:uuid-1234\",\n            $job->uniqueId()\n        );\n    }\n\n    public function testJobReleasesBackToQueueOnFailure(): void\n    {\n        $node = Node::factory()->make(['uuid' => 'uuid-1234']);\n\n        $mock = $this->mock(DaemonRevocationRepository::class, function ($mock) {\n            $mock->expects('setNode->deauthorize')->andThrows(\n                new DaemonConnectionException(new TransferException('Connection failed'))\n            );\n        });\n\n        $job = \\Mockery::mock(RevokeSftpAccessJob::class, ['user-1', $node])->makePartial();\n        $job->expects('release')->with(10);\n\n        $job->handle($mock);\n    }\n\n    public function testJobDispatchesForNode(): void\n    {\n        $node = Node::factory()->make(['uuid' => 'uuid-1234']);\n\n        $mock = $this->mock(DaemonRevocationRepository::class, function ($mock) {\n            $mock->expects('setNode')->andReturnSelf();\n            $mock->expects('deauthorize')->with('user-1', [])->andReturnUndefined();\n        });\n\n        (new RevokeSftpAccessJob('user-1', $node))->handle($mock);\n    }\n\n    public function testJobDispatchesForIndividualServer(): void\n    {\n        $node = Node::factory()->make(['uuid' => 'node-1234']);\n        $server = Server::factory()->make(['uuid' => 'server-1234'])->setRelation('node', $node);\n\n        $mock = $this->mock(DaemonRevocationRepository::class, function ($mock) {\n            $mock->expects('setNode')->with(\\Mockery::on(fn (Node $node) => $node->uuid === 'node-1234'))->andReturnSelf();\n            $mock->expects('deauthorize')->with('user-1', ['server-1234'])->andReturnUndefined();\n        });\n\n        (new RevokeSftpAccessJob('user-1', $server))->handle($mock);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Jobs/Schedule/RunTaskJobTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Jobs\\Schedule;\n\nuse Carbon\\Carbon;\nuse Carbon\\CarbonImmutable;\nuse GuzzleHttp\\Psr7\\Request;\nuse Pterodactyl\\Models\\Task;\nuse GuzzleHttp\\Psr7\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Schedule;\nuse Illuminate\\Support\\Facades\\Bus;\nuse Pterodactyl\\Jobs\\Schedule\\RunTaskJob;\nuse GuzzleHttp\\Exception\\BadResponseException;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Repositories\\Wings\\DaemonPowerRepository;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass RunTaskJobTest extends IntegrationTestCase\n{\n    /**\n     * An inactive job should not be run by the system.\n     */\n    public function testInactiveJobIsNotRun()\n    {\n        $server = $this->createServerModel();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create([\n            'server_id' => $server->id,\n            'is_processing' => true,\n            'last_run_at' => null,\n            'is_active' => false,\n        ]);\n        /** @var Task $task */\n        $task = Task::factory()->create(['schedule_id' => $schedule->id, 'is_queued' => true]);\n\n        $job = new RunTaskJob($task);\n\n        Bus::dispatchSync($job);\n\n        $task->refresh();\n        $schedule->refresh();\n\n        $this->assertFalse($task->is_queued);\n        $this->assertFalse($schedule->is_processing);\n        $this->assertFalse($schedule->is_active);\n        $this->assertTrue(CarbonImmutable::now()->isSameAs(\\DateTimeInterface::ATOM, $schedule->last_run_at));\n    }\n\n    public function testJobWithInvalidActionThrowsException()\n    {\n        $server = $this->createServerModel();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n        /** @var Task $task */\n        $task = Task::factory()->create(['schedule_id' => $schedule->id, 'action' => 'foobar']);\n\n        $job = new RunTaskJob($task);\n\n        $this->expectException(\\InvalidArgumentException::class);\n        $this->expectExceptionMessage('提供的任务操作无效: foobar');\n        Bus::dispatchSync($job);\n    }\n\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('isManualRunDataProvider')]\n    public function testJobIsExecuted(bool $isManualRun)\n    {\n        $server = $this->createServerModel();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create([\n            'server_id' => $server->id,\n            'is_active' => !$isManualRun,\n            'is_processing' => true,\n            'last_run_at' => null,\n        ]);\n        /** @var Task $task */\n        $task = Task::factory()->create([\n            'schedule_id' => $schedule->id,\n            'action' => Task::ACTION_POWER,\n            'payload' => 'start',\n            'is_queued' => true,\n            'continue_on_failure' => false,\n        ]);\n\n        $mock = \\Mockery::mock(DaemonPowerRepository::class);\n        $this->instance(DaemonPowerRepository::class, $mock);\n\n        $mock->expects('setServer')->with(\\Mockery::on(function ($value) use ($server) {\n            return $value instanceof Server && $value->id === $server->id;\n        }))->andReturnSelf();\n        $mock->expects('send')->with('start')->andReturn(new Response());\n\n        Bus::dispatchSync(new RunTaskJob($task, $isManualRun));\n\n        $task->refresh();\n        $schedule->refresh();\n\n        $this->assertFalse($task->is_queued);\n        $this->assertFalse($schedule->is_processing);\n        $this->assertTrue(CarbonImmutable::now()->isSameAs(\\DateTimeInterface::ATOM, $schedule->last_run_at));\n    }\n\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('isManualRunDataProvider')]\n    public function testExceptionDuringRunIsHandledCorrectly(bool $continueOnFailure)\n    {\n        $server = $this->createServerModel();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n        /** @var Task $task */\n        $task = Task::factory()->create([\n            'schedule_id' => $schedule->id,\n            'action' => Task::ACTION_POWER,\n            'payload' => 'start',\n            'continue_on_failure' => $continueOnFailure,\n        ]);\n\n        $mock = \\Mockery::mock(DaemonPowerRepository::class);\n        $this->instance(DaemonPowerRepository::class, $mock);\n\n        $mock->expects('setServer->send')->andThrow(\n            new DaemonConnectionException(new BadResponseException('Bad request', new Request('GET', '/test'), new Response()))\n        );\n\n        if (!$continueOnFailure) {\n            $this->expectException(DaemonConnectionException::class);\n        }\n\n        Bus::dispatchSync(new RunTaskJob($task));\n\n        if ($continueOnFailure) {\n            $task->refresh();\n            $schedule->refresh();\n\n            $this->assertFalse($task->is_queued);\n            $this->assertFalse($schedule->is_processing);\n            $this->assertTrue(CarbonImmutable::now()->isSameAs(\\DateTimeInterface::ATOM, $schedule->last_run_at));\n        }\n    }\n\n    /**\n     * Test that a schedule is not executed if the server is suspended.\n     *\n     * @see https://github.com/pterodactyl/panel/issues/4008\n     */\n    public function testTaskIsNotRunIfServerIsSuspended()\n    {\n        $server = $this->createServerModel([\n            'status' => Server::STATUS_SUSPENDED,\n        ]);\n\n        $schedule = Schedule::factory()->for($server)->create([\n            'last_run_at' => Carbon::now()->subHour(),\n        ]);\n\n        $task = Task::factory()->for($schedule)->create([\n            'action' => Task::ACTION_POWER,\n            'payload' => 'start',\n        ]);\n\n        Bus::dispatchSync(new RunTaskJob($task));\n\n        $task->refresh();\n        $schedule->refresh();\n\n        $this->assertFalse($task->is_queued);\n        $this->assertFalse($schedule->is_processing);\n        $this->assertTrue(Carbon::now()->isSameAs(\\DateTimeInterface::ATOM, $schedule->last_run_at));\n    }\n\n    public static function isManualRunDataProvider(): array\n    {\n        return [[true], [false]];\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Allocations/FindAssignableAllocationServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Allocations;\n\nuse Pterodactyl\\Models\\Allocation;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Services\\Allocations\\FindAssignableAllocationService;\nuse Pterodactyl\\Exceptions\\Service\\Allocation\\AutoAllocationNotEnabledException;\nuse Pterodactyl\\Exceptions\\Service\\Allocation\\NoAutoAllocationSpaceAvailableException;\n\nclass FindAssignableAllocationServiceTest extends IntegrationTestCase\n{\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        config()->set('pterodactyl.client_features.allocations.enabled', true);\n        config()->set('pterodactyl.client_features.allocations.range_start', 0);\n        config()->set('pterodactyl.client_features.allocations.range_end', 0);\n    }\n\n    /**\n     * Test that an unassigned allocation is preferred rather than creating an entirely new\n     * allocation for the server.\n     */\n    public function testExistingAllocationIsPreferred()\n    {\n        $server = $this->createServerModel();\n\n        $created = Allocation::factory()->create([\n            'node_id' => $server->node_id,\n            'ip' => $server->allocation->ip,\n        ]);\n\n        $response = $this->getService()->handle($server);\n\n        $this->assertSame($created->id, $response->id);\n        $this->assertSame($server->allocation->ip, $response->ip);\n        $this->assertSame($server->node_id, $response->node_id);\n        $this->assertSame($server->id, $response->server_id);\n        $this->assertNotSame($server->allocation_id, $response->id);\n    }\n\n    /**\n     * Test that a new allocation is created if there is not a free one available.\n     */\n    public function testNewAllocationIsCreatedIfOneIsNotFound()\n    {\n        $server = $this->createServerModel();\n        config()->set('pterodactyl.client_features.allocations.range_start', 5000);\n        config()->set('pterodactyl.client_features.allocations.range_end', 5005);\n\n        $response = $this->getService()->handle($server);\n        $this->assertSame($server->id, $response->server_id);\n        $this->assertSame($server->allocation->ip, $response->ip);\n        $this->assertSame($server->node_id, $response->node_id);\n        $this->assertNotSame($server->allocation_id, $response->id);\n        $this->assertTrue($response->port >= 5000 && $response->port <= 5005);\n    }\n\n    /**\n     * Test that a currently assigned port is never assigned to a server.\n     */\n    public function testOnlyPortNotInUseIsCreated()\n    {\n        $server = $this->createServerModel();\n        $server2 = $this->createServerModel(['node_id' => $server->node_id]);\n\n        config()->set('pterodactyl.client_features.allocations.range_start', 5000);\n        config()->set('pterodactyl.client_features.allocations.range_end', 5001);\n\n        Allocation::factory()->create([\n            'server_id' => $server2->id,\n            'node_id' => $server->node_id,\n            'ip' => $server->allocation->ip,\n            'port' => 5000,\n        ]);\n\n        $response = $this->getService()->handle($server);\n        $this->assertSame(5001, $response->port);\n    }\n\n    public function testExceptionIsThrownIfNoMoreAllocationsCanBeCreatedInRange()\n    {\n        $server = $this->createServerModel();\n        $server2 = $this->createServerModel(['node_id' => $server->node_id]);\n        config()->set('pterodactyl.client_features.allocations.range_start', 5000);\n        config()->set('pterodactyl.client_features.allocations.range_end', 5005);\n\n        for ($i = 5000; $i <= 5005; ++$i) {\n            Allocation::factory()->create([\n                'ip' => $server->allocation->ip,\n                'port' => $i,\n                'node_id' => $server->node_id,\n                'server_id' => $server2->id,\n            ]);\n        }\n\n        $this->expectException(NoAutoAllocationSpaceAvailableException::class);\n        $this->expectExceptionMessage('无法分配更多端口：节点上没有可用空间。');\n\n        $this->getService()->handle($server);\n    }\n\n    /**\n     * Test that we only auto-allocate from the current server's IP address space, and not a random\n     * IP address available on that node.\n     */\n    public function testExceptionIsThrownIfOnlyFreePortIsOnADifferentIp()\n    {\n        $server = $this->createServerModel();\n\n        Allocation::factory()->times(5)->create(['node_id' => $server->node_id]);\n\n        $this->expectException(NoAutoAllocationSpaceAvailableException::class);\n        $this->expectExceptionMessage('无法分配更多端口：节点上没有可用空间。');\n\n        $this->getService()->handle($server);\n    }\n\n    public function testExceptionIsThrownIfStartOrEndRangeIsNotDefined()\n    {\n        $server = $this->createServerModel();\n\n        $this->expectException(NoAutoAllocationSpaceAvailableException::class);\n        $this->expectExceptionMessage('无法分配更多端口：节点上没有可用空间。');\n\n        $this->getService()->handle($server);\n    }\n\n    public function testExceptionIsThrownIfStartOrEndRangeIsNotNumeric()\n    {\n        $server = $this->createServerModel();\n        config()->set('pterodactyl.client_features.allocations.range_start', 'hodor');\n        config()->set('pterodactyl.client_features.allocations.range_end', 10);\n\n        try {\n            $this->getService()->handle($server);\n            $this->fail('This assertion should not be reached.');\n        } catch (\\Exception $exception) {\n            $this->assertInstanceOf(\\InvalidArgumentException::class, $exception);\n            $this->assertSame('Expected an integerish value. Got: string', $exception->getMessage());\n        }\n\n        config()->set('pterodactyl.client_features.allocations.range_start', 10);\n        config()->set('pterodactyl.client_features.allocations.range_end', 'hodor');\n\n        try {\n            $this->getService()->handle($server);\n            $this->fail('This assertion should not be reached.');\n        } catch (\\Exception $exception) {\n            $this->assertInstanceOf(\\InvalidArgumentException::class, $exception);\n            $this->assertSame('Expected an integerish value. Got: string', $exception->getMessage());\n        }\n    }\n\n    public function testExceptionIsThrownIfFeatureIsNotEnabled()\n    {\n        config()->set('pterodactyl.client_features.allocations.enabled', false);\n        $server = $this->createServerModel();\n\n        $this->expectException(AutoAllocationNotEnabledException::class);\n\n        $this->getService()->handle($server);\n    }\n\n    /**\n     * Test that handleConsecutive returns the requested number of consecutive ports\n     * and assigns them all to the server.\n     */\n    public function testConsecutiveAllocationReturnsValidConsecutivePorts()\n    {\n        $server = $this->createServerModel();\n        config()->set('pterodactyl.client_features.allocations.range_start', 5000);\n        config()->set('pterodactyl.client_features.allocations.range_end', 5010);\n\n        $allocations = $this->getService()->handleConsecutive($server, 3);\n\n        $this->assertCount(3, $allocations);\n\n        $ports = array_map(fn ($a) => $a->port, $allocations);\n        sort($ports);\n\n        // Verify all ports are consecutive.\n        for ($i = 0; $i < count($ports) - 1; ++$i) {\n            $this->assertSame($ports[$i] + 1, $ports[$i + 1]);\n        }\n\n        // Verify all allocations belong to the server.\n        foreach ($allocations as $allocation) {\n            $this->assertSame($server->id, $allocation->server_id);\n            $this->assertSame($server->allocation->ip, $allocation->ip);\n        }\n    }\n\n    /**\n     * Test that handleConsecutive picks a random starting port (like single-port allocation)\n     * rather than always returning the first available consecutive sequence.\n     */\n    public function testConsecutiveAllocationIsRandomized()\n    {\n        $server = $this->createServerModel();\n        config()->set('pterodactyl.client_features.allocations.range_start', 5000);\n        config()->set('pterodactyl.client_features.allocations.range_end', 5019);\n\n        $startPorts = [];\n        // Run many times; with 19 possible start positions for count=2 across 20 ports,\n        // the probability of always getting 5000 is (1/19)^20 ≈ negligible.\n        for ($attempt = 0; $attempt < 20; ++$attempt) {\n            // Reset all allocations between runs.\n            $server->node->allocations()->whereNotIn('id', [$server->allocation_id])->delete();\n\n            $allocations = $this->getService()->handleConsecutive($server, 2);\n            $ports = array_map(fn ($a) => $a->port, $allocations);\n            sort($ports);\n            $startPorts[] = $ports[0];\n\n            // Reset server_id so ports are available again for next iteration.\n            $server->node->allocations()\n                ->whereNotIn('id', [$server->allocation_id])\n                ->update(['server_id' => null]);\n        }\n\n        // After 20 runs there must be more than one distinct starting port, proving randomness.\n        $this->assertGreaterThan(1, count(array_unique($startPorts)));\n    }\n\n    /**\n     * Test that handleConsecutive throws when there are not enough consecutive ports.\n     */\n    public function testConsecutiveAllocationThrowsWhenNoConsecutiveSequenceAvailable()\n    {\n        $server = $this->createServerModel();\n        $server2 = $this->createServerModel(['node_id' => $server->node_id]);\n        config()->set('pterodactyl.client_features.allocations.range_start', 5000);\n        config()->set('pterodactyl.client_features.allocations.range_end', 5004);\n\n        // Block every other port so no two consecutive ports are free.\n        foreach ([5001, 5003] as $port) {\n            Allocation::factory()->create([\n                'ip' => $server->allocation->ip,\n                'port' => $port,\n                'node_id' => $server->node_id,\n                'server_id' => $server2->id,\n            ]);\n        }\n\n        $this->expectException(NoAutoAllocationSpaceAvailableException::class);\n        $this->expectExceptionMessage('无法分配更多端口：节点上没有可用空间。');\n\n        $this->getService()->handleConsecutive($server, 2);\n    }\n\n    private function getService(): FindAssignableAllocationService\n    {\n        return $this->app->make(FindAssignableAllocationService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Backups/DeleteBackupServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Backups;\n\nuse GuzzleHttp\\Psr7\\Request;\nuse GuzzleHttp\\Psr7\\Response;\nuse Pterodactyl\\Models\\Backup;\nuse GuzzleHttp\\Exception\\ClientException;\nuse Pterodactyl\\Extensions\\Backups\\BackupManager;\nuse Pterodactyl\\Extensions\\Filesystem\\S3Filesystem;\nuse Pterodactyl\\Services\\Backups\\DeleteBackupService;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Repositories\\Wings\\DaemonBackupRepository;\nuse Pterodactyl\\Exceptions\\Service\\Backup\\BackupLockedException;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass DeleteBackupServiceTest extends IntegrationTestCase\n{\n    public function testLockedBackupCannotBeDeleted()\n    {\n        $server = $this->createServerModel();\n        $backup = Backup::factory()->create([\n            'server_id' => $server->id,\n            'is_locked' => true,\n        ]);\n\n        $this->expectException(BackupLockedException::class);\n\n        $this->app->make(DeleteBackupService::class)->handle($backup);\n    }\n\n    public function testFailedBackupThatIsLockedCanBeDeleted()\n    {\n        $server = $this->createServerModel();\n        $backup = Backup::factory()->create([\n            'server_id' => $server->id,\n            'is_locked' => true,\n            'is_successful' => false,\n        ]);\n\n        $mock = $this->mock(DaemonBackupRepository::class);\n        $mock->expects('setServer->delete')->with($backup)->andReturn(new Response());\n\n        $this->app->make(DeleteBackupService::class)->handle($backup);\n\n        $backup->refresh();\n\n        $this->assertNotNull($backup->deleted_at);\n    }\n\n    public function testExceptionThrownDueToMissingBackupIsIgnored()\n    {\n        $server = $this->createServerModel();\n        $backup = Backup::factory()->create(['server_id' => $server->id]);\n\n        $mock = $this->mock(DaemonBackupRepository::class);\n        $mock->expects('setServer->delete')->with($backup)->andThrow(\n            new DaemonConnectionException(\n                new ClientException('', new Request('DELETE', '/'), new Response(404))\n            )\n        );\n\n        $this->app->make(DeleteBackupService::class)->handle($backup);\n\n        $backup->refresh();\n\n        $this->assertNotNull($backup->deleted_at);\n    }\n\n    public function testExceptionIsThrownIfNot404()\n    {\n        $server = $this->createServerModel();\n        $backup = Backup::factory()->create(['server_id' => $server->id]);\n\n        $mock = $this->mock(DaemonBackupRepository::class);\n        $mock->expects('setServer->delete')->with($backup)->andThrow(\n            new DaemonConnectionException(\n                new ClientException('', new Request('DELETE', '/'), new Response(500))\n            )\n        );\n\n        $this->expectException(DaemonConnectionException::class);\n\n        $this->app->make(DeleteBackupService::class)->handle($backup);\n\n        $backup->refresh();\n\n        $this->assertNull($backup->deleted_at);\n    }\n\n    public function testS3ObjectCanBeDeleted()\n    {\n        $server = $this->createServerModel();\n        $backup = Backup::factory()->create([\n            'disk' => Backup::ADAPTER_AWS_S3,\n            'server_id' => $server->id,\n        ]);\n\n        $manager = $this->mock(BackupManager::class);\n        $adapter = $this->mock(S3Filesystem::class);\n\n        $manager->expects('adapter')->with(Backup::ADAPTER_AWS_S3)->andReturn($adapter);\n\n        $adapter->expects('getBucket')->andReturn('foobar');\n        $adapter->expects('getClient->deleteObject')->with([\n            'Bucket' => 'foobar',\n            'Key' => sprintf('%s/%s.tar.gz', $server->uuid, $backup->uuid),\n        ]);\n\n        $this->app->make(DeleteBackupService::class)->handle($backup);\n\n        $this->assertSoftDeleted($backup);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Databases/DatabaseManagementServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Databases;\n\nuse Mockery\\MockInterface;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Repositories\\Eloquent\\DatabaseRepository;\nuse Pterodactyl\\Services\\Databases\\DatabaseManagementService;\nuse Pterodactyl\\Exceptions\\Repository\\DuplicateDatabaseNameException;\nuse Pterodactyl\\Exceptions\\Service\\Database\\TooManyDatabasesException;\nuse Pterodactyl\\Exceptions\\Service\\Database\\DatabaseClientFeatureNotEnabledException;\n\nclass DatabaseManagementServiceTest extends IntegrationTestCase\n{\n    private MockInterface $repository;\n\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        config()->set('pterodactyl.client_features.databases.enabled', true);\n\n        $this->repository = $this->mock(DatabaseRepository::class);\n    }\n\n    /**\n     * Test that the name generated by the unique name function is what we expect.\n     */\n    public function testUniqueDatabaseNameIsGeneratedCorrectly()\n    {\n        $this->assertSame('s1_example', DatabaseManagementService::generateUniqueDatabaseName('example', 1));\n        $this->assertSame('s123_something_else', DatabaseManagementService::generateUniqueDatabaseName('something_else', 123));\n        $this->assertSame('s123_' . str_repeat('a', 43), DatabaseManagementService::generateUniqueDatabaseName(str_repeat('a', 100), 123));\n    }\n\n    /**\n     * Test that disabling the client database feature flag prevents the creation of databases.\n     */\n    public function testExceptionIsThrownIfClientDatabasesAreNotEnabled()\n    {\n        config()->set('pterodactyl.client_features.databases.enabled', false);\n\n        $this->expectException(DatabaseClientFeatureNotEnabledException::class);\n\n        $server = $this->createServerModel();\n        $this->getService()->create($server, []);\n    }\n\n    /**\n     * Test that a server at its database limit cannot have an additional one created if\n     * the $validateDatabaseLimit flag is not set to false.\n     */\n    public function testDatabaseCannotBeCreatedIfServerHasReachedLimit()\n    {\n        $server = $this->createServerModel(['database_limit' => 2]);\n        $host = DatabaseHost::factory()->create(['node_id' => $server->node_id]);\n\n        Database::factory()->times(2)->create(['server_id' => $server->id, 'database_host_id' => $host->id]);\n\n        $this->expectException(TooManyDatabasesException::class);\n\n        $this->getService()->create($server, []);\n    }\n\n    /**\n     * Test that a missing or invalid database name format causes an exception to be thrown.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('invalidDataDataProvider')]\n    public function testEmptyDatabaseNameOrInvalidNameTriggersAnException(array $data)\n    {\n        $server = $this->createServerModel();\n\n        $this->expectException(\\InvalidArgumentException::class);\n        $this->expectExceptionMessage('The database name passed to DatabaseManagementService::handle MUST be prefixed with \"s{server_id}_\".');\n\n        $this->getService()->create($server, $data);\n    }\n\n    /**\n     * Test that creating a server database with an identical name triggers an exception.\n     */\n    public function testCreatingDatabaseWithIdenticalNameTriggersAnException()\n    {\n        $server = $this->createServerModel();\n        $name = DatabaseManagementService::generateUniqueDatabaseName('soemthing', $server->id);\n\n        $host = DatabaseHost::factory()->create(['node_id' => $server->node_id]);\n        $host2 = DatabaseHost::factory()->create(['node_id' => $server->node_id]);\n        Database::factory()->create([\n            'database' => $name,\n            'database_host_id' => $host->id,\n            'server_id' => $server->id,\n        ]);\n\n        $this->expectException(DuplicateDatabaseNameException::class);\n        $this->expectExceptionMessage('A database with that name already exists for this server.');\n\n        // Try to create a database with the same name as a database on a different host. We expect\n        // this to fail since we don't account for the specific host when checking uniqueness.\n        $this->getService()->create($server, [\n            'database' => $name,\n            'database_host_id' => $host2->id,\n        ]);\n\n        $this->assertDatabaseMissing('databases', ['server_id' => $server->id]);\n    }\n\n    /**\n     * Test that a server database can be created successfully.\n     */\n    public function testServerDatabaseCanBeCreated()\n    {\n        $server = $this->createServerModel();\n        $name = DatabaseManagementService::generateUniqueDatabaseName('soemthing', $server->id);\n\n        $host = DatabaseHost::factory()->create(['node_id' => $server->node_id]);\n\n        $this->repository->expects('createDatabase')->with($name);\n\n        $username = null;\n        $secondUsername = null;\n        $password = null;\n\n        // The value setting inside the closures if to avoid throwing an exception during the\n        // assertions that would get caught by the functions catcher and thus lead to the exception\n        // being swallowed incorrectly.\n        $this->repository->expects('createUser')->with(\n            \\Mockery::on(function ($value) use (&$username) {\n                $username = $value;\n\n                return true;\n            }),\n            '%',\n            \\Mockery::on(function ($value) use (&$password) {\n                $password = $value;\n\n                return true;\n            }),\n            null\n        );\n\n        $this->repository->expects('assignUserToDatabase')->with($name, \\Mockery::on(function ($value) use (&$secondUsername) {\n            $secondUsername = $value;\n\n            return true;\n        }), '%');\n\n        $this->repository->expects('flush')->withNoArgs();\n\n        $response = $this->getService()->create($server, [\n            'remote' => '%',\n            'database' => $name,\n            'database_host_id' => $host->id,\n        ]);\n\n        $this->assertInstanceOf(Database::class, $response);\n        $this->assertSame($response->server_id, $server->id);\n        $this->assertMatchesRegularExpression('/^(u\\d+_)(\\w){10}$/', $username);\n        $this->assertSame($username, $secondUsername);\n        $this->assertSame(24, strlen($password));\n\n        $this->assertDatabaseHas('databases', ['server_id' => $server->id, 'id' => $response->id]);\n    }\n\n    /**\n     * Test that an exception encountered while creating the database leads to the cleanup code\n     * being called and any exceptions encountered while cleaning up go unreported.\n     */\n    public function testExceptionEncounteredWhileCreatingDatabaseAttemptsToCleanup()\n    {\n        $server = $this->createServerModel();\n        $name = DatabaseManagementService::generateUniqueDatabaseName('soemthing', $server->id);\n\n        $host = DatabaseHost::factory()->create(['node_id' => $server->node_id]);\n\n        $this->repository->expects('createDatabase')->with($name)->andThrows(new \\BadMethodCallException());\n        $this->repository->expects('dropDatabase')->with($name);\n        $this->repository->expects('dropUser')->withAnyArgs()->andThrows(new \\InvalidArgumentException());\n\n        $this->expectException(\\BadMethodCallException::class);\n\n        $this->getService()->create($server, [\n            'remote' => '%',\n            'database' => $name,\n            'database_host_id' => $host->id,\n        ]);\n\n        $this->assertDatabaseMissing('databases', ['server_id' => $server->id]);\n    }\n\n    public static function invalidDataDataProvider(): array\n    {\n        return [\n            [[]],\n            [['database' => '']],\n            [['database' => 'something']],\n            [['database' => 's_something']],\n            [['database' => 's12s_something']],\n            [['database' => 's12something']],\n        ];\n    }\n\n    private function getService(): DatabaseManagementService\n    {\n        return $this->app->make(DatabaseManagementService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Databases/DeployServerDatabaseServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Databases;\n\nuse Mockery\\MockInterface;\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\DatabaseHost;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Services\\Databases\\DatabaseManagementService;\nuse Pterodactyl\\Services\\Databases\\DeployServerDatabaseService;\nuse Pterodactyl\\Exceptions\\Service\\Database\\NoSuitableDatabaseHostException;\n\nclass DeployServerDatabaseServiceTest extends IntegrationTestCase\n{\n    private MockInterface $managementService;\n\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->managementService = \\Mockery::mock(DatabaseManagementService::class);\n        $this->swap(DatabaseManagementService::class, $this->managementService);\n    }\n\n    /**\n     * Ensure we reset the config to the expected value.\n     */\n    protected function tearDown(): void\n    {\n        config()->set('pterodactyl.client_features.databases.allow_random', true);\n\n        Database::query()->delete();\n        DatabaseHost::query()->delete();\n\n        parent::tearDown();\n    }\n\n    /**\n     * Test that an error is thrown if either the database name or the remote host are empty.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('invalidDataProvider')]\n    public function testErrorIsThrownIfDatabaseNameIsEmpty(array $data)\n    {\n        $server = $this->createServerModel();\n\n        $this->expectException(\\InvalidArgumentException::class);\n        $this->expectExceptionMessageMatches('/^Expected a non-empty value\\. Got: /');\n        $this->getService()->handle($server, $data);\n    }\n\n    /**\n     * Test that an error is thrown if there are no database hosts on the same node as the\n     * server and the allow_random config value is false.\n     */\n    public function testErrorIsThrownIfNoDatabaseHostsExistOnNode()\n    {\n        $server = $this->createServerModel();\n\n        $node = Node::factory()->create(['location_id' => $server->location->id]);\n        DatabaseHost::factory()->create(['node_id' => $node->id]);\n\n        config()->set('pterodactyl.client_features.databases.allow_random', false);\n\n        $this->expectException(NoSuitableDatabaseHostException::class);\n\n        $this->getService()->handle($server, [\n            'database' => 'something',\n            'remote' => '%',\n        ]);\n    }\n\n    /**\n     * Test that an error is thrown if no database hosts exist at all on the system.\n     */\n    public function testErrorIsThrownIfNoDatabaseHostsExistOnSystem()\n    {\n        $server = $this->createServerModel();\n\n        $this->expectException(NoSuitableDatabaseHostException::class);\n\n        $this->getService()->handle($server, [\n            'database' => 'something',\n            'remote' => '%',\n        ]);\n    }\n\n    /**\n     * Test that a database host on the same node as the server is preferred.\n     */\n    public function testDatabaseHostOnSameNodeIsPreferred()\n    {\n        $server = $this->createServerModel();\n\n        $node = Node::factory()->create(['location_id' => $server->location->id]);\n        DatabaseHost::factory()->create(['node_id' => $node->id]);\n        $host = DatabaseHost::factory()->create(['node_id' => $server->node_id]);\n\n        $this->managementService->expects('create')->with($server, [\n            'database_host_id' => $host->id,\n            'database' => \"s{$server->id}_something\",\n            'remote' => '%',\n        ])->andReturns(new Database());\n\n        $response = $this->getService()->handle($server, [\n            'database' => 'something',\n            'remote' => '%',\n        ]);\n\n        $this->assertInstanceOf(Database::class, $response);\n    }\n\n    /**\n     * Test that a database host not assigned to the same node as the server is used if\n     * there are no same-node hosts and the allow_random configuration value is set to\n     * true.\n     */\n    public function testDatabaseHostIsSelectedIfNoSuitableHostExistsOnSameNode()\n    {\n        $server = $this->createServerModel();\n\n        $node = Node::factory()->create(['location_id' => $server->location->id]);\n        $host = DatabaseHost::factory()->create(['node_id' => $node->id]);\n\n        $this->managementService->expects('create')->with($server, [\n            'database_host_id' => $host->id,\n            'database' => \"s{$server->id}_something\",\n            'remote' => '%',\n        ])->andReturns(new Database());\n\n        $response = $this->getService()->handle($server, [\n            'database' => 'something',\n            'remote' => '%',\n        ]);\n\n        $this->assertInstanceOf(Database::class, $response);\n    }\n\n    public static function invalidDataProvider(): array\n    {\n        return [\n            [['remote' => '%']],\n            [['database' => null, 'remote' => '%']],\n            [['database' => '', 'remote' => '%']],\n            [['database' => '']],\n            [['database' => '', 'remote' => '']],\n        ];\n    }\n\n    private function getService(): DeployServerDatabaseService\n    {\n        return $this->app->make(DeployServerDatabaseService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Deployment/FindViableNodesServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Deployment;\n\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\Location;\nuse Illuminate\\Support\\Collection;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Services\\Deployment\\FindViableNodesService;\nuse Pterodactyl\\Exceptions\\Service\\Deployment\\NoViableNodeException;\n\nclass FindViableNodesServiceTest extends IntegrationTestCase\n{\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        Database::query()->delete();\n        Server::query()->delete();\n        Node::query()->delete();\n    }\n\n    public function testExceptionIsThrownIfNoDiskSpaceHasBeenSet()\n    {\n        $this->expectException(\\InvalidArgumentException::class);\n        $this->expectExceptionMessage('Disk space must be an int, got NULL');\n\n        $this->getService()->handle();\n    }\n\n    public function testExceptionIsThrownIfNoMemoryHasBeenSet()\n    {\n        $this->expectException(\\InvalidArgumentException::class);\n        $this->expectExceptionMessage('Memory usage must be an int, got NULL');\n\n        $this->getService()->setDisk(10)->handle();\n    }\n\n    /**\n     * Ensure that errors are not thrown back when passing in expected values.\n     *\n     * @see https://github.com/pterodactyl/panel/issues/2529\n     */\n    public function testNoExceptionIsThrownIfStringifiedIntegersArePassedForLocations()\n    {\n        $this->getService()->setLocations([1, 2, 3]);\n        $this->getService()->setLocations(['1', '2', '3']);\n        $this->getService()->setLocations(['1', 2, 3]);\n\n        try {\n            $this->getService()->setLocations(['a']);\n            $this->fail('This expectation should not be called.');\n        } catch (\\Exception $exception) {\n            $this->assertInstanceOf(\\InvalidArgumentException::class, $exception);\n            $this->assertSame('An array of location IDs should be provided when calling setLocations.', $exception->getMessage());\n        }\n\n        try {\n            $this->getService()->setLocations(['1.2', '1', 2]);\n            $this->fail('This expectation should not be called.');\n        } catch (\\Exception $exception) {\n            $this->assertInstanceOf(\\InvalidArgumentException::class, $exception);\n            $this->assertSame('An array of location IDs should be provided when calling setLocations.', $exception->getMessage());\n        }\n    }\n\n    public function testExpectedNodeIsReturnedForLocation()\n    {\n        /** @var \\Pterodactyl\\Models\\Location[] $locations */\n        $locations = Location::factory()->times(2)->create();\n\n        /** @var \\Pterodactyl\\Models\\Node[] $nodes */\n        $nodes = [\n            // This node should never be returned once we've completed the initial test which\n            // runs without a location filter.\n            Node::factory()->create([\n                'location_id' => $locations[0]->id,\n                'memory' => 2048,\n                'disk' => 1024 * 100,\n            ]),\n            Node::factory()->create([\n                'location_id' => $locations[1]->id,\n                'memory' => 1024,\n                'disk' => 10240,\n                'disk_overallocate' => 10,\n            ]),\n            Node::factory()->create([\n                'location_id' => $locations[1]->id,\n                'memory' => 1024 * 4,\n                'memory_overallocate' => 50,\n                'disk' => 102400,\n            ]),\n        ];\n\n        // Expect that all the nodes are returned as we're under all of their limits\n        // and there is no location filter being provided.\n        $response = $this->getService()->setDisk(512)->setMemory(512)->handle();\n        $this->assertInstanceOf(Collection::class, $response);\n        $this->assertCount(3, $response);\n        $this->assertInstanceOf(Node::class, $response[0]);\n\n        // Expect that only the last node is returned because it is the only one with enough\n        // memory available to this instance.\n        $response = $this->getService()->setDisk(512)->setMemory(2049)->handle();\n        $this->assertInstanceOf(Collection::class, $response);\n        $this->assertCount(1, $response);\n        $this->assertSame($nodes[2]->id, $response[0]->id);\n\n        // Helper, I am lazy.\n        $base = function () use ($locations) {\n            return $this->getService()->setLocations([$locations[1]->id])->setDisk(512);\n        };\n\n        // Expect that we can create this server on either node since the disk and memory\n        // limits are below the allowed amount.\n        $response = $base()->setMemory(512)->handle();\n        $this->assertCount(2, $response);\n        $this->assertSame(2, $response->where('location_id', $locations[1]->id)->count());\n\n        // Expect that we can only create this server on the second node since the memory\n        // allocated is over the amount of memory available to the first node.\n        $response = $base()->setMemory(2048)->handle();\n        $this->assertCount(1, $response);\n        $this->assertSame($nodes[2]->id, $response[0]->id);\n\n        // Expect that we can only create this server on the second node since the disk\n        // allocated is over the limit assigned to the first node (even with the overallocate).\n        $response = $base()->setDisk(20480)->setMemory(256)->handle();\n        $this->assertCount(1, $response);\n        $this->assertSame($nodes[2]->id, $response[0]->id);\n\n        // Expect that we could create the server on either node since the disk allocated is\n        // right at the limit for Node 1 when the overallocate value is included in the calc.\n        $response = $base()->setDisk(11264)->setMemory(256)->handle();\n        $this->assertCount(2, $response);\n\n        // Create two servers on the first node so that the disk space used is equal to the\n        // base amount available to the node (without overallocation included).\n        $servers = Collection::make([\n            $this->createServerModel(['node_id' => $nodes[1]->id, 'disk' => 5120]),\n            $this->createServerModel(['node_id' => $nodes[1]->id, 'disk' => 5120]),\n        ]);\n\n        // Expect that we cannot create a server with a 1GB disk on the first node since there\n        // is not enough space (even with the overallocate) available to the node.\n        $response = $base()->setDisk(1024)->setMemory(256)->handle();\n        $this->assertCount(1, $response);\n        $this->assertSame($nodes[2]->id, $response[0]->id);\n\n        // Cleanup servers since we need to test some other stuff with memory here.\n        $servers->each->delete();\n\n        // Expect that no viable node can be found when the memory limit for the given instance\n        // is greater than either node can support, even with the overallocation limits taken\n        // into account.\n        $this->expectException(NoViableNodeException::class);\n        $base()->setMemory(10000)->handle();\n\n        // Create four servers so that the memory used for the second node is equal to the total\n        // limit for that node (pre-overallocate calculation).\n        Collection::make([\n            $this->createServerModel(['node_id' => $nodes[2]->id, 'memory' => 1024]),\n            $this->createServerModel(['node_id' => $nodes[2]->id, 'memory' => 1024]),\n            $this->createServerModel(['node_id' => $nodes[2]->id, 'memory' => 1024]),\n            $this->createServerModel(['node_id' => $nodes[2]->id, 'memory' => 1024]),\n        ]);\n\n        // Expect that either node can support this server when we account for the overallocate\n        // value of the second node.\n        $response = $base()->setMemory(500)->handle();\n        $this->assertCount(2, $response);\n        $this->assertSame(2, $response->where('location_id', $locations[1]->id)->count());\n\n        // Expect that only the first node can support this server when we go over the remaining\n        // memory for the second nodes overallocate calculation.\n        $response = $base()->setMemory(640)->handle();\n        $this->assertCount(1, $response);\n        $this->assertSame($nodes[1]->id, $response[0]->id);\n    }\n\n    private function getService(): FindViableNodesService\n    {\n        return $this->app->make(FindViableNodesService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Schedules/ProcessScheduleServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Schedules;\n\nuse Exception;\nuse Carbon\\CarbonImmutable;\nuse Pterodactyl\\Models\\Task;\nuse Pterodactyl\\Models\\Schedule;\nuse Illuminate\\Support\\Facades\\Bus;\nuse Illuminate\\Contracts\\Bus\\Dispatcher;\nuse Pterodactyl\\Jobs\\Schedule\\RunTaskJob;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Services\\Schedules\\ProcessScheduleService;\n\nclass ProcessScheduleServiceTest extends IntegrationTestCase\n{\n    /**\n     * Test that a schedule with no tasks registered returns an error.\n     */\n    public function testScheduleWithNoTasksReturnsException()\n    {\n        $server = $this->createServerModel();\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n\n        $this->expectException(DisplayException::class);\n        $this->expectExceptionMessage('Cannot process schedule for task execution: no tasks are registered.');\n\n        $this->getService()->handle($schedule);\n    }\n\n    /**\n     * Test that an error during the schedule update is not persisted to the database.\n     */\n    public function testErrorDuringScheduleDataUpdateDoesNotPersistChanges()\n    {\n        $server = $this->createServerModel();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create([\n            'server_id' => $server->id,\n            'cron_minute' => 'hodor', // this will break the getNextRunDate() function.\n        ]);\n\n        /** @var Task $task */\n        $task = Task::factory()->create(['schedule_id' => $schedule->id, 'sequence_id' => 1]);\n\n        $this->expectException(\\InvalidArgumentException::class);\n\n        $this->getService()->handle($schedule);\n\n        $this->assertDatabaseMissing('schedules', ['id' => $schedule->id, 'is_processing' => true]);\n        $this->assertDatabaseMissing('tasks', ['id' => $task->id, 'is_queued' => true]);\n    }\n\n    /**\n     * Test that a job is dispatched as expected using the initial delay.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('dispatchNowDataProvider')]\n    public function testJobCanBeDispatchedWithExpectedInitialDelay(bool $now)\n    {\n        Bus::fake();\n\n        $server = $this->createServerModel();\n\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n\n        /** @var Task $task */\n        $task = Task::factory()->create(['schedule_id' => $schedule->id, 'time_offset' => 10, 'sequence_id' => 1]);\n\n        $this->getService()->handle($schedule, $now);\n\n        Bus::assertDispatched(RunTaskJob::class, function ($job) use ($now, $task) {\n            $this->assertInstanceOf(RunTaskJob::class, $job);\n            $this->assertSame($task->id, $job->task->id);\n            // Jobs using dispatchNow should not have a delay associated with them.\n            $this->assertSame($now ? null : 10, $job->delay);\n\n            return true;\n        });\n\n        $this->assertDatabaseHas('schedules', ['id' => $schedule->id, 'is_processing' => true]);\n        $this->assertDatabaseHas('tasks', ['id' => $task->id, 'is_queued' => true]);\n    }\n\n    /**\n     * Test that even if a schedule's task sequence gets messed up the first task based on\n     * the ascending order of tasks is used.\n     *\n     * @see https://github.com/pterodactyl/panel/issues/2534\n     */\n    public function testFirstSequenceTaskIsFound()\n    {\n        Bus::fake();\n\n        $server = $this->createServerModel();\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id]);\n\n        /** @var Task $task */\n        $task2 = Task::factory()->create(['schedule_id' => $schedule->id, 'sequence_id' => 4]);\n        $task = Task::factory()->create(['schedule_id' => $schedule->id, 'sequence_id' => 2]);\n        $task3 = Task::factory()->create(['schedule_id' => $schedule->id, 'sequence_id' => 3]);\n\n        $this->getService()->handle($schedule);\n\n        Bus::assertDispatched(RunTaskJob::class, function (RunTaskJob $job) use ($task) {\n            return $task->id === $job->task->id;\n        });\n\n        $this->assertDatabaseHas('schedules', ['id' => $schedule->id, 'is_processing' => true]);\n        $this->assertDatabaseHas('tasks', ['id' => $task->id, 'is_queued' => true]);\n        $this->assertDatabaseHas('tasks', ['id' => $task2->id, 'is_queued' => false]);\n        $this->assertDatabaseHas('tasks', ['id' => $task3->id, 'is_queued' => false]);\n    }\n\n    /**\n     * Tests that a task's processing state is reset correctly if using \"dispatchNow\" and there is\n     * an exception encountered while running it.\n     *\n     * @see https://github.com/pterodactyl/panel/issues/2550\n     */\n    public function testTaskDispatchedNowIsResetProperlyIfErrorIsEncountered()\n    {\n        $this->swap(Dispatcher::class, $dispatcher = \\Mockery::mock(Dispatcher::class));\n\n        $server = $this->createServerModel();\n        /** @var Schedule $schedule */\n        $schedule = Schedule::factory()->create(['server_id' => $server->id, 'last_run_at' => null]);\n        /** @var Task $task */\n        $task = Task::factory()->create(['schedule_id' => $schedule->id, 'sequence_id' => 1]);\n\n        $dispatcher->expects('dispatchNow')->andThrows(new \\Exception('Test thrown exception'));\n\n        $this->expectException(\\Exception::class);\n        $this->expectExceptionMessage('Test thrown exception');\n\n        $this->getService()->handle($schedule, true);\n\n        $this->assertDatabaseHas('schedules', [\n            'id' => $schedule->id,\n            'is_processing' => false,\n            'last_run_at' => CarbonImmutable::now()->toAtomString(),\n        ]);\n\n        $this->assertDatabaseHas('tasks', ['id' => $task->id, 'is_queued' => false]);\n    }\n\n    public static function dispatchNowDataProvider(): array\n    {\n        return [[true], [false]];\n    }\n\n    private function getService(): ProcessScheduleService\n    {\n        return $this->app->make(ProcessScheduleService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Servers/BuildModificationServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Servers;\n\nuse Mockery\\MockInterface;\nuse GuzzleHttp\\Psr7\\Request;\nuse GuzzleHttp\\Psr7\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Allocation;\nuse GuzzleHttp\\Exception\\RequestException;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Services\\Servers\\BuildModificationService;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass BuildModificationServiceTest extends IntegrationTestCase\n{\n    private MockInterface $daemonServerRepository;\n\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->daemonServerRepository = $this->mock(DaemonServerRepository::class);\n    }\n\n    /**\n     * Test that allocations can be added and removed from a server. Only the allocations on the\n     * current node and belonging to this server should be modified.\n     */\n    public function testAllocationsCanBeModifiedForTheServer()\n    {\n        $server = $this->createServerModel();\n        $server2 = $this->createServerModel();\n\n        /** @var \\Pterodactyl\\Models\\Allocation[] $allocations */\n        $allocations = Allocation::factory()->times(4)->create(['node_id' => $server->node_id, 'notes' => 'Random notes']);\n\n        $initialAllocationId = $server->allocation_id;\n        $allocations[0]->update(['server_id' => $server->id, 'notes' => 'Test notes']);\n\n        // Some additional test allocations for the other server, not the server we are attempting\n        // to modify.\n        $allocations[2]->update(['server_id' => $server2->id]);\n        $allocations[3]->update(['server_id' => $server2->id]);\n\n        $this->daemonServerRepository->expects('setServer->sync')->andReturnUndefined();\n\n        $response = $this->getService()->handle($server, [\n            // Attempt to add one new allocation, and an allocation assigned to another server. The\n            // other server allocation should be ignored, and only the allocation for this server should\n            // be used.\n            'add_allocations' => [$allocations[2]->id, $allocations[1]->id],\n            // Remove the default server allocation, ensuring that the new allocation passed through\n            // in the data becomes the default allocation.\n            'remove_allocations' => [$server->allocation_id, $allocations[0]->id, $allocations[3]->id],\n        ]);\n\n        $this->assertInstanceOf(Server::class, $response);\n\n        // Only one allocation should exist for this server now.\n        $this->assertCount(1, $response->allocations);\n        $this->assertSame($allocations[1]->id, $response->allocation_id);\n        $this->assertNull($response->allocation->notes);\n\n        // These two allocations should not have been touched.\n        $this->assertDatabaseHas('allocations', ['id' => $allocations[2]->id, 'server_id' => $server2->id]);\n        $this->assertDatabaseHas('allocations', ['id' => $allocations[3]->id, 'server_id' => $server2->id]);\n\n        // Both of these allocations should have been removed from the server, and have had their\n        // notes properly reset.\n        $this->assertDatabaseHas('allocations', ['id' => $initialAllocationId, 'server_id' => null, 'notes' => null]);\n        $this->assertDatabaseHas('allocations', ['id' => $allocations[0]->id, 'server_id' => null, 'notes' => null]);\n    }\n\n    /**\n     * Test that an exception is thrown if removing the default allocation without also assigning\n     * new allocations to the server.\n     */\n    public function testExceptionIsThrownIfRemovingTheDefaultAllocation()\n    {\n        $server = $this->createServerModel();\n        /** @var \\Pterodactyl\\Models\\Allocation[] $allocations */\n        $allocations = Allocation::factory()->times(4)->create(['node_id' => $server->node_id]);\n\n        $allocations[0]->update(['server_id' => $server->id]);\n\n        $this->expectException(DisplayException::class);\n        $this->expectExceptionMessage('You are attempting to delete the default allocation for this server but there is no fallback allocation to use.');\n\n        $this->getService()->handle($server, [\n            'add_allocations' => [],\n            'remove_allocations' => [$server->allocation_id, $allocations[0]->id],\n        ]);\n    }\n\n    /**\n     * Test that the build data for the server is properly passed along to the Wings instance so that\n     * the server data is updated in realtime. This test also ensures that only certain fields get updated\n     * for the server, and not just any arbitrary field.\n     */\n    public function testServerBuildDataIsProperlyUpdatedOnWings()\n    {\n        $server = $this->createServerModel();\n\n        $this->daemonServerRepository->expects('setServer')->with(\\Mockery::on(function (Server $s) use ($server) {\n            return $s->id === $server->id;\n        }))->andReturnSelf();\n\n        $this->daemonServerRepository->expects('sync')->withNoArgs()->andReturnUndefined();\n\n        $response = $this->getService()->handle($server, [\n            'oom_disabled' => false,\n            'memory' => 256,\n            'swap' => 128,\n            'io' => 600,\n            'cpu' => 150,\n            'threads' => '1,2',\n            'disk' => 1024,\n            'backup_limit' => null,\n            'database_limit' => 10,\n            'allocation_limit' => 20,\n        ]);\n\n        $this->assertFalse($response->oom_disabled);\n        $this->assertSame(256, $response->memory);\n        $this->assertSame(128, $response->swap);\n        $this->assertSame(600, $response->io);\n        $this->assertSame(150, $response->cpu);\n        $this->assertSame('1,2', $response->threads);\n        $this->assertSame(1024, $response->disk);\n        $this->assertSame(0, $response->backup_limit);\n        $this->assertSame(10, $response->database_limit);\n        $this->assertSame(20, $response->allocation_limit);\n    }\n\n    /**\n     * Test that an exception when connecting to the Wings instance is properly ignored\n     * when making updates. This allows for a server to be modified even when the Wings\n     * node is offline.\n     */\n    public function testConnectionExceptionIsIgnoredWhenUpdatingServerSettings()\n    {\n        $server = $this->createServerModel();\n\n        $this->daemonServerRepository->expects('setServer->sync')->andThrows(\n            new DaemonConnectionException(\n                new RequestException('Bad request', new Request('GET', '/test'), new Response())\n            )\n        );\n\n        $response = $this->getService()->handle($server, ['memory' => 256, 'disk' => 10240]);\n\n        $this->assertInstanceOf(Server::class, $response);\n        $this->assertSame(256, $response->memory);\n        $this->assertSame(10240, $response->disk);\n\n        $this->assertDatabaseHas('servers', ['id' => $response->id, 'memory' => 256, 'disk' => 10240]);\n    }\n\n    /**\n     * Test that no exception is thrown if we are only removing an allocation.\n     */\n    public function testNoExceptionIsThrownIfOnlyRemovingAllocation()\n    {\n        $server = $this->createServerModel();\n        /** @var Allocation $allocation */\n        $allocation = Allocation::factory()->create(['node_id' => $server->node_id, 'server_id' => $server->id]);\n\n        $this->daemonServerRepository->expects('setServer->sync')->andReturnUndefined();\n\n        $this->getService()->handle($server, [\n            'remove_allocations' => [$allocation->id],\n        ]);\n\n        $this->assertDatabaseHas('allocations', ['id' => $allocation->id, 'server_id' => null]);\n    }\n\n    /**\n     * Test that allocations in both the add and remove arrays are only added, and not removed.\n     * This scenario wouldn't really happen in the UI, but it is possible to perform via the API,\n     * so we want to make sure that the logic being used doesn't break if the allocation exists\n     * in both arrays.\n     *\n     * We'll default to adding the allocation in this case.\n     */\n    public function testAllocationInBothAddAndRemoveIsAdded()\n    {\n        $server = $this->createServerModel();\n        /** @var Allocation $allocation */\n        $allocation = Allocation::factory()->create(['node_id' => $server->node_id]);\n\n        $this->daemonServerRepository->expects('setServer->sync')->andReturnUndefined();\n\n        $this->getService()->handle($server, [\n            'add_allocations' => [$allocation->id],\n            'remove_allocations' => [$allocation->id],\n        ]);\n\n        $this->assertDatabaseHas('allocations', ['id' => $allocation->id, 'server_id' => $server->id]);\n    }\n\n    /**\n     * Test that using the same allocation ID multiple times in the array does not cause an error.\n     */\n    public function testUsingSameAllocationIdMultipleTimesDoesNotError()\n    {\n        $server = $this->createServerModel();\n        /** @var Allocation $allocation */\n        $allocation = Allocation::factory()->create(['node_id' => $server->node_id, 'server_id' => $server->id]);\n        /** @var Allocation $allocation2 */\n        $allocation2 = Allocation::factory()->create(['node_id' => $server->node_id]);\n\n        $this->daemonServerRepository->expects('setServer->sync')->andReturnUndefined();\n\n        $this->getService()->handle($server, [\n            'add_allocations' => [$allocation2->id, $allocation2->id],\n            'remove_allocations' => [$allocation->id, $allocation->id],\n        ]);\n\n        $this->assertDatabaseHas('allocations', ['id' => $allocation->id, 'server_id' => null]);\n        $this->assertDatabaseHas('allocations', ['id' => $allocation2->id, 'server_id' => $server->id]);\n    }\n\n    /**\n     * Test that any changes we made to the server or allocations are rolled back if there is an\n     * exception while performing any action. This is different from the connection exception\n     * test which should properly ignore connection issues. We want any other type of exception\n     * to properly be thrown back to the caller.\n     */\n    public function testThatUpdatesAreRolledBackIfExceptionIsEncountered()\n    {\n        $server = $this->createServerModel();\n        /** @var Allocation $allocation */\n        $allocation = Allocation::factory()->create(['node_id' => $server->node_id]);\n\n        $this->daemonServerRepository->expects('setServer->sync')->andThrows(new DisplayException('Test'));\n\n        $this->expectException(DisplayException::class);\n\n        $this->getService()->handle($server, ['add_allocations' => [$allocation->id]]);\n\n        $this->assertDatabaseHas('allocations', ['id' => $allocation->id, 'server_id' => null]);\n    }\n\n    private function getService(): BuildModificationService\n    {\n        return $this->app->make(BuildModificationService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Servers/ServerCreationServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Servers;\n\nuse Mockery\\MockInterface;\nuse Pterodactyl\\Models\\Egg;\nuse GuzzleHttp\\Psr7\\Request;\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\User;\nuse GuzzleHttp\\Psr7\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Location;\nuse Pterodactyl\\Models\\Allocation;\nuse Illuminate\\Foundation\\Testing\\WithFaker;\nuse GuzzleHttp\\Exception\\BadResponseException;\nuse Illuminate\\Validation\\ValidationException;\nuse Pterodactyl\\Models\\Objects\\DeploymentObject;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Services\\Servers\\ServerCreationService;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass ServerCreationServiceTest extends IntegrationTestCase\n{\n    use WithFaker;\n\n    protected MockInterface $daemonServerRepository;\n\n    protected Egg $bungeecord;\n\n    /**\n     * Stub the calls to Wings so that we don't actually hit those API endpoints.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        /* @noinspection PhpFieldAssignmentTypeMismatchInspection */\n        $this->bungeecord = Egg::query()\n            ->where('author', 'support@pterodactyl.io')\n            ->where('name', 'Bungeecord')\n            ->firstOrFail();\n\n        $this->daemonServerRepository = \\Mockery::mock(DaemonServerRepository::class);\n        $this->swap(DaemonServerRepository::class, $this->daemonServerRepository);\n    }\n\n    /**\n     * Test that a server can be created when a deployment object is provided to the service.\n     *\n     * This doesn't really do anything super complicated, we'll rely on other more specific\n     * tests to cover that the logic being used does indeed find suitable nodes and ports. For\n     * this test we just care that it is recognized and passed off to those functions.\n     */\n    public function testServerIsCreatedWithDeploymentObject()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n\n        /** @var Location $location */\n        $location = Location::factory()->create();\n\n        /** @var Node $node */\n        $node = Node::factory()->create([\n            'location_id' => $location->id,\n        ]);\n\n        /** @var \\Pterodactyl\\Models\\Allocation[]|\\Illuminate\\Database\\Eloquent\\Collection $allocations */\n        $allocations = Allocation::factory()->times(5)->create([\n            'node_id' => $node->id,\n        ]);\n\n        $deployment = (new DeploymentObject())->setDedicated(true)->setLocations([$node->location_id])->setPorts([\n            $allocations[0]->port,\n        ]);\n\n        $egg = $this->cloneEggAndVariables($this->bungeecord);\n        // We want to make sure that the validator service runs as an admin, and not as a regular\n        // user when saving variables.\n        $egg->variables()->first()->update([\n            'user_editable' => false,\n        ]);\n\n        $data = [\n            'name' => $this->faker->name,\n            'description' => $this->faker->sentence,\n            'owner_id' => $user->id,\n            'memory' => 256,\n            'swap' => 128,\n            'disk' => 100,\n            'io' => 500,\n            'cpu' => 0,\n            'startup' => 'java server2.jar',\n            'image' => 'java:8',\n            'egg_id' => $egg->id,\n            'allocation_additional' => [\n                $allocations[4]->id,\n            ],\n            'environment' => [\n                'BUNGEE_VERSION' => '123',\n                'SERVER_JARFILE' => 'server2.jar',\n            ],\n            'start_on_completion' => true,\n        ];\n\n        $this->daemonServerRepository->expects('setServer->create')->with(true)->andReturnUndefined();\n\n        try {\n            $this->getService()->handle(array_merge($data, [\n                'environment' => [\n                    'BUNGEE_VERSION' => '',\n                    'SERVER_JARFILE' => 'server2.jar',\n                ],\n            ]), $deployment);\n\n            $this->fail('This execution pathway should not be reached.');\n        } catch (ValidationException $exception) {\n            $this->assertCount(1, $exception->errors());\n            $this->assertArrayHasKey('environment.BUNGEE_VERSION', $exception->errors());\n            $this->assertSame('Bungeecord 版本 变量 不能为空。', $exception->errors()['environment.BUNGEE_VERSION'][0]);\n        }\n\n        $response = $this->getService()->handle($data, $deployment);\n\n        $this->assertInstanceOf(Server::class, $response);\n        $this->assertNotNull($response->uuid);\n        $this->assertSame($response->uuidShort, substr($response->uuid, 0, 8));\n        $this->assertSame($egg->id, $response->egg_id);\n        $this->assertCount(2, $response->variables);\n        $this->assertSame('123', $response->variables[0]->server_value);\n        $this->assertSame('server2.jar', $response->variables[1]->server_value);\n\n        foreach ($data as $key => $value) {\n            if (in_array($key, ['allocation_additional', 'environment', 'start_on_completion'])) {\n                continue;\n            }\n\n            $this->assertSame($value, $response->{$key}, \"Failed asserting equality of '$key' in server response. Got: [{$response->{$key}}] Expected: [$value]\");\n        }\n\n        $this->assertCount(2, $response->allocations);\n        $this->assertSame($response->allocation_id, $response->allocations[0]->id);\n        $this->assertSame($allocations[0]->id, $response->allocations[0]->id);\n        $this->assertSame($allocations[4]->id, $response->allocations[1]->id);\n\n        $this->assertFalse($response->isSuspended());\n        $this->assertTrue($response->oom_disabled);\n        $this->assertSame(0, $response->database_limit);\n        $this->assertSame(0, $response->allocation_limit);\n        $this->assertSame(0, $response->backup_limit);\n    }\n\n    /**\n     * Test that a server is deleted from the Panel if Wings returns an error during the creation\n     * process.\n     */\n    public function testErrorEncounteredByWingsCausesServerToBeDeleted()\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n\n        /** @var Location $location */\n        $location = Location::factory()->create();\n\n        /** @var Node $node */\n        $node = Node::factory()->create([\n            'location_id' => $location->id,\n        ]);\n\n        /** @var Allocation $allocation */\n        $allocation = Allocation::factory()->create([\n            'node_id' => $node->id,\n        ]);\n\n        $data = [\n            'name' => $this->faker->name,\n            'description' => $this->faker->sentence,\n            'owner_id' => $user->id,\n            'allocation_id' => $allocation->id,\n            'node_id' => $allocation->node_id,\n            'memory' => 256,\n            'swap' => 128,\n            'disk' => 100,\n            'io' => 500,\n            'cpu' => 0,\n            'startup' => 'java server2.jar',\n            'image' => 'java:8',\n            'egg_id' => $this->bungeecord->id,\n            'environment' => [\n                'BUNGEE_VERSION' => '123',\n                'SERVER_JARFILE' => 'server2.jar',\n            ],\n        ];\n\n        $this->daemonServerRepository->expects('setServer->create')->andThrows(\n            new DaemonConnectionException(\n                new BadResponseException('Bad request', new Request('POST', '/create'), new Response(500))\n            )\n        );\n\n        $this->daemonServerRepository->expects('setServer->delete')->andReturnUndefined();\n\n        $this->expectException(DaemonConnectionException::class);\n\n        $this->getService()->handle($data);\n\n        $this->assertDatabaseMissing('servers', ['owner_id' => $user->id]);\n    }\n\n    private function getService(): ServerCreationService\n    {\n        return $this->app->make(ServerCreationService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Servers/ServerDeletionServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Servers;\n\nuse Mockery\\MockInterface;\nuse GuzzleHttp\\Psr7\\Request;\nuse GuzzleHttp\\Psr7\\Response;\nuse Pterodactyl\\Models\\Database;\nuse Pterodactyl\\Models\\DatabaseHost;\nuse GuzzleHttp\\Exception\\BadResponseException;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Services\\Servers\\ServerDeletionService;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\nuse Pterodactyl\\Services\\Databases\\DatabaseManagementService;\nuse Pterodactyl\\Exceptions\\Http\\Connection\\DaemonConnectionException;\n\nclass ServerDeletionServiceTest extends IntegrationTestCase\n{\n    private MockInterface $daemonServerRepository;\n\n    private MockInterface $databaseManagementService;\n\n    private static ?string $defaultLogger;\n\n    /**\n     * Stub out services that we don't want to test in here.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        self::$defaultLogger = config('logging.default');\n        // There will be some log calls during this test, don't actually write to the disk.\n        config()->set('logging.default', 'null');\n\n        $this->daemonServerRepository = \\Mockery::mock(DaemonServerRepository::class);\n        $this->databaseManagementService = \\Mockery::mock(DatabaseManagementService::class);\n\n        $this->app->instance(DaemonServerRepository::class, $this->daemonServerRepository);\n        $this->app->instance(DatabaseManagementService::class, $this->databaseManagementService);\n    }\n\n    /**\n     * Reset the log driver.\n     */\n    protected function tearDown(): void\n    {\n        config()->set('logging.default', self::$defaultLogger);\n        self::$defaultLogger = null;\n\n        parent::tearDown();\n    }\n\n    /**\n     * Test that a server is not deleted if the force option is not set and an error\n     * is returned by wings.\n     */\n    public function testRegularDeleteFailsIfWingsReturnsError()\n    {\n        $server = $this->createServerModel();\n\n        $this->expectException(DaemonConnectionException::class);\n\n        $this->daemonServerRepository->expects('setServer->delete')->withNoArgs()->andThrows(\n            new DaemonConnectionException(new BadResponseException('Bad request', new Request('GET', '/test'), new Response()))\n        );\n\n        $this->getService()->handle($server);\n\n        $this->assertDatabaseHas('servers', ['id' => $server->id]);\n    }\n\n    /**\n     * Test that a 404 from Wings while deleting a server does not cause the deletion to fail.\n     */\n    public function testRegularDeleteIgnores404FromWings()\n    {\n        $server = $this->createServerModel();\n\n        $this->daemonServerRepository->expects('setServer->delete')->withNoArgs()->andThrows(\n            new DaemonConnectionException(new BadResponseException('Bad request', new Request('GET', '/test'), new Response(404)))\n        );\n\n        $this->getService()->handle($server);\n\n        $this->assertDatabaseMissing('servers', ['id' => $server->id]);\n    }\n\n    /**\n     * Test that an error from Wings does not cause the deletion to fail if the server is being\n     * force deleted.\n     */\n    public function testForceDeleteIgnoresExceptionFromWings()\n    {\n        $server = $this->createServerModel();\n\n        $this->daemonServerRepository->expects('setServer->delete')->withNoArgs()->andThrows(\n            new DaemonConnectionException(new BadResponseException('Bad request', new Request('GET', '/test'), new Response(500)))\n        );\n\n        $this->getService()->withForce()->handle($server);\n\n        $this->assertDatabaseMissing('servers', ['id' => $server->id]);\n    }\n\n    /**\n     * Test that a non-force-delete call does not delete the server if one of the databases\n     * cannot be deleted from the host.\n     */\n    public function testExceptionWhileDeletingStopsProcess()\n    {\n        $server = $this->createServerModel();\n        $host = DatabaseHost::factory()->create();\n\n        /** @var Database $db */\n        $db = Database::factory()->create(['database_host_id' => $host->id, 'server_id' => $server->id]);\n\n        $server->refresh();\n\n        $this->daemonServerRepository->expects('setServer->delete')->withNoArgs()->andReturnUndefined();\n        $this->databaseManagementService->expects('delete')->with(\\Mockery::on(function ($value) use ($db) {\n            return $value instanceof Database && $value->id === $db->id;\n        }))->andThrows(new \\Exception());\n\n        $this->expectException(\\Exception::class);\n        $this->getService()->handle($server);\n\n        $this->assertDatabaseHas('servers', ['id' => $server->id]);\n        $this->assertDatabaseHas('databases', ['id' => $db->id]);\n    }\n\n    /**\n     * Test that a server is deleted even if the server databases cannot be deleted from the host.\n     */\n    public function testExceptionWhileDeletingDatabasesDoesNotAbortIfForceDeleted()\n    {\n        $server = $this->createServerModel();\n        $host = DatabaseHost::factory()->create();\n\n        /** @var Database $db */\n        $db = Database::factory()->create(['database_host_id' => $host->id, 'server_id' => $server->id]);\n\n        $server->refresh();\n\n        $this->daemonServerRepository->expects('setServer->delete')->withNoArgs()->andReturnUndefined();\n        $this->databaseManagementService->expects('delete')->with(\\Mockery::on(function ($value) use ($db) {\n            return $value instanceof Database && $value->id === $db->id;\n        }))->andThrows(new \\Exception());\n\n        $this->getService()->withForce(true)->handle($server);\n\n        $this->assertDatabaseMissing('servers', ['id' => $server->id]);\n        $this->assertDatabaseMissing('databases', ['id' => $db->id]);\n    }\n\n    private function getService(): ServerDeletionService\n    {\n        return $this->app->make(ServerDeletionService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Servers/StartupModificationServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Servers;\n\nuse Exception;\nuse Pterodactyl\\Models\\Nest;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\ServerVariable;\nuse Illuminate\\Validation\\ValidationException;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Illuminate\\Database\\Eloquent\\ModelNotFoundException;\nuse Pterodactyl\\Services\\Servers\\StartupModificationService;\n\nclass StartupModificationServiceTest extends IntegrationTestCase\n{\n    /**\n     * Test that a non-admin request to modify the server startup parameters does\n     * not perform any egg or nest updates. This also attempts to pass through an\n     * egg_id variable which should have no impact if the request is coming from\n     * a non-admin entity.\n     */\n    public function testNonAdminCanModifyServerVariables()\n    {\n        $server = $this->createServerModel();\n\n        try {\n            $this->app->make(StartupModificationService::class)->handle($server, [\n                'egg_id' => $server->egg_id + 1,\n                'environment' => [\n                    'BUNGEE_VERSION' => '$$',\n                    'SERVER_JARFILE' => 'server.jar',\n                ],\n            ]);\n\n            $this->fail('This assertion should not be called.');\n        } catch (\\Exception $exception) {\n            $this->assertInstanceOf(ValidationException::class, $exception);\n\n            /** @var ValidationException $exception */\n            $errors = $exception->validator->errors()->toArray();\n\n            $this->assertCount(1, $errors);\n            $this->assertArrayHasKey('environment.BUNGEE_VERSION', $errors);\n            $this->assertCount(1, $errors['environment.BUNGEE_VERSION']);\n            $this->assertSame('Bungeecord 版本 变量 只能由字母和数字组成。', $errors['environment.BUNGEE_VERSION'][0]);\n        }\n\n        ServerVariable::query()->where('variable_id', $server->variables[1]->id)->delete();\n\n        $result = $this->getService()\n            ->handle($server, [\n                'egg_id' => $server->egg_id + 1,\n                'startup' => 'random gibberish',\n                'environment' => [\n                    'BUNGEE_VERSION' => '1234',\n                    'SERVER_JARFILE' => 'test.jar',\n                ],\n            ]);\n\n        $this->assertInstanceOf(Server::class, $result);\n        $this->assertCount(2, $result->variables);\n        $this->assertSame($server->startup, $result->startup);\n        $this->assertSame('1234', $result->variables[0]->server_value);\n        $this->assertSame('test.jar', $result->variables[1]->server_value);\n    }\n\n    /**\n     * Test that modifying an egg as an admin properly updates the data for the server.\n     */\n    public function testServerIsProperlyModifiedAsAdminUser()\n    {\n        /** @var \\Pterodactyl\\Models\\Egg $nextEgg */\n        $nextEgg = Nest::query()->findOrFail(2)->eggs()->firstOrFail();\n\n        $server = $this->createServerModel(['egg_id' => 1]);\n\n        $this->assertNotSame($nextEgg->id, $server->egg_id);\n        $this->assertNotSame($nextEgg->nest_id, $server->nest_id);\n\n        $response = $this->getService()\n            ->setUserLevel(User::USER_LEVEL_ADMIN)\n            ->handle($server, [\n                'egg_id' => $nextEgg->id,\n                'startup' => 'sample startup',\n                'skip_scripts' => true,\n                'docker_image' => 'docker/hodor',\n            ]);\n\n        $this->assertInstanceOf(Server::class, $response);\n        $this->assertSame($nextEgg->id, $response->egg_id);\n        $this->assertSame($nextEgg->nest_id, $response->nest_id);\n        $this->assertSame('sample startup', $response->startup);\n        $this->assertSame('docker/hodor', $response->image);\n        $this->assertTrue($response->skip_scripts);\n        // Make sure we don't revert back to a lurking bug that causes servers to get marked\n        // as not installed when you modify the startup...\n        $this->assertTrue($response->isInstalled());\n    }\n\n    /**\n     * Test that hidden variables can be updated by an admin but are not affected by a\n     * regular user who attempts to pass them through.\n     */\n    public function testEnvironmentVariablesCanBeUpdatedByAdmin()\n    {\n        $server = $this->createServerModel();\n        $server->loadMissing(['egg', 'variables']);\n\n        $clone = $this->cloneEggAndVariables($server->egg);\n        // This makes the BUNGEE_VERSION variable not user editable.\n        $clone->variables()->first()->update([\n            'user_editable' => false,\n        ]);\n\n        $server->fill(['egg_id' => $clone->id])->saveOrFail();\n        $server->refresh();\n\n        ServerVariable::query()->updateOrCreate([\n            'server_id' => $server->id,\n            'variable_id' => $server->variables[0]->id,\n        ], ['variable_value' => 'EXIST']);\n\n        $response = $this->getService()->handle($server, [\n            'environment' => [\n                'BUNGEE_VERSION' => '1234',\n                'SERVER_JARFILE' => 'test.jar',\n            ],\n        ]);\n\n        $this->assertCount(2, $response->variables);\n        $this->assertSame('EXIST', $response->variables[0]->server_value);\n        $this->assertSame('test.jar', $response->variables[1]->server_value);\n\n        $response = $this->getService()\n            ->setUserLevel(User::USER_LEVEL_ADMIN)\n            ->handle($server, [\n                'environment' => [\n                    'BUNGEE_VERSION' => '1234',\n                    'SERVER_JARFILE' => 'test.jar',\n                ],\n            ]);\n\n        $this->assertCount(2, $response->variables);\n        $this->assertSame('1234', $response->variables[0]->server_value);\n        $this->assertSame('test.jar', $response->variables[1]->server_value);\n    }\n\n    /**\n     * Test that passing an invalid egg ID into the function throws an exception\n     * rather than silently failing or skipping.\n     */\n    public function testInvalidEggIdTriggersException()\n    {\n        $server = $this->createServerModel();\n\n        $this->expectException(ModelNotFoundException::class);\n\n        $this->getService()\n            ->setUserLevel(User::USER_LEVEL_ADMIN)\n            ->handle($server, ['egg_id' => 123456789]);\n    }\n\n    private function getService(): StartupModificationService\n    {\n        return $this->app->make(StartupModificationService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Servers/SuspensionServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Servers;\n\nuse Mockery\\MockInterface;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Services\\Servers\\SuspensionService;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Repositories\\Wings\\DaemonServerRepository;\n\nclass SuspensionServiceTest extends IntegrationTestCase\n{\n    private MockInterface $repository;\n\n    /**\n     * Setup test instance.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->repository = \\Mockery::mock(DaemonServerRepository::class);\n        $this->app->instance(DaemonServerRepository::class, $this->repository);\n    }\n\n    public function testServerIsSuspendedAndUnsuspended()\n    {\n        $server = $this->createServerModel();\n\n        $this->repository->expects('setServer->sync')->twice()->andReturnSelf();\n\n        $this->getService()->toggle($server);\n\n        $this->assertTrue($server->refresh()->isSuspended());\n\n        $this->getService()->toggle($server, SuspensionService::ACTION_UNSUSPEND);\n\n        $this->assertFalse($server->refresh()->isSuspended());\n    }\n\n    public function testNoActionIsTakenIfSuspensionStatusIsUnchanged()\n    {\n        $server = $this->createServerModel();\n\n        $this->getService()->toggle($server, SuspensionService::ACTION_UNSUSPEND);\n\n        $server->refresh();\n        $this->assertFalse($server->isSuspended());\n\n        $server->update(['status' => Server::STATUS_SUSPENDED]);\n        $this->getService()->toggle($server);\n\n        $server->refresh();\n        $this->assertTrue($server->isSuspended());\n    }\n\n    public function testExceptionIsThrownIfInvalidActionsArePassed()\n    {\n        $server = $this->createServerModel();\n\n        $this->expectException(\\InvalidArgumentException::class);\n        $this->expectExceptionMessage('Expected one of: \"suspend\", \"unsuspend\". Got: \"foo\"');\n\n        $this->getService()->toggle($server, 'foo');\n    }\n\n    private function getService(): SuspensionService\n    {\n        return $this->app->make(SuspensionService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Servers/VariableValidatorServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Servers;\n\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Support\\Collection;\nuse Illuminate\\Validation\\ValidationException;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\nuse Pterodactyl\\Services\\Servers\\VariableValidatorService;\n\nclass VariableValidatorServiceTest extends IntegrationTestCase\n{\n    protected Egg $egg;\n\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        /* @noinspection PhpFieldAssignmentTypeMismatchInspection */\n        $this->egg = Egg::query()\n            ->where('author', 'support@pterodactyl.io')\n            ->where('name', 'Bungeecord')\n            ->firstOrFail();\n    }\n\n    /**\n     * Test that environment variables for a server are validated as expected.\n     */\n    public function testEnvironmentVariablesCanBeValidated()\n    {\n        $egg = $this->cloneEggAndVariables($this->egg);\n\n        try {\n            $this->getService()->handle($egg->id, [\n                'BUNGEE_VERSION' => '1.2.3',\n            ]);\n\n            $this->fail('This statement should not be reached.');\n        } catch (ValidationException $exception) {\n            $errors = $exception->errors();\n\n            $this->assertCount(2, $errors);\n            $this->assertArrayHasKey('environment.BUNGEE_VERSION', $errors);\n            $this->assertArrayHasKey('environment.SERVER_JARFILE', $errors);\n            $this->assertSame('Bungeecord 版本 变量 只能由字母和数字组成。', $errors['environment.BUNGEE_VERSION'][0]);\n            $this->assertSame('Bungeecord Jar 文件 变量 不能为空。', $errors['environment.SERVER_JARFILE'][0]);\n        }\n\n        $response = $this->getService()->handle($egg->id, [\n            'BUNGEE_VERSION' => '1234',\n            'SERVER_JARFILE' => 'server.jar',\n        ]);\n\n        $this->assertInstanceOf(Collection::class, $response);\n        $this->assertCount(2, $response);\n        $this->assertSame('BUNGEE_VERSION', $response->get(0)->key);\n        $this->assertSame('1234', $response->get(0)->value);\n        $this->assertSame('SERVER_JARFILE', $response->get(1)->key);\n        $this->assertSame('server.jar', $response->get(1)->value);\n    }\n\n    /**\n     * Test that variables that are user_editable=false do not get validated (or returned) by\n     * the handler.\n     */\n    public function testNormalUserCannotValidateNonUserEditableVariables()\n    {\n        $egg = $this->cloneEggAndVariables($this->egg);\n        $egg->variables()->first()->update([\n            'user_editable' => false,\n        ]);\n\n        $response = $this->getService()->handle($egg->id, [\n            // This is an invalid value, but it shouldn't cause any issues since it should be skipped.\n            'BUNGEE_VERSION' => '1.2.3',\n            'SERVER_JARFILE' => 'server.jar',\n        ]);\n\n        $this->assertInstanceOf(Collection::class, $response);\n        $this->assertCount(1, $response);\n        $this->assertSame('SERVER_JARFILE', $response->get(0)->key);\n        $this->assertSame('server.jar', $response->get(0)->value);\n    }\n\n    public function testEnvironmentVariablesCanBeUpdatedAsAdmin()\n    {\n        $egg = $this->cloneEggAndVariables($this->egg);\n        $egg->variables()->first()->update([\n            'user_editable' => false,\n        ]);\n\n        try {\n            $this->getService()->setUserLevel(User::USER_LEVEL_ADMIN)->handle($egg->id, [\n                'BUNGEE_VERSION' => '1.2.3',\n                'SERVER_JARFILE' => 'server.jar',\n            ]);\n\n            $this->fail('This statement should not be reached.');\n        } catch (ValidationException $exception) {\n            $this->assertCount(1, $exception->errors());\n            $this->assertArrayHasKey('environment.BUNGEE_VERSION', $exception->errors());\n        }\n\n        $response = $this->getService()->setUserLevel(User::USER_LEVEL_ADMIN)->handle($egg->id, [\n            'BUNGEE_VERSION' => '123',\n            'SERVER_JARFILE' => 'server.jar',\n        ]);\n\n        $this->assertInstanceOf(Collection::class, $response);\n        $this->assertCount(2, $response);\n        $this->assertSame('BUNGEE_VERSION', $response->get(0)->key);\n        $this->assertSame('123', $response->get(0)->value);\n        $this->assertSame('SERVER_JARFILE', $response->get(1)->key);\n        $this->assertSame('server.jar', $response->get(1)->value);\n    }\n\n    public function testNullableEnvironmentVariablesCanBeUsedCorrectly()\n    {\n        $egg = $this->cloneEggAndVariables($this->egg);\n        $egg->variables()->where('env_variable', '!=', 'BUNGEE_VERSION')->delete();\n\n        $egg->variables()->update(['rules' => 'nullable|string']);\n\n        $response = $this->getService()->handle($egg->id, []);\n        $this->assertCount(1, $response);\n        $this->assertNull($response->get(0)->value);\n\n        $response = $this->getService()->handle($egg->id, ['BUNGEE_VERSION' => null]);\n        $this->assertCount(1, $response);\n        $this->assertNull($response->get(0)->value);\n\n        $response = $this->getService()->handle($egg->id, ['BUNGEE_VERSION' => '']);\n        $this->assertCount(1, $response);\n        $this->assertSame('', $response->get(0)->value);\n    }\n\n    private function getService(): VariableValidatorService\n    {\n        return $this->app->make(VariableValidatorService::class);\n    }\n}\n"
  },
  {
    "path": "tests/Integration/Services/Users/UserDeletionServiceTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration\\Services\\Users;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Subuser;\nuse Illuminate\\Support\\Facades\\Bus;\nuse Pterodactyl\\Jobs\\RevokeSftpAccessJob;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Pterodactyl\\Services\\Users\\UserDeletionService;\nuse Pterodactyl\\Tests\\Integration\\IntegrationTestCase;\n\nclass UserDeletionServiceTest extends IntegrationTestCase\n{\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        Bus::fake([RevokeSftpAccessJob::class]);\n    }\n\n    public function testExceptionReturnedIfUserAssignedToServers(): void\n    {\n        $server = $this->createServerModel();\n\n        $this->expectException(DisplayException::class);\n        $this->expectExceptionMessage(__('admin/user.exceptions.user_has_servers'));\n\n        $this->app->make(UserDeletionService::class)->handle($server->user);\n\n        $this->assertModelExists($server->user);\n\n        Bus::assertNotDispatched(RevokeSftpAccessJob::class);\n    }\n\n    public function testUserIsDeleted(): void\n    {\n        $user = User::factory()->create();\n\n        $this->app->make(UserDeletionService::class)->handle($user);\n\n        $this->assertModelMissing($user);\n\n        Bus::assertNotDispatched(RevokeSftpAccessJob::class);\n    }\n\n    public function testUserIsDeletedAndAccessRevoked(): void\n    {\n        $user = User::factory()->create();\n\n        $server1 = $this->createServerModel();\n        $server2 = $this->createServerModel(['node_id' => $server1->node_id]);\n\n        Subuser::factory()->for($server1)->for($user)->create();\n        Subuser::factory()->for($server2)->for($user)->create();\n\n        $this->app->make(UserDeletionService::class)->handle($user);\n\n        $this->assertModelMissing($user);\n\n        Bus::assertDispatchedTimes(RevokeSftpAccessJob::class);\n        Bus::assertDispatched(fn (RevokeSftpAccessJob $job) => $job->user === $user->uuid && $job->target->is($server1->node));\n    }\n}\n"
  },
  {
    "path": "tests/Integration/TestResponse.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Integration;\n\nuse Illuminate\\Http\\Response;\nuse Illuminate\\Testing\\Assert as PHPUnit;\nuse Pterodactyl\\Exceptions\\DisplayException;\nuse Illuminate\\Validation\\ValidationException;\nuse Illuminate\\Testing\\TestResponse as IlluminateTestResponse;\n\nclass TestResponse extends IlluminateTestResponse\n{\n    /**\n     * Overrides the default assert status logic to dump out the error to the\n     * test output if it is caused by a 500 level error, and we were not specifically\n     * look for that status response.\n     */\n    public function assertStatus($status): TestResponse\n    {\n        $actual = $this->getStatusCode();\n\n        // Dump the response to the screen before making the assertion which is going\n        // to fail so that debugging isn't such a nightmare.\n        if ($actual !== $status && $status !== 500) {\n            $this->dump();\n            if (!is_null($this->exception) && !$this->exception instanceof DisplayException && !$this->exception instanceof ValidationException) {\n                dump([\n                    'exception_class' => get_class($this->exception),\n                    'message' => $this->exception->getMessage(),\n                    'trace' => $this->exception->getTrace(),\n                ]);\n            }\n        }\n\n        PHPUnit::assertSame($actual, $status, \"Expected status code {$status} but received {$actual}.\");\n\n        return $this;\n    }\n\n    public function assertForbidden(): self\n    {\n        return self::assertStatus(Response::HTTP_FORBIDDEN);\n    }\n}\n"
  },
  {
    "path": "tests/TestCase.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests;\n\nuse Carbon\\Carbon;\nuse Carbon\\CarbonImmutable;\nuse Illuminate\\Foundation\\Testing\\TestCase as BaseTestCase;\n\nabstract class TestCase extends BaseTestCase\n{\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $now = Carbon::now()->startOfSecond();\n\n        Carbon::setTestNow($now);\n        CarbonImmutable::setTestNow($now);\n\n        // Why, you ask? If we don't force this to false it is possible for certain exceptions\n        // to show their error message properly in the integration test output, but not actually\n        // be setup correctly to display their message in production.\n        //\n        // If we expect a message in a test, and it isn't showing up (rather, showing the generic\n        // \"an error occurred\" message), we can probably assume that the exception isn't one that\n        // is recognized as being user viewable.\n        config()->set('app.debug', false);\n\n        $this->setKnownUuidFactory();\n    }\n\n    /**\n     * Tear down tests.\n     */\n    protected function tearDown(): void\n    {\n        parent::tearDown();\n\n        Carbon::setTestNow();\n        CarbonImmutable::setTestNow();\n    }\n\n    /**\n     * Handles the known UUID handling in certain unit tests. Use the \"KnownUuid\" trait\n     * in order to enable this ability.\n     */\n    public function setKnownUuidFactory()\n    {\n        // do nothing\n    }\n}\n"
  },
  {
    "path": "tests/Traits/Http/IntegrationJsonRequestAssertions.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Traits\\Http;\n\nuse Illuminate\\Http\\Response;\nuse Illuminate\\Testing\\TestResponse;\n\ntrait IntegrationJsonRequestAssertions\n{\n    /**\n     * Make assertions about a 404 response on the API.\n     */\n    public function assertNotFoundJson(TestResponse $response): void\n    {\n        $response->assertStatus(Response::HTTP_NOT_FOUND);\n        $response->assertJsonStructure(['errors' => [['code', 'status', 'detail']]]);\n        $response->assertJsonCount(1, 'errors');\n        $response->assertJson([\n            'errors' => [\n                [\n                    'code' => 'NotFoundHttpException',\n                    'status' => '404',\n                    'detail' => '无法在服务器上找到请求的资源。',\n                ],\n            ],\n        ], true);\n    }\n\n    /**\n     * Make assertions about a 403 error returned by the API.\n     */\n    public function assertAccessDeniedJson(TestResponse $response): void\n    {\n        $response->assertStatus(Response::HTTP_FORBIDDEN);\n        $response->assertJsonStructure(['errors' => [['code', 'status', 'detail']]]);\n        $response->assertJsonCount(1, 'errors');\n        $response->assertJson([\n            'errors' => [\n                [\n                    'code' => 'AccessDeniedHttpException',\n                    'status' => '403',\n                    'detail' => 'This action is unauthorized.',\n                ],\n            ],\n        ], true);\n    }\n}\n"
  },
  {
    "path": "tests/Traits/Http/MocksMiddlewareClosure.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Traits\\Http;\n\nuse Closure;\nuse Illuminate\\Http\\Request;\n\ntrait MocksMiddlewareClosure\n{\n    /**\n     * Provide a closure to be used when validating that the response from the middleware\n     * is the same request object we passed into it.\n     */\n    protected function getClosureAssertions(): \\Closure\n    {\n        if (is_null($this->request)) {\n            throw new \\BadFunctionCallException('不支持在不定义请求对象的情况下调用 getClosureAssertions。');\n        }\n\n        return function ($response) {\n            $this->assertInstanceOf(Request::class, $response);\n            $this->assertSame($this->request, $response);\n        };\n    }\n}\n"
  },
  {
    "path": "tests/Traits/Http/RequestMockHelpers.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Traits\\Http;\n\nuse Mockery as m;\nuse Mockery\\Mock;\nuse Illuminate\\Http\\Request;\nuse Pterodactyl\\Models\\User;\nuse Symfony\\Component\\HttpFoundation\\ParameterBag;\n\ntrait RequestMockHelpers\n{\n    private string $requestMockClass = Request::class;\n\n    protected Request|Mock $request;\n\n    /**\n     * Set the class to mock for requests.\n     */\n    public function setRequestMockClass(string $class): void\n    {\n        $this->requestMockClass = $class;\n\n        $this->buildRequestMock();\n    }\n\n    /**\n     * Configure the user model that the request mock should return with.\n     */\n    public function setRequestUserModel(?User $user = null): void\n    {\n        $this->request->shouldReceive('user')->andReturn($user);\n    }\n\n    /**\n     * Generates a new request user model and also returns the generated model.\n     */\n    public function generateRequestUserModel(array $args = []): User\n    {\n        /** @var User $user */\n        $user = User::factory()->make($args);\n        $this->setRequestUserModel($user);\n\n        return $user;\n    }\n\n    /**\n     * Set a request attribute on the mock object.\n     */\n    public function setRequestAttribute(string $attribute, mixed $value): void\n    {\n        $this->request->attributes->set($attribute, $value);\n    }\n\n    /**\n     * Set the request route name.\n     */\n    public function setRequestRouteName(string $name): void\n    {\n        $this->request->shouldReceive('route->getName')->andReturn($name);\n    }\n\n    /**\n     * Set the active request object to be an instance of a mocked request.\n     */\n    protected function buildRequestMock(): void\n    {\n        $this->request = m::mock($this->requestMockClass);\n        if (!$this->request instanceof Request) {\n            throw new \\InvalidArgumentException('Request mock class must be an instance of ' . Request::class . ' when mocked.');\n        }\n\n        $this->request->attributes = new ParameterBag();\n    }\n\n    /**\n     * Sets the mocked request user. If a user model is not provided, a factory model\n     * will be created and returned.\n     *\n     * @deprecated\n     */\n    protected function setRequestUser(?User $user = null): User\n    {\n        $user = $user instanceof User ? $user : User::factory()->make();\n        $this->request->shouldReceive('user')->withNoArgs()->andReturn($user);\n\n        return $user;\n    }\n}\n"
  },
  {
    "path": "tests/Traits/Integration/CreatesTestModels.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Traits\\Integration;\n\nuse Ramsey\\Uuid\\Uuid;\nuse Pterodactyl\\Models\\Egg;\nuse Pterodactyl\\Models\\Node;\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Models\\Server;\nuse Pterodactyl\\Models\\Subuser;\nuse Pterodactyl\\Models\\Location;\nuse Pterodactyl\\Models\\Allocation;\n\ntrait CreatesTestModels\n{\n    /**\n     * Creates a server model in the databases for the purpose of testing. If an attribute\n     * is passed in that normally requires this function to create a model no model will be\n     * created and that attribute's value will be used.\n     *\n     * The returned server model will have all the relationships loaded onto it.\n     */\n    public function createServerModel(array $attributes = []): Server\n    {\n        if (isset($attributes['user_id'])) {\n            $attributes['owner_id'] = $attributes['user_id'];\n        }\n\n        if (!isset($attributes['owner_id'])) {\n            /** @var User $user */\n            $user = User::factory()->create();\n            $attributes['owner_id'] = $user->id;\n        }\n\n        if (!isset($attributes['node_id'])) {\n            if (!isset($attributes['location_id'])) {\n                /** @var Location $location */\n                $location = Location::factory()->create();\n                $attributes['location_id'] = $location->id;\n            }\n\n            /** @var Node $node */\n            $node = Node::factory()->create(['location_id' => $attributes['location_id']]);\n            $attributes['node_id'] = $node->id;\n        }\n\n        if (!isset($attributes['allocation_id'])) {\n            /** @var Allocation $allocation */\n            $allocation = Allocation::factory()->create(['node_id' => $attributes['node_id']]);\n            $attributes['allocation_id'] = $allocation->id;\n        }\n\n        if (empty($attributes['egg_id'])) {\n            $egg = !empty($attributes['nest_id'])\n                ? Egg::query()->where('nest_id', $attributes['nest_id'])->firstOrFail()\n                : $this->getBungeecordEgg();\n\n            $attributes['egg_id'] = $egg->id;\n            $attributes['nest_id'] = $egg->nest_id;\n        }\n\n        if (empty($attributes['nest_id'])) {\n            $attributes['nest_id'] = Egg::query()->findOrFail($attributes['egg_id'])->nest_id;\n        }\n\n        unset($attributes['user_id'], $attributes['location_id']);\n\n        /** @var Server $server */\n        $server = Server::factory()->create($attributes);\n\n        Allocation::query()->where('id', $server->allocation_id)->update(['server_id' => $server->id]);\n\n        return $server->fresh([\n            'location', 'user', 'node', 'allocation', 'nest', 'egg',\n        ]);\n    }\n\n    /**\n     * Generates a user and a server for that user. If an array of permissions is passed it\n     * is assumed that the user is actually a subuser of the server.\n     *\n     * @param string[] $permissions\n     *\n     * @return array{\\Pterodactyl\\Models\\User, \\Pterodactyl\\Models\\Server}\n     */\n    public function generateTestAccount(array $permissions = []): array\n    {\n        /** @var User $user */\n        $user = User::factory()->create();\n\n        if (empty($permissions)) {\n            return [$user, $this->createServerModel(['user_id' => $user->id])];\n        }\n\n        $server = $this->createServerModel();\n\n        Subuser::query()->create([\n            'user_id' => $user->id,\n            'server_id' => $server->id,\n            'permissions' => $permissions,\n        ]);\n\n        return [$user, $server];\n    }\n\n    /**\n     * Clones a given egg allowing us to make modifications that don't affect other\n     * tests that rely on the egg existing in the correct state.\n     */\n    protected function cloneEggAndVariables(Egg $egg): Egg\n    {\n        $model = $egg->replicate(['id', 'uuid']);\n        $model->uuid = Uuid::uuid4()->toString();\n        $model->push();\n\n        /** @var Egg $model */\n        $model = $model->fresh();\n\n        foreach ($egg->variables as $variable) {\n            $variable->replicate(['id', 'egg_id'])->forceFill(['egg_id' => $model->id])->push();\n        }\n\n        return $model->fresh();\n    }\n\n    /**\n     * Almost every test just assumes it is using BungeeCord — this is the critical\n     * egg model for all tests unless specified otherwise.\n     */\n    private function getBungeecordEgg(): Egg\n    {\n        /** @var Egg $egg */\n        $egg = Egg::query()->where('author', 'support@pterodactyl.io')->where('name', 'Bungeecord')->firstOrFail();\n\n        return $egg;\n    }\n}\n"
  },
  {
    "path": "tests/Traits/MocksPdoConnection.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Traits;\n\nuse PDO;\nuse Mockery;\nuse Illuminate\\Database\\Eloquent\\Model;\nuse Illuminate\\Database\\MySqlConnection;\nuse Illuminate\\Database\\ConnectionResolver;\nuse Illuminate\\Database\\ConnectionResolverInterface;\n\ntrait MocksPdoConnection\n{\n    private static ?ConnectionResolverInterface $initialResolver;\n\n    /**\n     * Generates a mock PDO connection and injects it into the models so that any actual\n     * DB call can be properly intercepted.\n     */\n    protected function mockPdoConnection(): Mockery\\MockInterface\n    {\n        self::$initialResolver = Model::getConnectionResolver();\n\n        Model::unsetConnectionResolver();\n\n        $connection = new MySqlConnection($mock = \\Mockery::mock(\\PDO::class), 'testing_mock');\n        $resolver = new ConnectionResolver(['mocked' => $connection]);\n        $resolver->setDefaultConnection('mocked');\n\n        Model::setConnectionResolver($resolver);\n\n        return $mock;\n    }\n\n    /**\n     * Resets the mock state.\n     */\n    protected function tearDownPdoMock(): void\n    {\n        if (!self::$initialResolver) {\n            return;\n        }\n\n        Model::setConnectionResolver(self::$initialResolver);\n\n        self::$initialResolver = null;\n    }\n}\n"
  },
  {
    "path": "tests/Traits/MocksRequestException.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Traits;\n\nuse Mockery\\Mock;\nuse Mockery\\MockInterface;\nuse GuzzleHttp\\Exception\\RequestException;\n\ntrait MocksRequestException\n{\n    private RequestException|Mock $exception;\n\n    private mixed $exceptionResponse;\n\n    /**\n     * Configure the exception mock to work with the Panel's default exception\n     * handler actions.\n     */\n    protected function configureExceptionMock(string $abstract = RequestException::class, $response = null): void\n    {\n        $this->getExceptionMock($abstract)->shouldReceive('getResponse')->andReturn(value($response));\n    }\n\n    /**\n     * Return a mocked instance of the request exception.\n     */\n    protected function getExceptionMock(string $abstract = RequestException::class): MockInterface\n    {\n        return $this->exception ?? $this->exception = \\Mockery::mock($abstract);\n    }\n}\n"
  },
  {
    "path": "tests/Traits/MocksUuids.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Traits;\n\nuse Mockery as m;\nuse Ramsey\\Uuid\\Uuid;\nuse Ramsey\\Uuid\\UuidFactory;\n\ntrait MocksUuids\n{\n    /**\n     * The known UUID string.\n     */\n    protected string $knownUuid = 'ffb5c3a6-ab17-43ab-97f0-8ff37ccd7f5f';\n\n    /**\n     * Setup a factory mock to produce the same UUID whenever called.\n     */\n    public function setKnownUuidFactory(): void\n    {\n        $uuid = Uuid::fromString($this->getKnownUuid());\n        $factoryMock = m::mock(UuidFactory::class . '[uuid4]', [\n            'uuid4' => $uuid,\n        ]);\n\n        Uuid::setFactory($factoryMock);\n    }\n\n    /**\n     * Returns the known UUID for tests to use.\n     */\n    public function getKnownUuid(): string\n    {\n        return $this->knownUuid;\n    }\n}\n"
  },
  {
    "path": "tests/Unit/Helpers/EnvironmentWriterTraitTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Helpers;\n\nuse Pterodactyl\\Tests\\TestCase;\nuse Pterodactyl\\Traits\\Commands\\EnvironmentWriterTrait;\n\nclass EnvironmentWriterTraitTest extends TestCase\n{\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('variableDataProvider')]\n    public function testVariableIsEscapedProperly($input, $expected)\n    {\n        $output = (new FooClass())->escapeEnvironmentValue($input);\n\n        $this->assertSame($expected, $output);\n    }\n\n    public static function variableDataProvider(): array\n    {\n        return [\n            ['foo', 'foo'],\n            ['abc123', 'abc123'],\n            ['val\"ue', '\"val\\\"ue\"'],\n            ['my test value', '\"my test value\"'],\n            ['mysql_p@assword', '\"mysql_p@assword\"'],\n            ['mysql_p#assword', '\"mysql_p#assword\"'],\n            ['mysql p@$$word', '\"mysql p@$$word\"'],\n            ['mysql p%word', '\"mysql p%word\"'],\n            ['mysql p#word', '\"mysql p#word\"'],\n            ['abc_@#test', '\"abc_@#test\"'],\n            ['test 123 $$$', '\"test 123 $$$\"'],\n            ['#password%', '\"#password%\"'],\n            ['$pass ', '\"$pass \"'],\n        ];\n    }\n}\n\nclass FooClass\n{\n    use EnvironmentWriterTrait;\n}\n"
  },
  {
    "path": "tests/Unit/Helpers/IsDigitTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Helpers;\n\nuse Pterodactyl\\Tests\\TestCase;\n\nclass IsDigitTest extends TestCase\n{\n    /**\n     * Test the is_digit helper.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('helperDataProvider')]\n    public function testHelper($value, $response)\n    {\n        $this->assertSame($response, is_digit($value));\n    }\n\n    /**\n     * Provide data to test against the helper function.\n     */\n    public static function helperDataProvider(): array\n    {\n        return [\n            [true, false],\n            [false, false],\n            [12.3, false],\n            ['12.3', false],\n            ['string', false],\n            [-1, false],\n            ['-1', false],\n            [1, true],\n            [0, true],\n            [12345, true],\n            ['12345', true],\n            ['true', false],\n            ['false', false],\n            ['123_test', false],\n            ['123.test', false],\n            ['123test', false],\n            ['test123', false],\n            ['0x00000003', false],\n            [00000011, true],\n            ['00000011', true],\n            ['AD9C', false],\n        ];\n    }\n}\n"
  },
  {
    "path": "tests/Unit/Http/Middleware/AdminAuthenticateTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Http\\Middleware;\n\nuse Pterodactyl\\Models\\User;\nuse Pterodactyl\\Http\\Middleware\\AdminAuthenticate;\nuse Symfony\\Component\\HttpKernel\\Exception\\AccessDeniedHttpException;\n\nclass AdminAuthenticateTest extends MiddlewareTestCase\n{\n    /**\n     * Test that an admin is authenticated.\n     */\n    public function testAdminsAreAuthenticated()\n    {\n        $user = User::factory()->make(['root_admin' => 1]);\n\n        $this->request->shouldReceive('user')->withNoArgs()->twice()->andReturn($user);\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Test that a missing user in the request triggers an error.\n     */\n    public function testExceptionIsThrownIfUserDoesNotExist()\n    {\n        $this->expectException(AccessDeniedHttpException::class);\n\n        $this->request->shouldReceive('user')->withNoArgs()->once()->andReturnNull();\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Test that an exception is thrown if the user is not an admin.\n     */\n    public function testExceptionIsThrownIfUserIsNotAnAdmin()\n    {\n        $this->expectException(AccessDeniedHttpException::class);\n\n        $user = User::factory()->make(['root_admin' => 0]);\n\n        $this->request->shouldReceive('user')->withNoArgs()->twice()->andReturn($user);\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Return an instance of the middleware using mocked dependencies.\n     */\n    private function getMiddleware(): AdminAuthenticate\n    {\n        return new AdminAuthenticate();\n    }\n}\n"
  },
  {
    "path": "tests/Unit/Http/Middleware/Api/Application/AuthenticateUserTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Http\\Middleware\\Api\\Application;\n\nuse Pterodactyl\\Tests\\Unit\\Http\\Middleware\\MiddlewareTestCase;\nuse Symfony\\Component\\HttpKernel\\Exception\\AccessDeniedHttpException;\nuse Pterodactyl\\Http\\Middleware\\Api\\Application\\AuthenticateApplicationUser;\n\nclass AuthenticateUserTest extends MiddlewareTestCase\n{\n    /**\n     * Test that no user defined results in an access denied exception.\n     */\n    public function testNoUserDefined()\n    {\n        $this->expectException(AccessDeniedHttpException::class);\n\n        $this->setRequestUserModel(null);\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Test that a non-admin user results in an exception.\n     */\n    public function testNonAdminUser()\n    {\n        $this->expectException(AccessDeniedHttpException::class);\n\n        $this->generateRequestUserModel(['root_admin' => false]);\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Test that an admin user continues though the middleware.\n     */\n    public function testAdminUser()\n    {\n        $this->generateRequestUserModel(['root_admin' => true]);\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Return an instance of the middleware for testing.\n     */\n    private function getMiddleware(): AuthenticateApplicationUser\n    {\n        return new AuthenticateApplicationUser();\n    }\n}\n"
  },
  {
    "path": "tests/Unit/Http/Middleware/Api/Daemon/DaemonAuthenticateTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Http\\Middleware\\Api\\Daemon;\n\nuse Mockery as m;\nuse Mockery\\MockInterface;\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Contracts\\Encryption\\Encrypter;\nuse Pterodactyl\\Repositories\\Eloquent\\NodeRepository;\nuse Symfony\\Component\\HttpKernel\\Exception\\HttpException;\nuse Pterodactyl\\Exceptions\\Repository\\RecordNotFoundException;\nuse Pterodactyl\\Http\\Middleware\\Api\\Daemon\\DaemonAuthenticate;\nuse Pterodactyl\\Tests\\Unit\\Http\\Middleware\\MiddlewareTestCase;\nuse Symfony\\Component\\HttpKernel\\Exception\\BadRequestHttpException;\nuse Symfony\\Component\\HttpKernel\\Exception\\AccessDeniedHttpException;\n\nclass DaemonAuthenticateTest extends MiddlewareTestCase\n{\n    private MockInterface $encrypter;\n\n    private MockInterface $repository;\n\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->encrypter = m::mock(Encrypter::class);\n        $this->repository = m::mock(NodeRepository::class);\n    }\n\n    /**\n     * Test that if we are accessing the daemon.configuration route this middleware is not\n     * applied in order to allow an unauthenticated request to use a token to grab data.\n     */\n    public function testResponseShouldContinueIfRouteIsExempted()\n    {\n        $this->request->expects('route->getName')->withNoArgs()->andReturn('daemon.configuration');\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Test that not passing in the bearer token will result in a HTTP/401 error with the\n     * proper response headers.\n     */\n    public function testResponseShouldFailIfNoTokenIsProvided()\n    {\n        $this->request->expects('route->getName')->withNoArgs()->andReturn('random.route');\n        $this->request->expects('bearerToken')->withNoArgs()->andReturnNull();\n\n        try {\n            $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n        } catch (HttpException $exception) {\n            $this->assertEquals(401, $exception->getStatusCode(), 'Assert that a status code of 401 is returned.');\n            $this->assertTrue(is_array($exception->getHeaders()), 'Assert that an array of headers is returned.');\n            $this->assertArrayHasKey('WWW-Authenticate', $exception->getHeaders(), 'Assert exception headers contains WWW-Authenticate.');\n            $this->assertEquals('Bearer', $exception->getHeaders()['WWW-Authenticate']);\n        }\n    }\n\n    /**\n     * Test that passing in an invalid node daemon secret will result in a bad request\n     * exception being returned.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('badTokenDataProvider')]\n    public function testResponseShouldFailIfTokenFormatIsIncorrect(string $token)\n    {\n        $this->expectException(BadRequestHttpException::class);\n\n        $this->request->expects('route->getName')->withNoArgs()->andReturn('random.route');\n        $this->request->expects('bearerToken')->withNoArgs()->andReturn($token);\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Test that an access denied error is returned if the node is valid but the token\n     * provided is not valid.\n     */\n    public function testResponseShouldFailIfTokenIsNotValid()\n    {\n        $this->expectException(AccessDeniedHttpException::class);\n\n        /** @var Node $model */\n        $model = Node::factory()->make();\n\n        $this->request->expects('route->getName')->withNoArgs()->andReturn('random.route');\n        $this->request->expects('bearerToken')->withNoArgs()->andReturn($model->daemon_token_id . '.random_string_123');\n\n        $this->repository->expects('findFirstWhere')->with(['daemon_token_id' => $model->daemon_token_id])->andReturn($model);\n        $this->encrypter->expects('decrypt')->with($model->daemon_token)->andReturns(decrypt($model->daemon_token));\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Test that an access denied exception is returned if the node is not found using\n     * the token ID provided.\n     */\n    public function testResponseShouldFailIfNodeIsNotFound()\n    {\n        $this->expectException(AccessDeniedHttpException::class);\n\n        $this->request->expects('route->getName')->withNoArgs()->andReturn('random.route');\n        $this->request->expects('bearerToken')->withNoArgs()->andReturn('abcd1234.random_string_123');\n\n        $this->repository->expects('findFirstWhere')->with(['daemon_token_id' => 'abcd1234'])->andThrow(RecordNotFoundException::class);\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Test a successful middleware process.\n     */\n    public function testSuccessfulMiddlewareProcess()\n    {\n        /** @var Node $model */\n        $model = Node::factory()->make();\n\n        $this->request->expects('route->getName')->withNoArgs()->andReturn('random.route');\n        $this->request->expects('bearerToken')->withNoArgs()->andReturn($model->daemon_token_id . '.' . decrypt($model->daemon_token));\n\n        $this->repository->expects('findFirstWhere')->with(['daemon_token_id' => $model->daemon_token_id])->andReturn($model);\n        $this->encrypter->expects('decrypt')->with($model->daemon_token)->andReturns(decrypt($model->daemon_token));\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n        $this->assertRequestHasAttribute('node');\n        $this->assertRequestAttributeEquals($model, 'node');\n    }\n\n    /**\n     * Provides different tokens that should trigger a bad request exception due to\n     * their formatting.\n     *\n     * @return array|\\string[][]\n     */\n    public static function badTokenDataProvider(): array\n    {\n        return [\n            ['foo'],\n            ['foobar'],\n            ['foo-bar'],\n            ['foo.bar.baz'],\n            ['.foo'],\n            ['foo.'],\n            ['foo..bar'],\n        ];\n    }\n\n    /**\n     * Return an instance of the middleware using mocked dependencies.\n     */\n    private function getMiddleware(): DaemonAuthenticate\n    {\n        return new DaemonAuthenticate($this->encrypter, $this->repository);\n    }\n}\n"
  },
  {
    "path": "tests/Unit/Http/Middleware/LanguageMiddlewareTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Http\\Middleware;\n\nuse Mockery as m;\nuse Mockery\\MockInterface;\nuse Pterodactyl\\Models\\User;\nuse Illuminate\\Foundation\\Application;\nuse Pterodactyl\\Http\\Middleware\\LanguageMiddleware;\n\nclass LanguageMiddlewareTest extends MiddlewareTestCase\n{\n    private MockInterface $appMock;\n\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->appMock = m::mock(Application::class);\n    }\n\n    /**\n     * Test that a language is defined via the middleware for guests.\n     */\n    public function testLanguageIsSetForGuest()\n    {\n        $this->request->shouldReceive('user')->withNoArgs()->andReturnNull();\n        $this->appMock->shouldReceive('setLocale')->with('zh')->once()->andReturnNull();\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Test that a language is defined via the middleware for a user.\n     */\n    public function testLanguageIsSetWithAuthenticatedUser()\n    {\n        $user = User::factory()->make(['language' => 'de']);\n\n        $this->request->shouldReceive('user')->withNoArgs()->andReturn($user);\n        $this->appMock->shouldReceive('setLocale')->with('de')->once()->andReturnNull();\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Return an instance of the middleware using mocked dependencies.\n     */\n    private function getMiddleware(): LanguageMiddleware\n    {\n        return new LanguageMiddleware($this->appMock);\n    }\n}\n"
  },
  {
    "path": "tests/Unit/Http/Middleware/MaintenanceMiddlewareTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Http\\Middleware;\n\nuse Mockery as m;\nuse Mockery\\MockInterface;\nuse Pterodactyl\\Models\\Node;\nuse Illuminate\\Http\\Response;\nuse Pterodactyl\\Models\\Server;\nuse Illuminate\\Contracts\\Routing\\ResponseFactory;\nuse Pterodactyl\\Http\\Middleware\\MaintenanceMiddleware;\n\nclass MaintenanceMiddlewareTest extends MiddlewareTestCase\n{\n    private MockInterface $response;\n\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->response = m::mock(ResponseFactory::class);\n    }\n\n    /**\n     * Test that a node not in maintenance mode continues through the request cycle.\n     */\n    public function testHandle()\n    {\n        $server = Server::factory()->make();\n        $node = Node::factory()->make(['maintenance' => 0]);\n\n        $server->setRelation('node', $node);\n        $this->setRequestAttribute('server', $server);\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Test that a node in maintenance mode returns an error view.\n     */\n    public function testHandleInMaintenanceMode()\n    {\n        $server = Server::factory()->make();\n        $node = Node::factory()->make(['maintenance_mode' => 1]);\n\n        $server->setRelation('node', $node);\n        $this->setRequestAttribute('server', $server);\n\n        $this->response->shouldReceive('view')\n            ->once()\n            ->with('errors.maintenance')\n            ->andReturn(new Response());\n\n        $response = $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n        $this->assertInstanceOf(Response::class, $response);\n    }\n\n    private function getMiddleware(): MaintenanceMiddleware\n    {\n        return new MaintenanceMiddleware($this->response);\n    }\n}\n"
  },
  {
    "path": "tests/Unit/Http/Middleware/MiddlewareTestCase.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Http\\Middleware;\n\nuse Pterodactyl\\Tests\\TestCase;\nuse Pterodactyl\\Tests\\Traits\\Http\\RequestMockHelpers;\nuse Pterodactyl\\Tests\\Traits\\Http\\MocksMiddlewareClosure;\nuse Pterodactyl\\Tests\\Assertions\\MiddlewareAttributeAssertionsTrait;\n\nabstract class MiddlewareTestCase extends TestCase\n{\n    use MiddlewareAttributeAssertionsTrait;\n    use MocksMiddlewareClosure;\n    use RequestMockHelpers;\n\n    /**\n     * Setup tests with a mocked request object and normal attributes.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->buildRequestMock();\n    }\n}\n"
  },
  {
    "path": "tests/Unit/Http/Middleware/RedirectIfAuthenticatedTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Http\\Middleware;\n\nuse Mockery as m;\nuse Mockery\\MockInterface;\nuse Illuminate\\Auth\\AuthManager;\nuse Illuminate\\Http\\RedirectResponse;\nuse Pterodactyl\\Http\\Middleware\\RedirectIfAuthenticated;\n\nclass RedirectIfAuthenticatedTest extends MiddlewareTestCase\n{\n    private MockInterface $authManager;\n\n    /**\n     * Setup tests.\n     */\n    public function setUp(): void\n    {\n        parent::setUp();\n\n        $this->authManager = m::mock(AuthManager::class);\n    }\n\n    /**\n     * Test that an authenticated user is redirected.\n     */\n    public function testAuthenticatedUserIsRedirected()\n    {\n        $this->authManager->shouldReceive('guard')->with(null)->once()->andReturnSelf();\n        $this->authManager->shouldReceive('check')->withNoArgs()->once()->andReturn(true);\n\n        $response = $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n        $this->assertInstanceOf(RedirectResponse::class, $response);\n        $this->assertEquals(route('index'), $response->getTargetUrl());\n    }\n\n    /**\n     * Test that a non-authenticated user continues through the middleware.\n     */\n    public function testNonAuthenticatedUserIsNotRedirected()\n    {\n        $this->authManager->shouldReceive('guard')->with(null)->once()->andReturnSelf();\n        $this->authManager->shouldReceive('check')->withNoArgs()->once()->andReturn(false);\n\n        $this->getMiddleware()->handle($this->request, $this->getClosureAssertions());\n    }\n\n    /**\n     * Return an instance of the middleware using mocked dependencies.\n     */\n    private function getMiddleware(): RedirectIfAuthenticated\n    {\n        return new RedirectIfAuthenticated($this->authManager);\n    }\n}\n"
  },
  {
    "path": "tests/Unit/Rules/UsernameTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Rules;\n\nuse Pterodactyl\\Rules\\Username;\nuse Pterodactyl\\Tests\\TestCase;\n\nclass UsernameTest extends TestCase\n{\n    /**\n     * Test that this rule can be cast to a string correctly.\n     */\n    public function testRuleIsStringable()\n    {\n        $this->assertSame('p_username', (string) new Username());\n    }\n\n    /**\n     * Test valid usernames.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('validUsernameDataProvider')]\n    public function testValidUsernames(string $username)\n    {\n        $this->assertTrue((new Username())->passes('test', $username), 'Assert username is valid.');\n    }\n\n    /**\n     * Test invalid usernames return false.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('invalidUsernameDataProvider')]\n    public function testInvalidUsernames(string $username)\n    {\n        $this->assertFalse((new Username())->passes('test', $username), 'Assert username is not valid.');\n    }\n\n    /**\n     * Provide valid usernames.\n     */\n    public static function validUsernameDataProvider(): array\n    {\n        return [\n            ['username'],\n            ['user_name'],\n            ['user.name'],\n            ['user-name'],\n            ['123username123'],\n            ['123-user.name'],\n            ['123456'],\n        ];\n    }\n\n    /**\n     * Provide invalid usernames.\n     */\n    public static function invalidUsernameDataProvider(): array\n    {\n        return [\n            ['_username'],\n            ['username_'],\n            ['_username_'],\n            ['-username'],\n            ['.username'],\n            ['username-'],\n            ['username.'],\n            ['user*name'],\n            ['user^name'],\n            ['user#name'],\n            ['user+name'],\n            ['1234_'],\n        ];\n    }\n}\n"
  },
  {
    "path": "tests/Unit/Services/Acl/Api/AdminAclTest.php",
    "content": "<?php\n\nnamespace Pterodactyl\\Tests\\Unit\\Services\\Acl\\Api;\n\nuse Pterodactyl\\Models\\ApiKey;\nuse Pterodactyl\\Tests\\TestCase;\nuse Pterodactyl\\Services\\Acl\\Api\\AdminAcl;\n\nclass AdminAclTest extends TestCase\n{\n    /**\n     * Test that permissions return the expects values.\n     */\n    #[\\PHPUnit\\Framework\\Attributes\\DataProvider('permissionsDataProvider')]\n    public function testPermissions(int $permission, int $check, bool $outcome)\n    {\n        $this->assertSame($outcome, AdminAcl::can($permission, $check));\n    }\n\n    /**\n     * Test that checking against a model works as expected.\n     */\n    public function testCheck()\n    {\n        $model = ApiKey::factory()->make(['r_servers' => AdminAcl::READ | AdminAcl::WRITE]);\n\n        $this->assertTrue(AdminAcl::check($model, AdminAcl::RESOURCE_SERVERS, AdminAcl::WRITE));\n    }\n\n    /**\n     * Provide valid and invalid permissions combos for testing.\n     */\n    public static function permissionsDataProvider(): array\n    {\n        return [\n            [AdminAcl::READ, AdminAcl::READ, true],\n            [AdminAcl::READ | AdminAcl::WRITE, AdminAcl::READ, true],\n            [AdminAcl::READ | AdminAcl::WRITE, AdminAcl::WRITE, true],\n            [AdminAcl::WRITE, AdminAcl::WRITE, true],\n            [AdminAcl::READ, AdminAcl::WRITE, false],\n            [AdminAcl::NONE, AdminAcl::READ, false],\n            [AdminAcl::NONE, AdminAcl::WRITE, false],\n        ];\n    }\n}\n"
  },
  {
    "path": "tsconfig.json",
    "content": "{\n  \"compilerOptions\": {\n    \"target\": \"es2015\",\n    \"module\": \"es2020\",\n    \"jsx\": \"react-jsx\",\n    \"moduleResolution\": \"node\",\n    \"lib\": [\n      \"es2015\",\n      \"dom\"\n    ],\n    \"strict\": true,\n    \"noEmit\": true,\n    \"sourceMap\": true,\n    \"noImplicitReturns\": true,\n    \"skipLibCheck\": true,\n    \"skipDefaultLibCheck\": true,\n    \"esModuleInterop\": true,\n    \"allowSyntheticDefaultImports\": true,\n    \"baseUrl\": \".\",\n    \"verbatimModuleSyntax\": false,\n    \"paths\": {\n      \"@/*\": [\n        \"./resources/scripts/*\"\n      ],\n      \"@definitions/*\": [\n        \"./resources/scripts/api/definitions/*\"\n      ],\n      \"@feature/*\": [\n        \"./resources/scripts/components/server/features/*\"\n      ]\n    },\n    \"plugins\": [\n      {\n        \"name\": \"typescript-plugin-tw-template\"\n      }\n    ],\n    \"typeRoots\": [\n      \"node_modules/@types\"\n    ]\n  },\n  \"include\": [\n    \"./resources/scripts/**/*\"\n  ],\n  \"exclude\": [\n    \"/node_modules/\"\n  ]\n}\n"
  },
  {
    "path": "webpack.config.js",
    "content": "const path = require('node:path');\nconst webpack = require('webpack');\nconst { WebpackAssetsManifest } = require('webpack-assets-manifest');\nconst TerserPlugin = require('terser-webpack-plugin');\n\nconst isProduction = process.env.NODE_ENV === 'production';\n\nmodule.exports = {\n    cache: true,\n    target: 'web',\n    mode: isProduction ? 'production' : 'development',\n    devtool: process.env.DEVTOOL || (isProduction ? false : 'eval-source-map'),\n    performance: {\n        hints: false,\n    },\n    entry: ['react-hot-loader/patch', './resources/scripts/index.tsx'],\n    output: {\n        path: path.join(__dirname, '/public/assets'),\n        filename: isProduction ? 'bundle.[chunkhash:8].js' : 'bundle.[fullhash:8].js',\n        chunkFilename: isProduction ? '[name].[chunkhash:8].js' : '[name].[fullhash:8].js',\n        publicPath: process.env.WEBPACK_PUBLIC_PATH || '/assets/',\n        crossOriginLoading: 'anonymous',\n    },\n    module: {\n        rules: [\n            {\n                test: /\\.tsx?$/,\n                exclude: /node_modules|\\.spec\\.tsx?$/,\n                loader: 'babel-loader',\n            },\n            {\n                test: /\\.mjs$/,\n                include: /node_modules/,\n                type: 'javascript/auto',\n            },\n            {\n                test: /\\.css$/,\n                use: [\n                    { loader: 'style-loader' },\n                    {\n                        loader: 'css-loader',\n                        options: {\n                            modules: {\n                                auto: true,\n                                // https://github.com/webpack/css-loader/blob/main/CHANGELOG.md#700-2024-04-04\n                                namedExport: false,\n                                exportLocalsConvention: 'as-is',\n                                localIdentName: isProduction ? '[name]_[hash:base64:8]' : '[path][name]__[local]',\n                                localIdentContext: path.join(__dirname, 'resources/scripts/components'),\n                            },\n                            sourceMap: !isProduction,\n                            importLoaders: 1,\n                        },\n                    },\n                    {\n                        loader: 'postcss-loader',\n                        options: { sourceMap: !isProduction },\n                    },\n                ],\n            },\n            {\n                test: /\\.(png|jp(e?)g|gif)$/,\n                loader: 'file-loader',\n                options: {\n                    name: 'images/[name].[hash:8].[ext]',\n                },\n            },\n            {\n                test: /\\.(woff|woff2)$/i,\n                type: 'asset/resource',\n            },\n            {\n                test: /\\.svg$/,\n                loader: 'svg-url-loader',\n            },\n            {\n                test: /\\.js$/,\n                enforce: 'pre',\n                loader: 'source-map-loader',\n            },\n        ],\n    },\n    stats: {\n        // Ignore warnings emitted by \"source-map-loader\" when trying to parse source maps from\n        // JS plugins we use, namely brace editor.\n        warningsFilter: [/Failed to parse source map/],\n    },\n    resolve: {\n        extensions: ['.ts', '.tsx', '.js', '.json'],\n        alias: {\n            '@': path.join(__dirname, '/resources/scripts'),\n            '@definitions': path.join(__dirname, '/resources/scripts/api/definitions'),\n            '@feature': path.join(__dirname, '/resources/scripts/components/server/features'),\n        },\n        symlinks: false,\n    },\n    externals: {\n        // Mark moment as an external to exclude it from the Chart.js build since we don't need to use\n        // it for anything.\n        moment: 'moment',\n    },\n    plugins: [\n        new webpack.EnvironmentPlugin({\n            NODE_ENV: process.env.NODE_ENV || 'development',\n            DEBUG: process.env.NODE_ENV !== 'production',\n            WEBPACK_BUILD_HASH: Date.now().toString(16),\n        }),\n        new WebpackAssetsManifest({\n            output: 'manifest.json',\n            writeToDisk: true,\n            publicPath: true,\n            integrity: true,\n            integrityHashes: ['sha384'],\n        }),\n    ],\n    optimization: {\n        usedExports: true,\n        sideEffects: false,\n        runtimeChunk: false,\n        removeEmptyChunks: true,\n        minimize: isProduction,\n        minimizer: [\n            new TerserPlugin({\n                parallel: true,\n                extractComments: false,\n                terserOptions: {\n                    mangle: true,\n                    output: {\n                        comments: false,\n                    },\n                },\n            }),\n        ],\n    },\n    watchOptions: {\n        poll: 1000,\n        ignored: /node_modules/,\n    },\n    devServer: {\n        compress: true,\n        port: 5173,\n        server: {\n            type: 'https',\n            options: process.env.USE_LOCAL_CERTS\n                ? {\n                      ca: path.join(__dirname, '../../docker/certificates/root_ca.pem'),\n                      cert: path.join(__dirname, '../../docker/certificates/pterodactyl.test.pem'),\n                      key: path.join(__dirname, '../../docker/certificates/pterodactyl.test-key.pem'),\n                  }\n                : undefined,\n        },\n        static: {\n            directory: path.join(__dirname, '/public'),\n            publicPath: process.env.WEBPACK_PUBLIC_PATH || '/assets/',\n        },\n        allowedHosts: ['.pterodactyl.test'],\n        headers: {\n            'Access-Control-Allow-Origin': '*',\n        },\n    },\n};\n"
  }
]